how to set up an inline svg with webpack

余生长醉 提交于 2019-11-27 19:00:28

Actually Michelle's answer pointed me in the right direction, and that works nicely for loading an svg file with webpack and using it as your <img> src

However to actually get the inline svg, I needed to do the following:

Instead of file-loader use svg-inline-loader as your svg loader:

{ test: /\.svg$/, loader: 'svg-inline-loader' }

Then to load the svg inline in a component:

import React, { Component } from 'react'
import logo from "./logo.svg";

class Header extends Component {

  render() {
    return (
        <div className='header'>
          <span dangerouslySetInnerHTML={{__html: logo}} />
        </div>
    );
  }
};

export default Header

It looks like there is an inline svg wrapper for react svg-inline-react which would be another option instead of the <div dangerouslySetInnerHTML={{__html: mySvg}} />

Old question, but I didn't see this solution anywhere so I decided to post it, hoping it will help someone.

If you want to be able to style those SVG icons, you might want to load them with the raw loader:

webpack.config.js:

 { 
      test: /\.svg$/, 
      loader: 'raw-loader' 
 } 

The import in my view:

import closeIcon from 'svg/ic_close_black_24px.svg'; 

The template (Mustache uses 3 brackets to insert the SVG data (URL)unencoded):

<button id="closeModal">
  {{{closeIcon}}}
</button>

this way the SVG data will be inserted instead of the brackets and look like this:

<button id="closeModal">
  <svg fill="#000000" height="24" viewBox="0 0 24 24" width="24" xmlns="http://www.w3.org/2000/svg">
    <path d="M19 6.41L17.59 5 12 10.59 6.41 5 5 6.41 10.59 12 5 17.59 6.41 19 12 13.41 17.59 19 19 17.59 13.41 12z"></path>
    <path d="M0 0h24v24H0z" fill="none"></path>
  </svg>
</button>

I'm using Backbone with Mustache template engine with Webpack 2.5.1

I hope my late answer will still be useful for someone, because I don't like any of abovementioned options.

The react-svg-loader webpack loader allows you to import SVG icons like JSX components:

import Logo from './logo.svg';

class App extends Component {
  render() {
    return (
      <div className="App">
          <Logo fill="red" className="logo" width={50} height={50} />
      </div>
    );
  }
}

and minimum config looks like this:

{
  test: /\.svg$/,
  use: [
    {
      loader: "babel-loader"
    },
    {
      loader: "react-svg-loader",
      options: {
        jsx: true // true outputs JSX tags
      }
    }
  ]
}

The best part is that it just outputs the svg file contents, without any extra wrappers and dangerouslySetInnerHTML in your code.

Michelle Tilley

If I'm not mistaken, since you're using the file loader, you can utilize it in much the same way as any other require. Webpack will turn require("./logo.svg") into a path to a file, which it will emit when it bundles.

import React, { Component } from 'react'

import mySvg from './logo.svg'

class Header extends Component {

  render() {
    return (
        <div className='header'>
            <img src={mySvg} />
        </div>
    );
  }
};

export default Header

Similar to another answer using React, there is also a handy Vue plugin as well.

vue-svg-loader just throw it in your configuration and start using. The nice thing is it will also run your svg through SVGO to optimize it.

Configuration

{
    test: /\.svg$/,
  loader: 'vue-svg-loader', // `vue-svg` for webpack 1.x
  options: {
    // optional [svgo](https://github.com/svg/svgo) options
    svgo: {
      plugins: [
        {removeDoctype: true},
        {removeComments: true}
      ]
    }
  }
}

Usage

<template>
  <nav id="menu">
    <a href="...">
      <SomeIcon class="icon" />
      Some page
    </a>
  </nav>
</template>

<script>
import SomeIcon from './assets/some-icon.svg';

export default {
  name: 'menu',
  components: {
    SomeIcon,
  },
};
</script>

Here is a simple non-react solution.

  1. Install Svg inline loader
  2. In webpack.config.js add { test: /\.svg$/, loader: 'svg-inline-loader' }
  3. In your js file import svg image and add it to a DOM element like so
  import Svg from './svg.svg';

  function component() {
    const element = document.createElement('div');

    element.innerHTML = Svg;

    return element;
  }

  document.body.appendChild(component());
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!