React Native

Drop PNG! How to Adopt SVG in Your React Native App

Have you already experienced heavy apps because of images? We have a solution: you can use SVG as React Native component with react-native-svg and SVGR!

What is SVG format?

First, what is the main difference between SVG format and PNG format? Let's look at the differences:

  • PNG is mainly a map of each pixel (a bitmap), with compression to get a lighter file. So the bigger the picture is, the heavier the file will be.
  • SVG is a vector image format, which is basically the plan of how to draw the image. This means that, unlike bitmap formats, the size of the file does not depend on the size of the image anymore, but on its complexity to drawn.

To put it in a nutshell:

  • PNG are nice for photos as the shapes on it are too complicated for a vectorial image
  • SVG are nice for icons as they have simple shapes. And as most of the designs in our apps are simple, we can save a lot of storage using them because they will be smaller.

Here is an example of an SVG icon representing the flag of Japan. We can see the two circles components corresponding to each circles we see on the icon.

Example of an SVG file: the flag of Japan

How can I use it?++code class="has-line-data" data-line-start="14" data-line-end="16">++/code>

There are many ways to use them in your react native app, depending on the kind of picture. If it is a monochromatic icon, you can use Icomoon/Fontello, using the SVG as a font, as explained here: Add custom icons to your React Native application. But since it's a font, we have only one color so it's easily limited. For other icons, I recommend you to use react-native-svg. Let's see a little example.++code class="has-line-data" data-line-start="14" data-line-end="16">++/code>

In our app, we want to use country flag icons. We won't use Icomoon or Fontello because we need multicolor icons. And moreover we use a lot of images (several hundred) with low complexity, so we really should use SVGs. First, let's download the flags here: https://www.flaticon.com/packs/countrys-flags. We can already see that the PNG folder is 10 times bigger than the SVG folder!++code class="has-line-data" data-line-start="14" data-line-end="16">++/code>

Then you have many ways to use these SVGs in your app. For example you can use the component ++code>SvgUri++/code> which loads the SVG and automatically converts it in a component. But I advice you to convert your SVG before, to keep a nice performance on your app. So, you can convert these SVG images to React components thanks to SVGR. To convert all the SVG files from the folder to React components, you just have to run on the command line:

++pre>++code class="has-line-data" data-line-start="14" data-line-end="16">npx @svgr/cli --native --svgo-config "{ \"plugins\": [ {\"convertPathData\": false} ] }" [-d out-dir] [src-dir] ++/code>++/pre>

We are using npx, which is an npm tool that makes it easy to use CLI tools and other executables hosted on an npm registry. So no need for any installation! We also add a SVGO config so that SVGO doesn't optimize the SVG to much: react-native-svg doesn't accept a too optimized SVG.

With our example, we get:

Screenshot 2019-08-28 at 00.02.50

Finally, to use them in your app, you need react-native-svg. If you are using Expo, it is already installed. If not, run ++code>yarn add react-native-svg++/code> then link native code with:

  • ++code>cd ios && pod install++/code> (react native 0.60+)
  • ++code>react-native link react-native-svg++/code> (before react native 0.60)

And now, you can have all the SVG components you want with your lighter and faster app!

Screenshot 2019-08-28 at 00.59.52

Développeur mobile ?

Rejoins nos équipes