English 中文(简体)
2. 向Svelte电器进口特殊产品
原标题:Best way to import SVG icons into a Svelte app

我有大约80种习俗,即Im 进口到Svelte前端口服。 在上,它安装了滚动装置,包括打字机、Tailwind和所有现代货物。

“entergraph

两难是,如何在 app中添加ons。 缩略语为特殊群体,短文为XML短文,不超过2kB。

Option 1: as image assets

  1. Upload all the icons as foo.svg into public/assets/icons.
  2. Create a svelte component <Icon type="foo /> that displays an the icon using <img src="foo.svg>.

这种做法意味着这些术语不属于守则的一部分。

Benefits:根据需求,可通过先令代码对信标进行动态装饰。 无需将所有电线打入配方。

<>Cons: 如果有许多新信标,页面负荷就会放缓,浏览器必须排出几十个1kB文档。 用该笔照相作为全局,意味着我们需要用人工方式告诉它,以便事先打上ons。

Option 2: as part of the app build

  1. Use something like https://github.com/cristovao-trevisan/svelte-icon or https://github.com/codefeathers/rollup-plugin-svelte-svg to directly import each icon into code: import Home from ./icons/home.svg ;
  2. Create a svelte component that selects the right imported component or SVG string and displays it.

在此,这些信标被捆绑,作为随附本身的案文。

Benefits: Icons are delivered as part of the app bundle. Caching is unnecessary. Possible to dynamically modify some of the icon code e.g. colors, viewBox, etc on load.

<>Cons: 没有必要把所有缩略语都包含在 app中,以便把时间缩短到头部。 不能不增加复杂性。 放慢速度,因为 Java文法首先需要将体格变成特殊群体,而不是仅仅装上形象。

Questions

  • It seems that building icons in tthe app is a better way from this analysis, but have I missed something?
  • Does the calculus change if the "icons" are detailed images that are 50-100kB instead of the tiny strings here?
问题回答

以下做法具有这些优势:

  • One central point to maintain all your icons for your app
  • Reduced network requests for fetching SVG icons
  • Reusable icons throughout the app without having duplicate svg elements

拥有一个专门的Icon.svelte构成部分,如:

<script>
  export let name;
  export let width = "1rem";
  export let height = "1rem";
  export let focusable = false;
  let icons = [
    {
      box: 24,
      name: "save",
      svg: `<g stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M19 21H5a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h11l5 5v11a2 2 0 0 1-2 2z"/><path d="M17 21v-8H7v8"/><path d="M7 3v5h8"/></g>`
    },
    {
      box: 32,
      name: "trash",
      svg: `<path d="M12 12h2v12h-2z" /><path d="M18 12h2v12h-2z" /><path d="M4 6v2h2v20a2 2 0 0 0 2 2h16a2 2 0 0 0 2-2V8h2V6zm4 22V8h16v20z" /><path d="M12 2h8v2h-8z" />`
    }
  ];
  let displayIcon = icons.find((e) => e.name === name);
</script>
<svg
  class={$$props.class}
  {focusable}
  {width}
  {height}
  viewBox="0 0 {displayIcon.box} {displayIcon.box}">
    { @html displayIcon.svg }
</svg>

<script lang="ts">
    export let name: keyof typeof icons;
    export let width =  1rem ;
    export let height =  1rem ;
    export let focusable: string | number | null | undefined = undefined;
    let icons = {
        delete: {
            box: 32,
            svg: `<path d="M 15 4 C 14.476563 4 13.941406 4.183594 13.5625 4.5625 C 13.183594 4.941406 13 5.476563 13 6 L 13 7 L 7 7 L 7 9 L 8 9 L 8 25 C 8 26.644531 9.355469 28 11 28 L 23 28 C 24.644531 28 26 26.644531 26 25 L 26 9 L 27 9 L 27 7 L 21 7 L 21 6 C 21 5.476563 20.816406 4.941406 20.4375 4.5625 C 20.058594 4.183594 19.523438 4 19 4 Z M 15 6 L 19 6 L 19 7 L 15 7 Z M 10 9 L 24 9 L 24 25 C 24 25.554688 23.554688 26 23 26 L 11 26 C 10.445313 26 10 25.554688 10 25 Z M 12 12 L 12 23 L 14 23 L 14 12 Z M 16 12 L 16 23 L 18 23 L 18 12 Z M 20 12 L 20 23 L 22 23 L 22 12 Z"></path>`
        }
    } as const;
    let displayIcon = icons[name];
