Using SVG (Scalable Vector Graphics) in React Native requires a bit of additional setup because React Native doesn’t support SVG out of the box. You can use SVGs in your React Native app by using a library like react-native-svg. This library provides SVG support for React Native and allows you to use SVG files or SVG code directly in your components.

Installation

Npm:

1
npm install react-native-svg

Yarn:

1
yarn add react-native-svg

Linking (for React Native versions < 0.60):

1
react-native link react-native-svg

For React Native 0.60 and above, auto linking should take care of this.

Using SVGs in Your App

There are two main ways to use SVGs with react-native-svg:

A. Using Inline SVG Code

Just write the SVG code as other components does. Here’s an example:

1
2
3
4
5
6
7
8
9
10
11
import React from 'react';
import { Svg, Circle, Rect } from 'react-native-svg';

const MyInlineSvgComponent = () => {
return (
<Svg height="100" width="100">
<Circle cx="50" cy="50" r="30" fill="pink" />
<Rect x="15" y="15" width="70" height="70" stroke="blue" strokeWidth="2" fill="green" />
</Svg>
);
};

In this example, Svg, Circle, and Rect are components provided by react-native-svg that correspond to their SVG equivalents.

B. Using SVG Files

If you have SVG files and want to use them directly in your components, you need a loader called react-native-svg-transformer to import them as React components.

Step 1: Install library

using npm:

1
npm install --save-dev react-native-svg-transformer

or yarn:

1
yarn add --dev react-native-svg-transformer

Step 2: Configure the react native packager

You need to configure the Metro bundler to use the transformer. Modify your metro.config.js to look like this:

For React Native v0.72.1 or newer

Merge the contents from your project’s metro.config.js file with this config (create the file if it does not exist already).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
const { getDefaultConfig, mergeConfig } = require("@react-native/metro-config");

const defaultConfig = getDefaultConfig(__dirname);
const { assetExts, sourceExts } = defaultConfig.resolver;

/**
* Metro configuration
* https://facebook.github.io/metro/docs/configuration
*
* @type {import('metro-config').MetroConfig}
*/
const config = {
transformer: {
babelTransformerPath: require.resolve("react-native-svg-transformer")
},
resolver: {
assetExts: assetExts.filter((ext) => ext !== "svg"),
sourceExts: [...sourceExts, "svg"]
}
};

module.exports = mergeConfig(defaultConfig, config);

For Expo SDK v41.0.0 or newer

Merge the contents from your project’s metro.config.js file with this config (create the file if it does not exist already).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
const { getDefaultConfig } = require("expo/metro-config");

module.exports = (() => {
const config = getDefaultConfig(__dirname);

const { transformer, resolver } = config;

config.transformer = {
...transformer,
babelTransformerPath: require.resolve("react-native-svg-transformer")
};
config.resolver = {
...resolver,
assetExts: resolver.assetExts.filter((ext) => ext !== "svg"),
sourceExts: [...resolver.sourceExts, "svg"]
};

return config;
})();

For React Native v0.59 or newer

Merge the contents from your project’s metro.config.js file with this config (create the file if it does not exist already).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
const { getDefaultConfig } = require("metro-config");

module.exports = (async () => {
const {
resolver: { sourceExts, assetExts }
} = await getDefaultConfig();
return {
transformer: {
babelTransformerPath: require.resolve("react-native-svg-transformer")
},
resolver: {
assetExts: assetExts.filter((ext) => ext !== "svg"),
sourceExts: [...sourceExts, "svg"]
}
};
})();

Using TypeScript

If you are using TypeScript, you need to add this to your declarations.d.ts file at your root dir (create one if you don’t have one already), so you will get the type hint:

1
2
3
4
5
6
declare module "*.svg" {
import React from "react";
import { SvgProps } from "react-native-svg";
const content: React.FC<SvgProps>;
export default content;
}

More custom options

Check the README in their repo

Usage

Here’s a example to use it:

1
2
3
4
5
6
7
8
9
10
11
import React from 'react';
import { View } from 'react-native';
import MySvgImage from './path-to-your-svg-file.svg';

const MyComponent = () => {
return (
<View>
<MySvgImage width={120} height={120} />
</View>
);
};

References

  1. software-mansion/react-native-svg: SVG library for React Native, React Native Web, and plain React web projects. (github.com)
  2. kristerkari/react-native-svg-transformer: Import SVG files in your React Native project the same way that you would in a Web application. (github.com)