Edit Page

#Frame

The basic container for layout, styling, animation and events.

The Frame component is a div with extra options and opinionated defaults to get things done more quickly. The top level props just generate style for the underlying div, but you always override any styling with the style prop. Frames allow you to do the following.

  • Set sizes and add layout constraints.
  • Center horizontally or vertically.
  • Change colors or background images.
  • Animate between states (variants).
  • Add tap events that work on desktop and mobile.
  • Add advanced behavior like dragging.
  • Respond to advanced gestures like pan.

Framer Library v0.10 and earlier used an older Frame API.
import * as React from "react"
import { Frame } from "framer"

export function MyComponent() {
  return (
    <Frame size={300} center>
      Hello
    </Frame>
  )
}

#Performance

To get the most performance from your animations, try to only animate transform values and opacity, as they are GPU-accelerated. This way, you can animate hundreds of layers on modern mobile devices.

// GPU accelerated (fast)
<Frame initial={{scale: 1}} animate={{scale: 2}} />

// CPU drawing (slower)
<Frame initial={{size: 200}} animate={{size: 400}} />

#Integration

The Frame component was designed to play nice with any DOM element, mainly because it is a DOM element (regular div) itself. You can use any layout combination between size, width, height, top, right, bottom, left and center.

Here’s an example of a complicated dynamic layout that uses variable, fixed and centered layout right inside a parent div.

export function MyComponent(props) {
  return (
    <div
      style={{
        width: "100%",
        height: "100%",
        background: "rgba(255, 0, 0, .5)",
      }}
    >
      <Frame size="40%" center="x" top={50}>
        Hello
      </Frame>
    </div>
  )
}

#Text Centering

If your Frame only contains text contents, it will be centered by default for convenience. You can avoid this behavior by wrapping the text in a span element.

// Text contents will be centered
<Frame>Hello</Frame>

// Text contents will not be centered
<Frame><span>Hello</span></Frame>

#Event Handling

Event propagation is handled by React and behaves like DOM events. You can cancel events with preventDefault() and stop propagation with stopPropagation().


#DOM

The Frame component is based on an HTML div so it inherits all DOM properties using camelCasing.

// CSS classes
<Frame className="pretty" />

// DOM events
<Frame onClick={onClick} />
<Frame onMouseOut={onMouseOut} />
<Frame onTouchUp={onTouchUp} />


#Layout

Layout rules for Frame behave like regular CSS, and re-layout if the parent element (Frame or div) resizes. You can optionally use handy shortcuts like center to quickly center elements in their parent.

Frames are positioned absolute by default. You can explicitly change this with the position property. If you add a Frame as a child of a component that expects relative layout (like Stack), that component may override the position to relative automatically, for convenience.

When the combination of layout properties is incompatible, the override order is consistent with CSS. The x and y transforms always work, as they are applied after the normal layout rules are set.

  • height > top, bottom > center=“y”
  • width > left, right > center=“x”
// Right is ignored
<Frame width={100} left={100} right={100} />

// Center is ignored
<Frame left={0} right={100} center="x" />

#width: number | string | MotionValue<number | string>

Set the CSS width property. Set to 200 by default. Accepts all CSS value types (including pixels, percentages, keywords and more).

// Pixels
<Frame width={100} />

// Percentages
<Frame width={"100%"} />

#height: number | string | MotionValue<number | string>

Set the CSS height property. Set to 200 by default. Accepts all CSS value types (including pixels, percentages, keywords and more).

// Pixels
<Frame height={100} />

// Percentages
<Frame height={"100%"} />

#size: number | string

Shortcut for setting the width and height simultaneously.

<Frame size={100} />

#top: number | string | MotionValue<number | string>

Distance from the top in pixels. Set to 0 by default.

<Frame top={100} />

#right: number | string | MotionValue<number | string>

Distance from the right in pixels. Set to 0 by default.

<Frame right={100} />

#bottom: number | string | MotionValue<number | string>

Distance from the bottom in pixels. Set to 0 by default.

<Frame bottom={100} />

#left: number | string | MotionValue<number | string>

Distance from the left in pixels. Set to 0 by default.

<Frame left={100} />

#center: boolean | "x" | "y"

Shortcut for centering Frames.

// Center
<Frame center />

// Center horizontally
<Frame center="x" />

// Center vertically
<Frame center="y" />

#position: string

Set the CSS position property. Set to "absolute" by default.

<Frame position={"relative"} />

#Visual

#style: MotionStyle

The React DOM style prop, useful for setting CSS properties that aren't explicitly exposed by Frame props.