</script>

<svg
    class={$$props.class}
    {focusable}
    {width}
    {height}
    viewBox="0 0 {displayIcon.box} {displayIcon.box}">{@html displayIcon.svg}</svg
>

那么,你可以这样使用:

<Icon name="trash" class="this-is-optional" />

你只能将档案延伸到<代码>。

another way is to use a symbol defs file (ex: icons.svg) in your public folder. then in your code do something like this :

Icon.svelte

<script>
    export let name;
    export let width = "1.5rem";
    export let height = "1.5rem";
    export let focusable = false;
</script>

<svg class={$$props.class} {focusable} {width} {height}>
    <use href={`/icons.svg#${name}`} />
</svg>

icons.svg

<svg aria-hidden="true" style="position: absolute; width: 0; height: 0; overflow: hidden;" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
    <defs>
        <symbol id="icon-warning" viewBox="0 0 20 20">
            <path d="M19.511 17.98l-8.907-16.632c-0.124-0.215-0.354-0.348-0.604-0.348s-0.481 0.133-0.604 0.348l-8.906 16.632c-0.121 0.211-0.119 0.471 0.005 0.68 0.125 0.211 0.352 0.34 0.598 0.34h17.814c0.245 0 0.474-0.129 0.598-0.34 0.124-0.209 0.126-0.469 0.006-0.68zM11 17h-2v-2h2v2zM11 13.5h-2v-6.5h2v6.5z">
            </path>
        </symbol>
    </defs>
</svg>

App.svelte

<Icon name="icon-warning" />

this way you use one http call to load svg file. and then just use the part you need in markup.

Using like {@html SVG_CODE} for rendering a svg code from another component or variable is a Bad choice . This sometimes gives risk of XSS attack . Specially when the image comes from external source. check : https://github.com/sveltejs/svelte/issues/2545

Svelte don t 履行在{@html ......} 之后插入管理局的表述。 换言之,如果你利用这一特点,你就必须从你不信任的来源中人工逃避超文本,否则,你会冒风险使用户受到XSS攻击。

我想使用以下简称:rollup-plugin-svelte-svg。 更好的选择

1.Install using npm

npm i -D rollup-plugin-svelte-svg

2.Simply call svelteSVG before svelte in your rollup config.


export default {
    
    plugins: [
        svelteSVG({
            // optional SVGO options
            // pass empty object to enable defaults
            svgo: {}
        }),
    ],
    ...
}

3.You can then import svg in your JS thusly:

<script>
    import Logo from "./logo.svg";
</script>

<Logo width=20 />

Or

Open your svg image using text editor, copy all the code and paste in a file name with .svelte extension .

for example , icon.svg file contains :

<svg class="w-6 h-6" fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path fill-rule="evenodd" d="M14.243 5.757a6 6 0 10-.986 9.284 1 1 0 111.087 1.678A8 8 0 1118 10a3 3 0 01-4.8 2.401A4 4 0 1114 10a1 1 0 102 0c0-1.537-.586-3.07-1.757-4.243zM12 10a2 2 0 10-4 0 2 2 0 004 0z" clip-rule="evenodd"></path></svg>

Copy it in a icon.svelte file

<script></script>
<style></style>
<svg class="w-6 h-6" fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path fill-rule="evenodd" d="M14.243 5.757a6 6 0 10-.986 9.284 1 1 0 111.087 1.678A8 8 0 1118 10a3 3 0 01-4.8 2.401A4 4 0 1114 10a1 1 0 102 0c0-1.537-.586-3.07-1.757-4.243zM12 10a2 2 0 10-4 0 2 2 0 004 0z" clip-rule="evenodd"></path></svg>

When you want use icon.svelte component

<script>
import Icon from "$lib/icon.svelte"
</script>
<style></style>
<Icon />

If you want you can pass optional class

