0.0.4 • Published 7 years ago

react-motion-flip-animated v0.0.4

Weekly downloads
1
License
MIT
Repository
github
Last release
7 years ago

react-motion-flip-animated

Render here, render there, watch it animate, move on.

React Motion Flip Animated is a one component library that makes it dead simple to animate anything from here to there.

It makes use of the FLIP animation technique in combination with react-motion to automagically animate anything you throw at it, no measuring pixels required.

npm version

import { Animated } from 'react-motion-flip-animated';

// render this...
<div>
  <div className="here">
    <Animated id="animate-me">
      <MyCoolComponent />
    </Animated>
  </div>
  <div className="there">
    null
  </div>
</div>

// then render this...
<div>
  <div className="here">
    null
  </div>
  <div className="there">
    <Animated id="animate-me">
      <MyCoolComponent />
    </Animated>
  </div>
</div>

gif here

Install

npm install --save react-motion react-motion-flip-animated

Yes there is a peer dependency on react-motion (and obviously react);

If you're allergic to module bundling:

// unpkg build coming soon...

Use it

react-motion-flip-animated exports a single component Animated.

Make something move from here to there

  • Wrap it inside an Animated with a unique id.
<Animated id="animated-thingy">
  <MyCoolComponent />
</Animated>
  • Render it somewhere "before"
<div className="somewhere">
  <Animated id="animated-thingy">
    <MyCoolComponent />
  </Animated>
</div>
  • Cause it to render elsewhere "after" (due to a state/props/context change).
<div className="somewhere">
  null
</div>
<div className="elsewhere">
  <Animated id="animated-thingy">
    <MyCoolComponent />
  </Animated>
</div>

Warning: Your animated must remain mounted between your before and after renders. If the animated unmounts (is not rendered) for just a single update, it loses memory of its last position and assumes it is new.

You can also make things swap positions:

  • Render the before.
<div className="somewhere">
  <Animated id="animated-thingy-1">
    <Component1 />
  </Animated>
</div>
<div className="elsewhere">
  <Animated id="animated-thingy-2">
    <Component2 />
  </Animated>
</div>
  • Render the after (with your animateds swapped).
<div className="somewhere">
  <Animated id="animated-thingy-2">
    <Component2 />
  </Animated>
</div>
<div className="elsewhere">
  <Animated id="animated-thingy-1">
    <Component1 />
  </Animated>
</div>

And even reorder entire collections:

  • Render (also supplying the index prop).
<div>
  {this.state.items.map(({ id, ...etc }, i) => (
    <Animated id={id} key={id} index={i}>
      <Component {...etc} />
    </Animated>
  ))}
</div>
  • Reorder the items.
  • Render again.

Remember: the key prop goes on the root node of any element in an array, however, the index prop is for <Animated> only. For example:

<div>
  {this.state.items.map(({ id, ...etc }, i) => (
    <div className="wrap-each-item-but-don't-animate-this-element" key={id}>
      <Animated id={id} index={i}>
        <Component {...etc} /> // I'll still be animated
      </Animated>
    </div>
  ))}
</div>

API

Props

  • id: string (required)

    An id for tracking this specific animated component. It must be unique from all other ids of <Animated>s currently being rendered. If you happen to use two of the same id, there will be no warning (currently), and the animation won't occur.

  • index: number (optional)

    The index of this item, if this item was rendered in a collection. You must supply this prop when rendering collections of <Animated>s that you wish to reanimate when reordered. (If you for some reason don't want that, don't supply the prop).

  • children: ReactElement | ManualRenderFunction (required)

    What will be rendered.

    • If ReactElement: the element will be wrapped in a <div>, and that div will receive style={{ transform: `translate(${translateX}px, ${translateY}px)` }} to perform the animation. If you want to avoid the extra div and apply the transformation directly to your component, use a ManualRenderFunction instead.

    • If ManualRenderFunction: this function will be called with the signature (getRef: (node) => void, AnimationData { translateX: number, translateY: number, progress: number, isAnimating: boolean }) => ReactElement. This will be called every frame with updated (tweened) animation data. You must supply getRef to the root element of your component as a ref callback so that its position can be measured, and you must apply the transformation yourself. progress is a number from 0 to (over) 100 (it may go over 100 if the animation overshoots the target. ie. animation === 100 does not mean the animation has finished).

  • spring: SpringConfig (optional)

    This is a react-motion spring config, which has the shape { stiffness: number (optional), damping: number (optional), precision: number (optional) }, you can use this to configure the physics of the animation.

  • transitionBegan: function (optional)

    A callback which is triggered when the transition animation has begun.

  • transitionFinished: function (optional)

    A callback which is triggered when the transition animation has come to a full stop.

Run the demos

git clone https://github.com/MarcoThePoro/react-motion-flip-animated.git
cd react-motion-flip-animated
npm install
npm run storybook

Then navigate to http://localhost:9001

Test it

404 tests not found

FAQ

  • I'm trying to swap two <Animated>s but they're jumping to their new position without animating.

    Check if you're accidentally giving them the same id.

  • I'm trying to reorder a collection of <Animated>s but they're jumping to their new position without animating.

    Ensure you're supplying correct values for key (trackable across renders) and index (position in collection).

  • Help! Now that all the animation work is done by this library, I no longer have a job!

    Oh no!

0.0.4

7 years ago

0.0.3

7 years ago

0.0.2

7 years ago

0.0.1

7 years ago