Components Components are reusable, interactive building blocks that you can compose into larger ones to make up entire screens, interfaces and apps.

In most other graphics tools, components are visual — a picture of a button, slider or toggle. The big difference is that in Framer X, components can be interactive. They scroll, click, move and handle input, all backed by the popular React JavaScript framework for building interfaces.

To create a new component, you can navigate to the Components panel and click the New Component button located at the bottom. You can create two types of components: Design and Code. A design component is created by selecting an element on your canvas. A code component is created from scratch, and you’ll be presented with a new .tsx file.

Design First, give your design component a unique name in the Layer Panel. Then, right click on the layer and select Create Design Component. You can also create new design components from selection by hitting CMD + K.

The design components you see in the panel are referred to as a master components. All of your own master components live on the canvas: removing them from the canvas will also remove them from the Components panel. If you paste, duplicate or drag a component from the panel to the canvas, you’ll create an instance of that component. All changes made to the master will be reflected within each instance. You can still override the properties of any single instance and customize things like color, opacity and radius, or layout options like position and size. Don’t like the end result? Right-click and hit Reset Overrides to revert styling back to match the master component.

Code Interactive components are code components, written in React. You can also render plain HTML elements, and style them with CSS, so setting up your first code component is easier than it may sound. In our documentation, we assume a basic knowledge of HTML/CSS/Javascript. For a refresher or more information, please read React’s Getting Started guide.

React

React components use JSX, an HTML-like markup language. Below you’ll find a very basic example of a React component. Notice how the render() method returns something very close to plain HTML and CSS. As you learn, we highly recommend to check out the official React documentation.

import * as React from "react"; ​
 
export class Example extends React.Component {
    render() {
        return <div style={{color: "blue"}}>Hello World!</div>
    }
}

Creation To create a new code component, head to the Components panel in the left menu bar and click select New Component. Then, select from Code, pick a name (no spaces) and click Create and Edit.

Framer X relies on an external editor for writing code so if you have a code editor installed, it should automatically open. If you don’t, any editor will work, though we strongly suggest downloading one that supports TypeScript (for auto-complete). We recommend VSCode by Microsoft with the optional Prettier extension installed so your code is always formatted consistently. Now, when you open up the code editor, you will see the code powering the component, including "hello world" displayed in purple text.

Dragging the same component onto the canvas will make each one an instance of the original code component, no matter where you position them on the canvas. Every time you make a change to the CSS styling or text in the code editor, your saved changes will be reflected across the master and all its instances.

Canvas Interactive components like scrolling and click handlers don’t animate on the canvas to avoid distracting you from the functional aspects of layout design. But you can test your interactive components at any time by hitting the Play icon to open the Preview window.

Layout and Sizing

Every component rendered on the canvas or Preview is wrapped in a frame so they have the same layout rules as anything else on the canvas. Both the width and height are passed to the code component as props so you can use them.

import * as React from "react"; ​
 
export class Example extends React.Component {
    render() {
        return (
            <div>
                {this.props.width} x {this.props.height}
            </div>
        );
    }
}

Displaying Canvas Elements Because the code determines the contents of code components, you cannot directly edit code component contents on the canvas. But often you'd like a code component to display something else from your canvas. For example, a Card component could render an image with some overlay that is somewhere else on your canvas. You can accomplish this in two ways.

Using props.children

React props are basically the attributes for a component to display, and one of those is a list of children, or it's contents (like in the DOM or you see in the layer panel). Normally these are determined from your code, but in Framer you can set any Frame on your canvas as children for your component. Let's look at an example.

import * as React from "react"; ​
interface Props {
    width: number;
    height: number;
}
 
export class Example extends React.Component<Props> {
    render() {
        return (
            <div style={{width: this.props.widthheight: this.props.height}}>
                <h1>Hello</h1>
                {this.props.children}
            </div>
        );
    }
}

Framer detects you are using the props.children property in your render method and automatically adds a connector to each instance of the component on your canvas (a purple dot on the right side, like the scroll tool). You can drag a connection from this connector to any Frame on the canvas and it will use it as its children to render.