然后,icon.svelte

<script></script>
<style></style>
<svg class="{$$props.class}" fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path fill-rule="evenodd" d="M14.243 5.757a6 6 0 10-.986 9.284 1 1 0 111.087 1.678A8 8 0 1118 10a3 3 0 01-4.8 2.401A4 4 0 1114 10a1 1 0 102 0c0-1.537-.586-3.07-1.757-4.243zM12 10a2 2 0 10-4 0 2 2 0 004 0z" clip-rule="evenodd"></path></svg>

When you want to call icon.svelte component

<script>
import Icon from "$lib/icon.svelte"
</script>
<style></style>
<Icon class="h-6 w-6" />

一种工作解决办法是将特别志愿人员安排在一个单独的Iconservice。 j)

export const chevron_down = "<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-chevron-down"><polyline points="6 9 12 15 18 9"></polyline></svg>";

export const chevron_right = "<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-chevron-right"><polyline points="9 18 15 12 9 6"></polyline></svg>";

这可以很容易地进口,并在Svelte @html功能中使用。

<script>
    import {chevron_down, chevron_right} from  IconService ;
</script>

{@html chevron_down}

A Svelte Component with SVG Icons inside:

<script>
  export let i
  export let stroke = 3
</script>

<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" 
  stroke-width={stroke} stroke="currentColor" class={`w-6 h-6 ${$$props.class}`}>
  
  {#if i ==  search }
  <path stroke-linecap="round" stroke-linejoin="round" d="M21 21l-5.197-5.197m0 0A7.5 7.5 0 105.196 5.196a7.5 7.5 0 0010.607 10.607z" />
  
  {:else if i ==  plus }
  <path stroke-linecap="round" stroke-linejoin="round" d="M12 4.5v15m7.5-7.5h-15" />

  {:else}
  <path stroke-linecap="round" stroke-linejoin="round" d="M18.364 18.364A9 9 0 005.636 5.636m12.728 12.728A9 9 0 015.636 5.636m12.728 12.728L5.636 5.636" />
  {/if}
</svg>

Use like this:

<Icon i= search />
<Icon i= plus  stroke={5} class="w-10 h-10 text-slate-500"/>

Benefits

所有ic都用单一文档收集。 SVG-Paths是作为超文本处理而不是作为线体汇编的。 这还显示,社会、文化权利委员会在社会、文化权利委员会中存在任何错误。 当你增加一个新的Icon时,你才不得不将特别安全小组的内容抄录到这个档案中。

Programmatically loading the svg as string from one module (iconsProvider.js) which is exporting all svgs as constants. So basically, with every new svg, you only need to export it from iconprovider.js. And then pass <>strong>icon.svelte the right iconName prop.

<>strong>icon.svelte

<script lang="ts">
import * as iconsProvider from "../lib/iconsProvider"

export let iconName: string
</script>
{@html iconsProvider[ iconName ]}

iconsProvider.js

export const icon1 = `<svg ...>`
export const icon2 = `<svg ...>`

希望这一帮助。





相关问题
selected text in iframe

How to get a selected text inside a iframe. I my page i m having a iframe which is editable true. So how can i get the selected text in that iframe.

How to fire event handlers on the link using javascript

I would like to click a link in my page using javascript. I would like to Fire event handlers on the link without navigating. How can this be done? This has to work both in firefox and Internet ...

How to Add script codes before the </body> tag ASP.NET

Heres the problem, In Masterpage, the google analytics code were pasted before the end of body tag. In ASPX page, I need to generate a script (google addItem tracker) using codebehind ClientScript ...

Clipboard access using Javascript - sans Flash?

Is there a reliable way to access the client machine s clipboard using Javascript? I continue to run into permissions issues when attempting to do this. How does Google Docs do this? Do they use ...

javascript debugging question

I have a large javascript which I didn t write but I need to use it and I m slowely going trough it trying to figure out what does it do and how, I m using alert to print out what it does but now I ...

Parsing date like twitter

I ve made a little forum and I want parse the date on newest posts like twitter, you know "posted 40 minutes ago ","posted 1 hour ago"... What s the best way ? Thanx.

热门标签