<svg-icon>

by WebComponents

HTML

<style>
  body {
    font: 18px arial;
    color: darkgreen;
  }
  svg-icon {
    background: lightgreen;
    width: 110px;
  }
  svg-icon[is*="source"] {
    background: pink;
  }
  svg-icon::part(size){ /* show icon name and size in bytes inside shadowDOM */
    font-size: 70%;
    color: black;
  }
</style>

<svg-icon is="right-arrow-source" color="red"></svg-icon>
<svg-icon is="right-arrow"></svg-icon>
<svg-icon is="settings-source" color="red"></svg-icon>
<svg-icon is="settings"></svg-icon>

<h1>Web Component: &lt;svg-icon is="[name]"></h1>
<ul>
<li>
Define the Web Component in the &lt;head> to <b>not</b> create any FOUCs.
</il><li>
  Edit/optimize the d-path in: <a href="https://yqnn.github.io/svg-path-editor/">https://yqnn.github.io/svg-path-editor/</a>
</il><li>
Ask your AI to create a <i>refactor/compress skill</i> from the source icon to the <i>slimmed</i> icon.
</il><li>
Then copy/past new SVG icons and ask AI to convert the source to the final version.
</il><li>
  <a href="https://www.svgrepo.com/svg/523734/settings?edit=true">copy SVG per Icon from https://svgrepo.com</a>
</il><li>
Delete <i>source</i> versions when done.
</il><li>
Using <b>is</b> attribute is safe because that is a HTMLElement property by default; but only used in <i>Customized Built-In</i> Web Components, which nobody uses because Safari doesn't support those Web Components.
</ul>
<!-- WCQ - A Web Components Course -->

JavaScript

customElements.define(
  "svg-icon",
  class extends HTMLElement {
    get iconnames() {
      // optional
      return Object.keys(this.icons);
    }
    icon(is) {
      return this.icons[is] || console.error(`No icon`, is);
    }
    connectedCallback(is = this.is || this.getAttribute("is")) {
      // safe for moving around in DOM, will redraw
      (this.shadowRoot || this.attachShadow({ mode: "open" })).innerHTML =
        `<style>` +
        `:host{display:inline-block}` +
        `svg{vertical-align:top;width:100%;height:100%}` +
        `svg *{fill:${this.getAttribute("color")||"currentColor"}` +
        `</style>` +
        this.icon(is)
        + `<size-info part="size" ><br>` + is + `<br>` + this.icon(is).length + ` Bytes</size-info>`;
        this.title = is;
    }
    // WCQ challenge: add observedAttributes: "is","color"

    // main SVG data store
    get icons() {
      return {
        "right-arrow-source": `<svg viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg"><g id="SVGRepo_bgCarrier" stroke-width="0"></g><g id="SVGRepo_tracerCarrier" stroke-linecap="round" stroke-linejoin="round"></g><g id="SVGRepo_iconCarrier"> <path fill-rule="evenodd" clip-rule="evenodd" d="M12.2929 4.29289C12.6834 3.90237 13.3166 3.90237 13.7071 4.29289L20.7071 11.2929C21.0976 11.6834 21.0976 12.3166 20.7071 12.7071L13.7071 19.7071C13.3166 20.0976 12.6834 20.0976 12.2929 19.7071C11.9024 19.3166 11.9024 18.6834 12.2929 18.2929L17.5858 13H4C3.44772 13 3 12.5523 3 12C3 11.4477 3.44772 11 4 11H17.5858L12.2929 5.70711C11.9024 5.31658 11.9024 4.68342 12.2929 4.29289Z" fill="#000000"></path> </g></svg>`,

        "right-arrow": `<svg viewBox="0 0 240 240"><path d="M123 43c4-4 10-4 14 0l70 70c4 4 4 10 0 14l-70 70c-4 4-10 4-14 0s-4-10 0-14l53-53H40c-6 0-10-4-10-10s4-10 10-10H176L123 57c-4-4-4-10 0-14Z"/></svg>`,

        "settings-source": `<svg viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg"><g...