<Frame style={{ mixBlendMode: "difference" }}  />

#visible: boolean

Defines whether or not the Frame is visible. Unlike opacity, this property cannot be animated. Set to true by default. Maps to CSS.

<Frame visible={false} />

#opacity: number | MotionValue<number>

Set the opacity value, which allows you to make elements semi-transparent or entirely hidden. Useful for show-and-hide animations. Set to 1 by default.

<Frame opacity={0.5} />

#background: Background | null

Set the background of a Frame. Supports color strings, color objects and images by using src. Set to a semi-transparent blue color by default. This will override the values set by the image property. To use a color and a image, use backgroundColor instead

<Frame background="#09F"/>
<Frame background={Color({r: 255, g: 0, b: 102})} />
<Frame background={{ alpha: 1, angle: 75, start: "#09F", end: "#F09"}} />
<Frame background={{ src: "https://example.com/logo.png"}} />

#backgroundColor: string | Color

Set the background color of a Frame. Supports color strings and objects. Use this property to set a background color alongside the image property.

<Frame backgroundColor="#09F"/>
<Frame backgroundColor={Color({r: 255, g: 0, b: 102})} />

#image: string

Sets a background image of a Frame. Will wrap the passed value in a url('') if needed.

<Frame image="https://source.unsplash.com/random" />

#color: string | MotionValue<string>

Set the color for text elements inside of a Frame. By default, text within Frames will be rendered in black.

<Frame color="#09F" />

#border: string | MotionValue<string>

Set the CSS border property, which accepts width, style and color. Set to "none" by default.

<Frame border="1px solid #09F" />

#radius: number | string | MotionValue<number | string>

Set the CSS border-radius property, in pixels or percentages. Set to 0 by default.

// Radius with pixels
<Frame radius={10} />

// Radius with percentages
<Frame radius="50%" />

#shadow: string | MotionValue<string>

Set the CSS box-shadow property.

<Frame shadow="10px 5px 5px black" />

#overflow: "visible" | "hidden"

Set the CSS overflow property. Set to "visible" by default.

<Frame overflow="hidden" />

#Transform

Transform properties are accelerated by the GPU and therefore animate smoothly. They are directly mapped to their CSS transform() counterparts, so x = 200 becomes transform: translateX(200). The transformations are applied after the normal layout rules.

The exact order how the transforms are applied is: translate, scale, rotate and skew. You can customize the order using transformTemplate.

<Frame
  x={100}
  y={100}
  z={100}
  rotate={90}
  scale={1.2}
  skew={15}
/>

#x: number | string | MotionValue<number | string>

Set the CSS transform translateX property.

<Frame x={100} />

#y: number | string | MotionValue<number | string>

Set the CSS transform translateY property.

<Frame y={100} />

#z: number | string | MotionValue<number | string>

Set the CSS transform translateZ property.

<Frame z={100} />

#rotate: number | string | MotionValue<number | string>

Set the CSS transform rotate property in degrees.

<Frame rotate={45}/>

#rotateX: number | string | MotionValue<number | string>

Set the CSS transform rotateX property in degrees.

<Frame rotateX={45}/>

#rotateY: number | string | MotionValue<number | string>

Set the CSS transform rotateY property in degrees.

<Frame rotateY={45}/>

#rotateZ: number | string | MotionValue<number | string>

Set the CSS transform rotateZ property in degrees.

<Frame rotateZ={45}/>

#scale: number | string | MotionValue<number | string>

Set the CSS transform scale property.

<Frame scale={1.5} />

#scaleX: number | string | MotionValue<number | string>

Set the CSS transform scaleX property.

<Frame scaleX={1.5} />

#scaleY: number | string | MotionValue<number | string>

Set the CSS transform scaleY property.

<Frame scaleY={2} />

#skew: number | string | MotionValue<number | string>

Set the CSS transform skew property in degrees.

<Frame skew={15} />

#skewX: number | string | MotionValue<number | string>

Set the CSS transform skewX property in degrees.

<Frame skewX={15} />

#skewY: number | string | MotionValue<number | string>

Set the CSS transform skewY property in degrees.

<Frame skewY={15} />

#originX: number | string | MotionValue<number | string>

Set the CSS transform originX property.

<Frame originX={0.5} />

#originY: number | string | MotionValue<number | string>

Set the CSS transform originY property.

<Frame originY={0.5} />

#originZ: number | string | MotionValue<number | string>

Set the CSS transform originZ property. Defaults to px units.

<Frame originZ={100} />

#perspective: number | string | MotionValue<number | string>

Set the CSS perspective property.

