Как прикрепить несколько реактивных пружин к одному компоненту? - PullRequest
0 голосов
/ 02 августа 2020

Я пытаюсь научиться использовать реакцию-пружину. Предположим, у меня есть три div для анимации.

<a.div style={trans1}>
<a.div style={trans2}>
<a.div style={trans3}>

и trans1 имеют следующую конфигурацию ...

  const [clicked, toggle] = useState(null)
  const { x } = useSpring({
    from: { x: 0 },
    x: clicked ? 1 : 0,
    config: { duration: 500 },
  })

  const trans1 = {
    transform: x
      .interpolate({
        range: [0, 0.25, 0.35, 0.45, 0.55, 0.65, 0.75, 1],
        output: [1, 0.97, 0.9, 1.1, 0.9, 1.1, 1.03, 1],
      })
      .interpolate((x) => `scale(${x})`),
  }

Как лучше всего реализовать тот же тип анимации на втором и третьи дивы без дублирования всего этого кода? Как сделать несколько экземпляров одной и той же пружины для использования на нескольких объектах Dom, не запуская их все одновременно? Я, конечно, не хочу дублировать полный набор кода для каждого элемента, верно?

Нужно ли мне создавать функцию, которая принимает параметр, который может переключать аргументы в конфигурации на лету? ??‍♂️ Любая помощь приветствуется.

Вот живой пример: https://codesandbox.io/s/optimistic-bassi-brnle

Как сделать, чтобы левая и правая стороны анимировались по очереди без создаете повторяющийся код?

1 Ответ

1 голос
/ 02 августа 2020

Первой возможностью было бы разделить стиль и передать его более чем одному div. Его недостаток в том, что они будут вести себя точно так же одновременно.

  const style = {
    opacity: x.interpolate({ range: [0, 1], output: [0.3, 1] }),
    transform: x
      .interpolate({
        range: [0, 0.25, 0.35, 0.45, 0.55, 0.65, 0.75, 1],
        output: [1, 0.97, 0.9, 1.1, 0.9, 1.1, 1.03, 1]
      })
      .interpolate(x => `scale(${x})`)
  };
  return (
    <div onClick={() => toggle(!state)}>
      <animated.div
        style={style}>
        click
      </animated.div>
      <animated.div
        style={style}>
        click
      </animated.div>
    </div>
  )

Второй вариант заключается в том, что вы создаете новый компонент с помощью щелчка и пружины logi c. Таким образом, вы записываете logi c один раз и можете использовать его несколько раз. Я ввел текстовый атрибут, чтобы сделать другой текст для компонента.

const AnimText = ({text}) => {
  const [state, toggle] = useState(true)
  const { x } = useSpring({ from: { x: 0 }, x: state ? 1 : 0, config: { duration: 1000 } })
  return (
    <div onClick={() => toggle(!state)}>
      <animated.div
        style={{
          opacity: x.interpolate({ range: [0, 1], output: [0.3, 1] }),
          transform: x
            .interpolate({
              range: [0, 0.25, 0.35, 0.45, 0.55, 0.65, 0.75, 1],
              output: [1, 0.97, 0.9, 1.1, 0.9, 1.1, 1.03, 1]
            })
            .interpolate(x => `scale(${x})`)
        }}>
        {text}
      </animated.div>
    </div>
  )
}

function Demo() {
  return (
    <div>
      <AnimText text={'click1'}/>
      <AnimText text={'click2'}/>
      <AnimText text={'click3'}/>
    </div>
  )
}

вот пример: https://codesandbox.io/s/divine-water-n1b6x

...