Using canvas imports

You can easily import and use any named design component. The example below assumes you have a design component named Row.

import * as React from "react";
import { Row } from "./canvas"; ​
 
export class Test extends React.Component {
    render() {
        return <Row title="Koen"/>;
    }
}

Custom Properties Code components become exponentially more powerful when they use propertyControls, which allows you to customize the user interface of your component, directly within our properties panel.

The only thing you have to do is add a static propertyControls method to your class with a descriptor. It will use defaultProps for the defaults and try to type check your descriptors if you added type annotations for your props.

import * as React from "react";
import { PropertyControlsControlType } from "framer";
 
interface Props { text: string; }
 
export class Example extends React.Component<props> {
 
    static defaultProps = { text: "Hello World!"};
    static propertyControls: PropertyControls = {
        text: { type: ControlType.Stringtitle: "Text" },
    };
 
    render() {
        return <div>{this.props.text}</div>;
    }
}

Available Controls

Controls can be described by specifying one of the following types.

Boolean Number String Color Image File Enum SegmentedEnum FusedNumber Boolean Control Booleans use a segmented control. The segment titles are True and False by default but these can be overridden using the enabledTitle and disabledTitle.

interface BooleanControlDescription {
    type: ControlType.Boolean
    disabledTitle?: string
    enabledTitle?: string
}

Number Control Number controls are displayed using an input field and a slider. The min and max values can be specified to constraint the output. The default step size is 1. When a step size smaller then 1 is entered, the output will be floats. When the unit type is set to %, the input field will display 10 as 10%.

interface NumberControlDescription {
    type: ControlType.Number
    max?: number
    min?: number
    step?: number
    unit?: string
}

String Control String controls are displayed using a single line input field. A placeholder value can be set when needed.

interface StringControlDescription {
    type: ControlType.String
    placeholder?: string
}

Color Control Color controls are displayed using a color picker popover and a number input for the alpha.

interface ColorControlDescription {
    type: ControlType.Color
}

Image Control Image controls are displayed using an image picker that shows a small preview. The component receives an absolute URL during rendering.

interface ColorControlDescription {
    type: ControlType.Image
}

File Control File controls are displayed using a file picker that shows the file name after selecting a file. The component receives an absolute URL during rendering. The allowedFileTypes is an array containing all allowed file types, like so: ["json", "obj", "collada"].

interface ColorControlDescription {
    type: ControlType.File
    allowedFileTypes: string[]
}

Enum Control An enum control displays a pop-up button with a fixed set of string values. The optionTitles can be set to have nicely formatted values for in the UI.

interface EnumControlDescription {
    type: ControlType.Enum
    options: string[]
    optionTitles?: string[]
}

Segmented Enum Control A segmented enum control is displayed using a segmented control. Since a segmented control has limited space this only works for a tiny set of string values.

interface SegmentedEnumControlDescription {
    type: ControlType.SegmentedEnum
    options: string[]
    optionTitles?: string[]
}

Fused Number Control The fused number control is specifically created for border-radius, border-width, and padding. It allows setting a numeric value by either using a single input or by using four seperate number inputs. The user can switch from a 1 input to 4 by toggling a boolean.

interface FusedNumberControlDescription {
    type: ControlType.FusedNumber
    splitKey: string
    splitLabels: [stringstring]
    valueKeys: [stringstringstringstring]
    valueLabels: [stringstringstringstring]
    min?: number
}

Hiding Controls Controls can be hidden by implementing the hidden function on the property description. The function receives an object containing the set properties and returns a boolean. In the following example we hide the the inCall boolean control when the connected property is false.

interface Props {
    connected: boolean
    inCall: boolean
}
    ​
export class NetworkComponent extends React.Component<Props> {
    static defaultProps: Props = {
            connected: true,
            inCall: false,
    }
    ​
    static propertyControls: PropertyControls<Props> = {
        connected: { type: ControlType.Boolean },
        inCall: {
            type: ControlType.Boolean,
            hidden(props) {
                    return props.connected === false
            },
        },
    }
}