<Frame perspective={500} />

#preserve3d: boolean

Position the children of the frame in 3D space. Set to false by default.

<Frame preserve3d={true} />

#backfaceVisible: boolean

Sets whether the back face is visible when turned towards the user. Set to true by default.

<Frame backfaceVisible={true} />

#transformTemplate(transform, generatedTransform): string

By default, Framer Motion generates a transform property with a sensible transform order. transformTemplate can be used to create a different order, or to append/preprend the automatically generated transform property.

function transformTemplate({ x, rotate }) {
  return `rotate(${rotate}deg) translateX(${x}px)`
}

<Frame x={0} rotate={180} transformTemplate={transformTemplate} />
transform: TransformProperties

The latest animated transform props.

generatedTransform: string

The transform string as automatically generated by Framer Motion

returns: string

#Animation

The following are properties accepted by the Frame component for animation, in addition to its standard properties. When animation properties are combined, they become very flexible and powerful.


#initial: boolean | Target | VariantLabels

Properties, variant label or array of variant labels to start in.

Set to false to initialise with the values in animate (disabling the mount animation)

// As values
<Frame initial={{ opacity: 1 }} />

// As variant
<Frame initial="visible" variants={variants} />

// Multiple variants
<Frame initial={["visible", "active"]} variants={variants} />

// As false (disable mount animation)
<Frame initial={false} animate={{ opacity: 0 }} />

#animate: AnimationControls | TargetAndTransition | VariantLabels

Values to animate to, variant label(s), or AnimationControls.

// As values
<Frame animate={{ opacity: 1 }} />

// As variant
<Frame animate="visible" variants={variants} />

// Multiple variants
<Frame animate={["visible", "active"]} variants={variants} />

// AnimationControls
<Frame animate={animation} />

#exit: AnimationControls | TargetAndTransition | VariantLabels

A target to animate to when this component is removed from the tree.

This component **must** be the first animatable child of an AnimatePresence to enable this exit animation.

This limitation exists because React doesn't allow components to defer unmounting until after an animation is complete. Once this limitation is fixed, the AnimatePresence component will be unnecessary.

import { Frame, AnimatePresence } from 'framer'

export function MyComponent(props) {
  return (
    <AnimatePresence>
       {props.isVisible && (
         <Frame
           initial={{ opacity: 0 }}
           animate={{ opacity: 1 }}
           exit={{ opacity: 0 }}
         />
       )}
    </AnimatePresence>
  )
}

#transition: Transition

Default transition. If no transition is defined in animate, it will use the transition defined here.

const spring = {
  type: "spring",
  damping: 10,
  stiffness: 100
}

<Frame transition={spring} animate={{ scale: 1.2 }} />

#positionTransition: Transition | boolean | ResolveLayoutTransition

When a Frame is the child of a Stack, the Stack is responsible for its layout. This makes it harder for us to know when a Frame's position changes within the Stack and make it animate to its new position.

By adding positionTransition to a Frame, it'll automatically animate to its new position in the Stack, whether the Stack layout has changed or the Frame has changed its order within it.

It can either be set as a Transition, or just true to use the default layout transition.

function MyComponent({ distribution = "space-around" }) {
  const spring = {
    type: "spring",
    damping: 10,
    stiffness: 100
  }

  return (
    <Stack distribution={distribution}>
      <Frame layoutTransition={spring} />
    </Stack>
  )
}

#onUpdate(latest): void

Callback with latest motion values, fired max once per frame.

function onUpdate(latest) {
  console.log(latest.x, latest.opacity)
}

<Frame animate={{ x: 100, opacity: 0 }} onUpdate={onUpdate} />
latest: { [key: string]: string | number; }

#onAnimationStart(): void

Callback when animation defined in animate begins.

function onStart() {
  console.log("Animation completed")
}

<Frame animate={{ x: 100 }} onAnimationStart={onStart} />

#onAnimationComplete(): void

Callback when animation defined in animate is complete.

function onComplete() {
  console.log("Animation completed")
}

<Frame animate={{ x: 100 }} onAnimationComplete={onComplete} />

#Transition

The transition property can be used to customise animations directly on a Frame. A transition typically defines a single transition that applies to all animating values on that Frame. It’s possible to override this transition property if a transition is added to an object or variants label given to the animate, hover or press properties.

<Frame
  animate={{ scale: 0.5 }}
  transition={{ ease: "easeOut" }}
/>

You can also define a seperate transition for each animating value on the Frame. Any properties left unspecified will use a default transition.

