# React Introduction

React Introduction — Legend State documentation.

Source: https://legend.so/state/v2/react/react-introduction/

Legend State v2 documentation. **Archived version.** [Read the current documentation.](https://legend.so/state/v3/intro/introduction/)

This is a high level overview for how to work with Legend-State in React. See [React API](https://legend.so/state/v2/react/react-api) for more specific details. Legend-State supports both React and React Native, but most of the examples are in React for ease of showing live demos.

## [Component reactivity](https://legend.so/state/v2/react/react-introduction/#component-reactivity)

The first step to working with observables in React is to make your components re-render when observable values change. Legend-State has three ways for your components to update themselves based on observables. This applies to all observables, whether in global state or local within a component.

### [enableReactTracking](https://legend.so/state/v2/react/react-introduction/#enablereacttracking)

To get started we recommend [enableReactTracking](https://legend.so/state/v2/usage/configuring#enablereacttracking) - it's the easiest way to work with observables in React. You only need to enable this once in your app's entry point.

```jsx
import { observable } from "@legendapp/state";
import { enableReactTracking } from "@legendapp/state/config/enableReactTracking";

enableReactTracking({
    auto: true,
});

const name$ = observable("Annyong");

function Component() {
  // The component re-renders when name changes
  const name = name$.get();

  return <div>{name}</div>;
}
```

We recommend using this to get started and for rapid prototyping, but it's always better to use `observer`. Under the hood, when called from a React component, it replaces `get()` with a `useSelector` hook. So keep in mind that it acts like a hook, so it is subject to the rules of hooks. So it can cause errors when used conditionally or within loops.

### [observer](https://legend.so/state/v2/react/react-introduction/#observer)

[observer](https://legend.so/state/v2/react/react-api#observer) turns the component into an [observing context](https://legend.so/state/v2/usage/reactivity#observing-contexts) so that `.get()` will trigger re-render when observable change. This is the best and most efficient way to use observables in React. Just wrap your components in `observer` to make them efficiently track all accessed observables.

Not an HOC

Although observer looks like an HOC, it actually creates a Proxy around the component, with effectively no performance cost, so it is extremely efficient.

```jsx
import { observable } from "@legendapp/state";
import { observer } from "@legendapp/state/react";

const state$ = observable({ count: 0 });

const Component = observer(function Component() {
  // Accessing state$ automatically makes this component track changes to re-render
  const count = state$.count.get();

  // Re-renders whenever count changes
  return <div>{count}</div>;
});
```

### [useSelector](https://legend.so/state/v2/react/react-introduction/#useselector)

`useSelector` returns the value of an observable or a function and updates the component when its value changes. You can use it for more complex cases to compute a value based on observables, and only re-render when its return value changes. See [useSelector](https://legend.so/state/v2/react/react-api#useselector) for more in-depth details.

```jsx
import { observable } from "@legendapp/state";
import { useSelector } from "@legendapp/state/react";

const state$ = observable({ fname: "hello", lname: "there" });

function Component() {
  // Re-render when fname changes
  const fname = useSelector(state$.fname);
  // Re-render when the computed value of fullname changes
  const fullname = useSelector(
    () => `${state$.fname.get()} ${state$.lname.get()}`
  );

  return (
    <div>
      {fname} {fullname}
    </div>
  );
}
```

## [Local state](https://legend.so/state/v2/react/react-introduction/#local-state)

In addition to using global state, you can create local state with `useObservable` to use immediately or pass down through children or context.

```jsx
import { observer, useObservable } from "@legendapp/state/react";

function App() {
  const store$ = useObservable({
    profile: { name: "hi" },
  });

  // This component does not get() the store so only Profile will re-render on changes

  return (
    <div>
      <Profile profile$={store$.profile} />
    </div>
  );
}

const Profile = observer(function Profile({ profile$ }) {
  const name = profile$.name.get();

  return <div>Name: {name}</div>;
})
```

## [Fine-grained reactivity](https://legend.so/state/v2/react/react-introduction/#fine-grained-reactivity)

A new (and fun) pattern with Legend-State is to make re-renders fine-grained so that your full components don't re-render at all - focusing updates to our tiny fine-grained components.

The most basic way to optimize renders is to have observable text or numbers render themselves, so their parent component doesn't have to.

You can take it even further with the `Reactive` components and control-flow components like `For`, `Show`, and `Switch`. Combining these we can use what we call a "render once" style - components render only the first time and state changes trigger only the tiniest possible re-renders. Especially with very large components, rendering the full component less often can give you a huge performance boost.

```jsx
import { observable } from "@legendapp/state";
import { Memo, For, Reactive, Show, Switch } from "@legendapp/state/react";

const state$ = observable({ showModal: false, page: 0, users: [] });

function MemoExample() {
  // This component itself never re-renders

  return (
    <div>
      // Reactive components have reactive props and children which re-render
      themselves on changes
      <Reactive.div
        $className={state$.showModal.get() ? "bg-blue-500" : "bg-red-500"}
      >
        {() => `Showing page: ${state$.page.get()}`}
      </Reactive.div>
      // Show re-renders itself whenever showModal changes
      <Show if={state$.showModal}>{() => <Modal />}</Show>
      // Switch re-renders itself whenever page changes
      <Switch value={state$.page}>
        {{
          0: <Page0 />,
          1: <Page1 />,
          2: <Page2 />,
        }}
      </Switch>
      // For optimizes array updates to be much faster
      <For each={state$.users} item={User} optimized />
    </div>
  );
}

function User({ item }) {
  return <Memo>{item.name}</Memo>;
}
```

These fine-grained reactivity patterns are inspired by Knockout.js as well as more modern frameworks like Solid and Svelte. They are a great way to optimize your apps, but teams who want a more canonical React experience or easy migration may want to ignore or use them sparingly to optimize specific heavy components.

[Read more](https://legend.so/state/v2/react/fine-grained-reactivity)

## [Example](https://legend.so/state/v2/react/react-introduction/#example)

This example shows:

1.  State persisted to local storage
2.  Reactive components

[View Markdown](https://legend.so/state/v2/react/react-introduction.md)[Report a documentation correction](https://github.com/LegendApp/legend-docs/issues/new?title=Docs%3A+React+Introduction&body=Page%3A+https%3A%2F%2Flegend.so%2Fstate%2Fv2%2Freact%2Freact-introduction%0A%0AWhat+is+incorrect+or+missing%3F%0A%0AExpected+behavior+or+supporting+source%3A%0A)
