is an element to element animation orchestrator for React.js
Clone or download
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Permalink
Type Name Latest commit message Commit time
Failed to load latest commit information.
.storybook feat: adds revealmove and concealmove animations Sep 22, 2018
.vscode feat: introduces internal composable api Oct 6, 2018
packages chore(release): publish v1.4.0 Nov 17, 2018
test
.editorconfig feat(ref-collector): adds ref collector component Apr 16, 2018
.eslintignore chore: replaces tslint with eslint Sep 23, 2018
.eslintrc feat: introduces internal composable api Oct 6, 2018
.gitignore
.npmignore
.prettierrc refactor(babel,ts): rips out babel, adds typescript, adds folder for … Apr 16, 2018
.travis.yml
.yarnrc
CHANGELOG.md
LICENSE Update readme, add license Jul 29, 2017
README.md chore: replaces github pages with netlify Oct 6, 2018
icon.png
lerna.json
package.json
tsconfig.json chore: move files around Sep 15, 2018
yarn.lock

README.md

yubaba

is an element to element animation orchestrator for React.js

npm npm bundle size (minified + gzip) Build Status Dev Dependencies

Example animation using yubaba

Installation

npm install yubaba --save

or

yarn add yubaba

Motivation

Complex page transitions are becoming more common on the web but we're still at a point where we need to write a lot of boilerplate to make it happen, worse yet disjointed parts of our apps needing to know about each other to make it all work.

Yubaba tries to solve this by allowing disjointed parts of your app define what animations they want to happen when a matching partner is found, without explicit knowledge of each other.

See usage and examples for a deeper look at this.

Examples

Parent to child

A list of elements (the parent) transitioning to show more information (the child).

Transformation

Elements transforming into another.

Core

A range of different scenarios for each animation component. Looking for component API docs?

Focal

Transitioning the same element from one place to another.

Supporting

Helping the focal animation look the best it can be.

Usage build ups

We'll build up each step to leave you with an awesome transition. Click each gif to see its codesandbox.

We have two disjointed components that are toggled when clicked (click on Finn!). How can we transition them to each other?

Intro to Yubaba 0/4

Introducing <Baba /> and <CrossFadeMove />

Let's use the Baba and CrossFadeMove components to have them seamlessly transition to the destination. Baba is the brains - it does all of the orchestration. CrossFadeMove is one of many focal animations available - it will cross fade both elements from the starting point to the destination point.

Intro to Yubaba 1/4

Okay so that looks cool, but Finn's sword is shown immediately! Is there anything we can do to make it show after all animations have finished?

Introducing <BabaManager />

Let's bring in a component BabaManager which will be used to delay showing Finn's sword. You can imagine this as content in a page around the destination element that should be shown after all animations have finished.

Intro to Yubaba 2/4

Cool, now we're making progress. We can do better though, what if Finn could really sell his preparation that he's about to attack?

Introducing <CircleExpand />

Let's bring in a component CircleExpand which will expand to fit the viewport, for Finn it will give him some oomph to really sell the attack.

Intro to Yubaba 3/4

Really cool! But both the CircleExpand and CrossFadeMove happening at the same time looks kind of weird, what if we could delay CrossFadeMove until after CircleExpand had finished animating?

Introducing <Wait />

Let's bring in a component Wait which will delay the next animation from happening until after the previous one has finished!

Intro to Yubaba 4/4

And there you have it, a masta-peece!

Create your own animations

Yubaba comes with the ability for you to make your own animations using the same plumbing the official animations are constructed from. Look in src/animations for example implementations.

Tutorial(s) coming soon.

Components

Utility

These components exist to pass data around and orchestrate the animations.

Baba

Docs | Props

This is the primary component in yubaba. When rendering it will be given all of the animation data from its children. When unmounting or flipping the "in" prop from true to false, it will execute all the animations top to bottom if a matching Baba pair is found within 50ms.

import Baba from 'yubaba';

<Baba name="baba">
  {({ ref, style, className }) => <div ref={ref} style={style} className={className} />}
</Baba>;

Target

Docs | Props