const transition = {
  x: { type: "spring", stiffness: 400 },
  opacity: { ease: "easeIn" },
}

To override the default transition, when defining separate transitions for each animating value, you can override the default property.

const transition = {
  x: { type: "keyframes", values: [0, 100, 0] },
  default: { duration: 0.5 },
}

You can add orchestration properties like delay to affect the whole animation. The numeric value represent seconds.

const transition = {
  delay: 1,
  opacity: { duration: 0.5 },
}

The transition property can also be specified inside your variants object and then passed to your Frame using the variants property.

const variants = {
  hidden: {
    opacity: 0,
    transition: { duration: 0.25 },
  },
  visible: { opacity: 1 },
}

#Variants

Variants are an advanced way to organize your animation states by name.

#variants: Variants

Variants allow you to define animation states and organise them by name. They allow you to control animations throughout a component tree by switching a single animate prop.

Using transition options like delayChildren and staggerChildren, you can orchestrate when children animations play relative to their parent.

After passing variants to one or more Frame's variants prop, these variants can be used in place of values on the animate, initial, whileTap and whileHover props.

const variants = {
  active: {
    backgroundColor: "#f00"
  },
  inactive: {
    backgroundColor: "#fff",
    transition: { duration: 2 }
  }
}

<Frame variants={variants} animate="active" />

#Tap

The tap gesture detects when a pointer presses down and releases on the same component.

It fires an tap event when tapping successfully completes on an component, and a tapCancel event when tapping ends outside the component.

If the tappable component is a child of a draggable component, it'll automatically cancel the tap gesture if the pointer moves further than 3 pixels during the gesture.


#whileTap: string | TargetAndTransition

Properties or variant label to animate to while the component is pressed.

<Frame whileTap={{ scale: 0.8 }} />

#onTap(event, info): void

Callback when the tap gesture successfully ends on this element.

