Configuration

Learn how to correctly configure your React Native or Expo project.


After installing @design-blocks/native from the installation section, proceed to create the blocks.config.ts file at the root of your project. This will centralize your entire design system, ensuring a better development experience.

Quick Start

To use the createBlocks and createTokens utilities, import them into the blocks.config.ts file as follows:

ts
// blocks.config.ts
import { createBlocks, createTokens } from "@design-blocks/native";
 
export const lightTheme = {
  tokens: {
    colors: {
      blue: {
        950: "#0000ff",
      },
      red: {
        950: "#ff0000",
      },
      green: {
        950: "#00ff00",
      },
    },
  },
} as const;
 
const [themeTokens] = createTokens({ theme: lightTheme });
 
export const { block, css, themes } = createBlocks({
  themes: { light: themeTokens },
});

If working with React Native CLI or Expo, locate your entry point file, usually App.tsx or App.js, and add the following code:

tsx
// App.tsx o App.js
 
import React from "react";
import { ThemeProvider } from "@design-blocks/native";
 
import Screen from "./Screen";
import { themes } from "./blocks.config";
 
const App = () => {
  return (
    <ThemeProvider theme={themes.light}>
      <Screen />
    </ThemeProvider>
  );
};
 
export default App;

This should suffice to use the design system in your project. For instance, the Screen.tsx file should look something like this:

tsx
// Screen.tsx
import {View, Text} from 'react-native';
 
import { block, css } from "[path-to]/blocks.config";
 
const TitleBlock = block.Text(({ theme }) => ({
  color: theme.colors.blue[950],
  fontSize: theme.fontSizes.['10xl'],
}));
 
function Screen() {
  return(
    <View>
       <TitleBlock>
        Hello World
      </TitleBlock>
 
      <Text
        style={css`
          font-Weight: '700';
        `}
      >
        Other Text
      </Text>
    </View>
  );
}
 
export default Screen;

To learn more about the block function, visit the block section, and for the css function, visit the css section.

Tokens

Following the previous example, we will define a theme with its tokens in the blocks.config.ts file. Keep in mind that the keys used here can be customized to your liking.

The tokens section is where you define colors, radii, fontSizes, fontWeights, spacings, sizes, and borders. The theme section is where you define the tokens to be used in the theme.

ts
// blocks.config.ts
import { createBlocks, createTokens } from "@design-blocks/native";
 
export const lightTheme = {
  tokens: {
    colors: {
      blue: {
        950: "#0000ff",
      },
      red: {
        950: "#ff0000",
      },
      green: {
        950: "#00ff00",
      },
      yellow: {
        950: "#ffff00",
      },
    },
  },
  extendTokens: {
    radii: {
      "6xl": 32,
    },
    spacings: {
      "7xl": 90,
    },
    sizes: {
      "21xl": 188,
    },
    borders: {
      "5xl": 32,
    },
    fontSizes: {
      "10xl": 64,
    },
    fontsWeight: {
      black2: "900",
    },
  },
} as const;
 
const [lightThemeTokens] = createTokens({ theme: lightTheme });

Override Tokens

To overwrite the default tokens that come with the design system, just add them in the tokens section as follows:

ts
// blocks.config.ts
import { createBlocks, createTokens } from "@design-blocks/native";
 
export const lightTheme = {
  tokens: {
    colors: {
      ...
    },
    radii: {
      none: 0,
      sm: 1,
      base: 2,
      true: 2,
      md: 4,
      lg: 6,
      xl: 8,
      '2xl': 16,
      '3xl': 20,
      '4xl': 24,
      '5xl': 28,
      full: 9999,
    },
    spacings: {
      none: 0,
      xxs: 4,
      xs: 8,
      sm: 12,
      md: 16,
      lg: 24,
      xl: 32,
      '2xl': 40,
      '3xl': 48,
      '4xl': 56,
      '5xl': 64,
      '6xl': 72,
      full: '100%',
      baseSpacing: 4,
    },
    sizes: {
      none: 0,
      xxs: 4,
      xs: 8,
      sm: 12,
      md: 16,
      lg: 24,
      xl: 32,
      '2xl': 40,
      '3xl': 48,
      true: 48,
      '4xl': 56,
      '5xl': 64,
      '6xl': 72,
      '7xl': 80,
      '8xl': 88,
      '9xl': 96,
      '10xl': 104,
      '11xl': 112,
      '12xl': 120,
      '13xl': 128,
      '14xl': 136,
      '15xl': 144,
      '16xl': 152,
      '17xl': 160,
      '18xl': 168,
      '19xl': 176,
      '20xl': 184,
      full: '100%',
    },
    borders: {
      none: 0,
      true: 4,
      sm: 2,
      md: 6,
      lg: 8,
      xl: 12,
      '2xl': 16,
      '3xl': 20,
      '4xl': 24,
      '5xl': 28,
    },
    fontSizes: {
      xs: 9,
      sm: 10,
      md: 12,
      lg: 14,
      xl: 16,
      '2xl': 18,
      '3xl': 24,
      '4xl': 32,
      '5xl': 40,
      '6xl': 48,
      '7xl': 56,
      '8xl': 64,
      '9xl': 72,
    },
    fontsWeight: {
      hairline: '100',
      thin: '200',
      light: '300',
      normal: '400',
      medium: '500',
      semibold: '600',
      bold: '700',
      extrabold: '800',
      black: '900',
    },
  },
} as const;
 