Used to explicitly mark the focal element, only a handful of animations require this component to be used, for example Reveal`.

import Baba, { Target } from 'yubaba';

<Baba name="target">
  <Target>{({ ref }) => <div ref={ref} />}</Target>
</Baba>;

Collector

Docs | Props

Used as the glue for all animation components, every animation component will use this internally to pass the data to the parent Baba.

import { Collector } from 'yubaba';

<Collector
  data={{
    action: 'animation',
    payload: {
      beforeAnimate: this.beforeAnimate,
      animate: this.animate,
      afterAnimate: this.afterAnimate,
    },
  }}
>
  {children}
</Collector>;

Focal

Transitioning visually similar elements from one place to another.

Move (example)

Docs | Props

Will transition the destination element from the origin element position.

// origin-element.js
import Baba, { FLIPMove as Move } from 'yubaba';

<Baba name="move">
  <Move>{baba => <div {...baba} />}</Move>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="move">{baba => <div {...baba} />}</Baba>;

FadeMove

Docs | Props

Will position: absolute move the origin element to the destination element while fading out.

// origin-element.js
import Baba, { FadeMove } from 'yubaba';

<Baba name="fade-move">
  <FadeMove>{baba => <div {...baba} />}</FadeMove>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="fade-move">{baba => <div {...baba} />}</Baba>;

CrossFadeMove (example)

Docs | Props

Composes the Move and FadeMove animations for a cross-fade move.

// origin-element.js
import Baba, { CrossFadeMove } from 'yubaba';

<Baba name="cross-fade">
  <CrossFadeMove>{baba => <div {...baba} />}</CrossFadeMove>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="cross-fade">{baba => <div {...baba} />}</Baba>;

Reveal

Docs | Props

Reveals the destination element container from the Target component. A limitation at the moment is the destination element must have an animation defined, if you don't want one to happen use the Noop animation. Requires the use of the Target component to specify the focal element.

// origin-element.js
import Baba, { Reveal, Target } from 'yubaba';

<Baba name="reveal">
  <Reveal>{baba => <div {...baba} />}</Reveal>
</Baba>;

// destination-element.js
import Baba, { Target, Noop } from 'yubaba';

<Baba name="reveal">
  <Noop>
    {baba => (
      <div {...baba}>
        <Target>{target => <div {...target} />}</Target>
      </div>
    )}
  </Noop>
</Baba>;

RevealMove (example)

Docs | Props

Useful for transitioning from a parent to a child, will expand from the focal element to the container. Requires the use of the Target component to specify the focal element.

// origin-element.js
import Baba, { RevealMove } from 'yubaba';

<Baba name="reveal-move">
  <RevealMove>{baba => <div {...baba} />}</RevealMove>
</Baba>;

// destination-element.js
import Baba, { Target, Noop } from 'yubaba';

<Baba name="reveal-move">
  <Noop>
    {baba => (
      <div {...baba}>
        <Target>{target => <div {...target} />}</Target>
      </div>
    )}
  </Noop>
</Baba>;

ConcealMove (example)

Docs | Props

Useful for transitioning from a child to a parent, will shrink from the container to the focal element. Requires the use of the Target component to specify the focal element.

// origin-element.js
import Baba, { Target, ConcealMove } from 'yubaba';

<Baba name="conceal-move">
  <ConcealMove>
    {baba => (
      <div {...baba}>
        <Target>{target => <div {...target} />}</Target>
      </div>
    )}
  </ConcealMove>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="conceal-move">{baba => <div {...baba} />}</Baba>;

Noop

Docs | Props

A no-operation "noop" animation.

// origin-element.js
import Baba, { Noop } from 'yubaba';

<Baba name="noop">
  <Noop>{baba => <div {...baba} />}</Noop>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="noop">{baba => <div {...baba} />}</Baba>;

Supporting

Helping the focal animation look the best it can be when transitioning.

BabaManager (example)

Docs | Props

Used to hide contents before an animation is complete triggered from a child component. If there is more than one child you can use an optional name prop which should match the appropriate component.

If it is the initial mount it will immediately be shown.

// origin-element.js
import Baba, { Move } from 'yubaba';

<Baba name="expand">
  <Move>{baba => <div {...baba} />}</Move>
</Baba>;

// destination-element.js
import Baba, { BabaManager } from 'yubaba';

<BabaManager>{({ style }) => <div style={style}>{<Baba>{/* ... */}</Baba>}</div>}</BabaManager>;

Wait

Docs | Props

Is used to pause the execution of all child animations until all parent children animations have completed.

E.g: CircleExpand will wait until Move has finished before starting.

// origin-element.js
import Baba, { Wait, Move, CircleExpand } from 'yubaba';

<Baba name="wait">
  <Move>
    <Wait>
      <CircleExpand>{baba => <div {...baba} />}</CircleExpand>
    </Wait>
  </Move>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="wait">{baba => <div {...baba} />}</Baba>;

CircleExpand (example)

Docs | Props

Will animate a circle from the origin element to cover the entire viewport, and then fade out.

Generally you should use CircleExpand and CricleShrink together to seamlessly transition the background between pages.

// origin-element.js
import Baba, { CircleExpand } from 'yubaba';

<Baba name="expand">
  <CircleExpand>{baba => <div {...baba} />}</CircleExpand>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="expand">{baba => <div {...baba} />}</Baba>;

CircleShrink (example)

Docs | Props

Will animate a circle from the viewport to destination element, and then fade out.

Generally you should use CircleExpand and CricleShrink together to seamlessly transition the background between pages.

// origin-element.js
import Baba, { CircleShrink } from 'yubaba';

<Baba name="shrink">
  <CircleShrink>{baba => <div {...baba} />}</CircleShrink>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="shrink">{baba => <div {...baba} />}</Baba>;

Swipe (example)

Docs | Props

Will animate a square swiping over the viewport.

// origin-element.js
import Baba, { Swipe } from 'yubaba';

<Baba name="swipe">
  <Swipe>{baba => <div {...baba} />}</Swipe>
</Baba>;

// destination-element.js
import Baba from 'yubaba';

<Baba name="swipe">{baba => <div {...baba} />}</Baba>;

API Reference

See typedoc.