function onTap(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onTap={onTap} />
event: MouseEvent | TouchEvent | PointerEvent

The originating pointer event.

info: TapInfo

An TapInfo object containing x and y values for the point relative to the device or page.

#onTapStart(event, info): void

Callback when the tap gesture starts on this element.

function onTapStart(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onTapStart={onTapStart} />
event: MouseEvent | TouchEvent | PointerEvent

The originating pointer event.

info: TapInfo

An TapInfo object containing x and y values for the point relative to the device or page.

#onTapCancel(event, info): void

Callback when the tap gesture ends outside this element.

function onTapCancel(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onTapCancel={onTapCancel} />
event: MouseEvent | TouchEvent | PointerEvent

The originating pointer event.

info: TapInfo

An TapInfo object containing x and y values for the point relative to the device or page.

#Hover

The hover gesture detects when a pointer hovers over or leaves a component.

It differs from onMouseEnter and onMouseLeave in that hover is guaranteed to only fire as a result of actual mouse events (as opposed to browser-generated mice events emulated from touch input).

#whileHover: string | TargetAndTransition

Properties or variant label to animate to while the hover gesture is recognised.

<Frame whileHover={{ scale: 1.2 }} />

#onHoverStart(event, info): void

Callback function that fires when pointer starts hovering over the component.

function onHoverStart(event) {
  console.log("Hover starts")
}

<Frame onHoverStart={onHoverStart} />
event: MouseEvent
info: EventInfo

#onHoverEnd(event, info): void

Callback function that fires when pointer stops hovering over the component.

function onHoverEnd(event) {
  console.log("Hover ends")
}

<Frame onHoverEnd={onHoverEnd} />
event: MouseEvent
info: EventInfo

#Pan

The pan gesture recognises when a pointer presses down on a component and moves further than 3 pixels. The pan gesture is ended when the pointer is released.

#onPan(event, info): void

Callback function that fires when the pan gesture is recognised on this element.

function onPan(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onPan={onPan} />
event: MouseEvent | TouchEvent | PointerEvent

The originating pointer event.

info: PanInfo

A PanInfo object containing x and y values for:

  • point: Relative to the device or page.
  • delta: Distance moved since the last event.
  • offset: Offset from the original pan event.
  • velocity: Current velocity of the pointer.

#onPanStart(event, info): void

Callback function that fires when the pan gesture begins on this element.

function onPanStart(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onPanStart={onPanStart} />
event: MouseEvent | TouchEvent | PointerEvent

The originating pointer event.

info: PanInfo

A PanInfo object containing x/y values for:

  • point: Relative to the device or page.
  • delta: Distance moved since the last event.
  • offset: Offset from the original pan event.
  • velocity: Current velocity of the pointer.

#onPanEnd(event, info): void

Callback function that fires when the pan gesture ends on this element.

function onPanEnd(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onPanEnd={onPanEnd} />
event: MouseEvent | TouchEvent | PointerEvent

The originating pointer event.

info: PanInfo

A PanInfo object containing x/y values for:

  • point: Relative to the device or page.
  • delta: Distance moved since the last event.
  • offset: Offset from the original pan event.
  • velocity: Current velocity of the pointer.

#Drag

The drag gesture follows the rules of the pan gesture but applies pointer movement to the x and/or y axis of the component.

#onDrag(event, info): void

Callback function that fires when the component is dragged.

function onDrag(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame drag onDrag={onDrag} />
event: MouseEvent | TouchEvent | PointerEvent
info: PanInfo

#onDragStart(event, info): void

Callback function that fires when dragging starts.

function onDragStart(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame drag onDragStart={onDragStart} />
event: MouseEvent | TouchEvent | PointerEvent
info: PanInfo

#onDragEnd(event, info): void

Callback function that fires when dragging ends.

function onDragEnd(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame drag onDragEnd={onDragEnd} />
event: MouseEvent | TouchEvent | PointerEvent
info: PanInfo

#onDirectionLock(axis): void

Callback function that fires a drag direction is determined.

function onDirectionLock(axis) {
  console.log(axis)
}

<Frame
  drag
  dragDirectionLock
  onDirectionLock={onDirectionLock}
/>
axis: "x" | "y"

#drag: boolean | "x" | "y"

Enable dragging for this element. Set to false by default. Set true to drag in both directions. Set "x" or "y" to only drag in a specific direction.

<Frame drag="x" />

#dragConstraints: false | { top?: number; right?: number; bottom?: number; left?: number; } | RefObject<Element>

An object of optional top, left, right, bottom pixel values, beyond which dragging is constrained.

Another component can be used as drag constraints by creating a ref with React's useRef.hook. This ref should be passed to that component's ref prop and to this component's dragConstraints prop.

// In pixels
<Frame
  drag="x"
  dragConstraints={{ left: 0, right: 300 }}
/>

// As a ref to another component
function MyComponent() {
  const constraintsRef = useRef(null)

  return (
     <Frame ref={constraintsRef} width={400} height={400}>
         <Frame drag dragConstraints={constraintsRef} />
     </Frame>
  )
}

#dragElastic: boolean | number

The degree of movement allowed outside constraints. 0 = no movement, 1 = full movement. Set to 0.5 by default.

<Frame
  drag={true}
  dragConstraints={{ left: 0, right: 300 }}
  dragElastic={0.2}
/>

#dragMomentum: boolean

Apply momentum from the pan gesture to the component when dragging finishes. Set to true by default.

<Frame
  drag={true}
  dragConstraints={{ left: 0, right: 300 }}
  dragMomentum={false}
/>

#dragTransition: InertiaOptions

Allows you to change dragging inertia parameters. When releasing a draggable Frame, an animation with type inertia starts. The animation is based on your dragging velocity. This property allows you to customize it. See Inertia for all properties you can use.

<Frame
  drag={true}
  dragTransition={{ bounceStiffness: 600, bounceDamping: 10 }}
/>

#dragPropagation: boolean

Allows drag gesture propagation to child components. Set to false by default.

<Frame drag="x" dragPropagation={true} />

#Types

#TapInfo

Passed in to tap event handlers like onTap the TapInfo object contains information about the tap gesture such as it‘s location.

function onTap(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onTap={onTap} />

#point: Point

Contains x and y values for the tap gesture relative to the device or page.

function onTapStart(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onTapStart={onTapStart} />

#PanInfo

Passed in to pan event handlers like onPan the PanInfo object contains information about the current state of the tap gesture such as its point, delta, offset and velocity.

function onPan(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onPan={onPan} />

#delta: Point

Contains x and y values for the distance moved since the last event.

function onPan(event, info) {
  console.log(info.delta.x, info.delta.y)
}

<Frame onPan={onPan} />

#offset: Point

Contains x and y values for the distance moved from the first pan event.

function onPan(event, info) {
  console.log(info.offset.x, info.offset.y)
}

<Frame onPan={onPan} />

#point: Point

Contains x and y values for the current pan position relative to the device or page.

function onPan(event, info) {
  console.log(info.point.x, info.point.y)
}

<Frame onPan={onPan} />

#velocity: Point

Contains x and y values for the current velocity of the pointer.

function onPan(event, info) {
  console.log(info.velocity.x, info.velocity.y)
}

<Frame onPan={onPan} />