const [lightThemeTokens] = createTokens({ theme: lightTheme });

This will override the default tokens provided by the design system.

Typescript

For TypeScript autocomplete to work correctly, manual changes are required. For example, you can create a block.d.ts file.

The @design-blocks/native package contains useful types to make this easier, including Leaves, LooseAutocomplete.

ts
import "@design-blocks/native";
 
import * as RN from "react-native";
 
import { lightTheme } from "./blocks.config";
 
import type { Leaves, LooseAutocomplete } from "@design-blocks/native";
 
type AppTheme = typeof lightTheme.tokens;
 
type ColorsAppTheme = AppTheme["colors"];
type SpacingsCustom = AppTheme["spacings"];
type RadiiCustom = AppTheme["radii"];
type FontSizesCustom = AppTheme["fontSizes"];
type ColorsValueMap =
  | LooseAutocomplete<Leaves<ColorsAppTheme>>
  | Omit<RN.TextStyle["color"], "string">;
 
declare module "@design-blocks/native" {
  export interface Colors extends ColorsAppTheme {}
  export interface Spacings extends SpacingsCustom {}
  export interface Radii extends RadiiCustom {}
  export interface FontSizes extends FontSizesCustom {}
 
  export interface TextColorsProps {
    color?: ColorsValueMap;
    textDecorationColor?: ColorsValueMap;
    textShadowColor?: ColorsValueMap;
    backgroundColor?: ColorsValueMap;
    bgColor?: ColorsValueMap;
    borderColor?: ColorsValueMap;
    borderTopColor?: ColorsValueMap;
    borderRightColor?: ColorsValueMap;
    borderEndColor?: ColorsValueMap;
    borderBottomColor?: ColorsValueMap;
    borderLeftColor?: ColorsValueMap;
    borderStartColor?: ColorsValueMap;
    borderBlockColor?: ColorsValueMap;
    borderBlockEndColor?: ColorsValueMap;
    borderBlockStartColor?: ColorsValueMap;
  }
 
  export interface BoxColorsProps {
    backgroundColor?: ColorsValueMap;
    bgColor?: ColorsValueMap;
    borderColor?: ColorsValueMap;
    borderTopColor?: ColorsValueMap;
    borderRightColor?: ColorsValueMap;
    borderEndColor?: ColorsValueMap;
    borderBottomColor?: ColorsValueMap;
    borderLeftColor?: ColorsValueMap;
    borderStartColor?: ColorsValueMap;
    borderBlockColor?: ColorsValueMap;
    borderBlockEndColor?: ColorsValueMap;
    borderBlockStartColor?: ColorsValueMap;
    shadowColor?: ColorsValueMap;
  }
}

With this, you can easily access your tokens in your project, ensuring a better development experience. For example, in the following snippet, you can see how you can easily access your tokens.

tsx
import { ScrollView, Image } from "react-native";
 
import { block } from "[path-to]/blocks.config";
 
const ScrollViewBlock = block(ScrollView)(({ theme }) => ({
  backgroundColor: theme.colors.blue[950],
  height: "100%",
}));
 
const AvatarBlock = block(Image)(({ theme }) => ({
  width: theme.sizes["10xl"],
  height: theme.sizes["10xl"],
  borderRadius: theme.radii["full"],
  borderWidth: theme.borders["xs"],
  borderColor: theme.colors.red[950],
}));
 
const Avatar2Block = block.Image(({ theme }) => ({
  width: theme.sizes["15xl"],
  height: theme.sizes["15xl"],
  borderRadius: theme.radii["xl"],
  borderWidth: theme.borders["sm"],
  borderColor: theme.colors.yellow[950],
}));