Um só conjunto de ícones para todos os frameworks
Todos os pacotes recebem as mesmas props (size, color, weight, corners, variant, animate, modifier, morphTo e as demais) e renderizam o mesmo SVG. Escolha o seu framework ou siga uma receita para o seu meta framework.
Pacotes
Tudo vem no pacote glyphfox (o Angular também tem o glyphfox-angular). Cada framework é uma peer dependency opcional, usada só quando você importa o ponto de entrada dele. Os componentes de ícone têm tree shaking e todos os pontos de entrada são tipados.
| Framework | Importação | Renderiza |
|---|---|---|
| React | glyphfox/react | Componentes de cliente (marcados com 'use client'), forwardRef |
| React Server Components | glyphfox/react/server | Icon e Fusion sem hooks, zero JavaScript |
| Vue 3 | glyphfox/vue | Componentes e useMorph |
| Svelte 5 | glyphfox/svelte | Arquivos-fonte .svelte e morphStore |
| Angular | glyphfox-angular | Componente standalone e provider de registro |
| Solid | glyphfox/solid | Componentes e useMorph, no servidor e no cliente |
| Preact | glyphfox/preact | Componentes e hooks, sem camada compat |
| Qwik | glyphfox/qwik | Componentes leves que retomam a execução sem JavaScript |
| Lit | glyphfox/lit | Elementos Lit (<gf-file>, <gf-glyph>) |
| Astro | glyphfox/astro | Componentes .astro, SVG estático |
| React Native | glyphfox/native | Componentes react-native-svg |
| Ember | glyphfox/ember | Helpers para .gjs, .gts e templates clássicos |
| Componente web | glyphfox/web | <glyph-fox>, também via CDN |
| Tailwind CSS | glyphfox/tailwind | Classes de máscara CSS |
Solid
import { createSignal } from 'solid-js';
import { HomeIcon, HeartIcon, Fusion, MorphIcon } from 'glyphfox/solid';
export function Toolbar() {
const [open, setOpen] = createSignal(false);
return (
<nav>
<HomeIcon size={20} class="nav-icon" />
<HeartIcon animate="pop" trigger="click" variant="duotone" />
<Fusion icons={['cloud', 'lock']} layout="overlap" />
<button onClick={() => setOpen(!open())}>
<MorphIcon name={open() ? 'x' : 'menu'} />
</button>
</nav>
);
}Sem configurar compilador de JSX e sem condição de export especial: o mesmo módulo renderiza no SolidStart, no servidor e no navegador. class, style, ref e eventos passam direto para o svg. useMorph(accessor) devolve um accessor de dados de ícone que se transformam sempre que o nome muda.
Preact
import { useState } from 'preact/hooks';
import { FileIcon, HeartIcon, MorphIcon } from 'glyphfox/preact';
export function App() {
const [copied, setCopied] = useState(false);
return (
<>
<FileIcon size={20} weight={1.5} modifier="check" class="doc" />
<HeartIcon animate="pop" trigger="click" />
<MorphIcon name={copied ? 'check' : 'copy'} onClick={() => setCopied(true)} />
</>
);
}A mesma API do React (Icon, Fusion, MorphIcon, useMorph), construída sobre preact e preact/hooks, então não puxa o preact/compat. No Preact 11, um ref chega ao elemento svg. Tanto class quanto className funcionam.
Qwik
import { component$, useSignal } from '@qwik.dev/core';
import { iconX } from 'glyphfox';
import { BellIcon, HomeIcon, MenuIcon, registerIcons } from 'glyphfox/qwik';
registerIcons([iconX]); // names used only by morphTo, Icon or Fusion
export default component$(() => {
const open = useSignal(false);
return (
<header>
<HomeIcon size={20} class="logo" />
<BellIcon animate="shake" trigger="hover" />
<button onClick$={() => (open.value = !open.value)}>
<MenuIcon morphTo="x" trigger="state" active={open.value} />
</button>
</header>
);
});Feito para o Qwik 2 (@qwik.dev/core). Os ícones são componentes leves: renderizam no servidor e retomam a execução sem baixar nada. Os estados vivos e o morphTo rodam em CSS, active alterna o trigger="state" e trigger="click" usa um pequeno handler inline. Nomes usados por Icon, morphTo e Fusion precisam ser registrados: os componentes de ícone registram o próprio ícone, e registerIcons([iconX]) (ou registerIcons(icons) com icons de glyphfox para o conjunto inteiro) cobre os nomes que você só escreve como strings.
Lit
import { LitElement, html } from 'lit';
import { defineIcons, FileIcon, HeartIcon, Icon, Fusion, MorphIcon } from 'glyphfox/lit';
// <gf-file>, <gf-heart>, <gf-glyph>, <gf-fusion> and <gf-morph>
defineIcons([FileIcon, HeartIcon, Icon, Fusion, MorphIcon]);
class AppBar extends LitElement {
static properties = { open: { type: Boolean } };
render() {
return html`
<gf-file size="20" weight="1.5" modifier="check"></gf-file>
<gf-heart animate="pop" trigger="click" secondary-color="#ff7a1a"></gf-heart>
<gf-glyph name="cloud&lock:overlap"></gf-glyph>
<gf-morph .name=${this.open ? 'x' : 'menu'} @click=${() => (this.open = !this.open)}></gf-morph>
`;
}
}
customElements.define('app-bar', AppBar);Nada é registrado na importação: defineIcons(list, { prefix }) define os elementos que você usa ({ prefix: 'my' } gera <my-file>). Os atributos são em kebab-case (secondary-color, flip-x, morph-to) e as propriedades em camelCase; o atributo animate é a propriedade animatePreset, porque animate() é um método de todo elemento, e animation toca a animação desenhada, como em todos os pacotes. class e style estilizam o elemento host. Os elementos renderizam em shadow DOM e funcionam com @lit-labs/ssr.
Astro
---
import { HomeIcon, BellIcon, Icon, Fusion } from 'glyphfox/astro';
import SearchIcon from 'glyphfox/astro/icons/search';
---
<nav>
<HomeIcon size={20} class:list={['nav-icon', { active: true }]} />
<SearchIcon weight={1.5} />
<BellIcon animate="shake" trigger="hover" />
<Icon name="file+check@tr" variant="duotone" />
<Fusion icons={['cloud', 'lock']} layout="overlap" />
</nav>Os componentes renderizam SVG estático no servidor e não enviam JavaScript. Todos os ícones do conjunto ficam disponíveis para os nomes de Icon, para morphTo e para Fusion. class (e class:list), style como string ou objeto e qualquer outro atributo passam direto para o svg. Os gatilhos hover, mount e state rodam em CSS; trigger="click" usa um pequeno handler inline.
React Native
npm install glyphfox react-native-svg
import { HomeIcon, BellIcon, HeartIcon, MorphIcon } from 'glyphfox/native';
export function Tabs({ open, unread }) {
return (
<View style={{ flexDirection: 'row', gap: 16 }}>
<HomeIcon size={28} color="#ff7a1a" />
<BellIcon animate="shake" trigger="state" active={unread > 0} />
<HeartIcon animate="pop" trigger="click" variant="duotone" />
<MorphIcon name={open ? 'x' : 'menu'} style={{ marginLeft: 'auto' }} />
</View>
);
}Os componentes renderizam elementos react-native-svg com as mesmas props. Não existe CSS no nativo, então os estados vivos são amostrados quadro a quadro a partir das mesmas animações e os morphs são interpolados; os dois respeitam a configuração de movimento reduzido. trigger="click" toca ao pressionar e trigger="hover" enquanto o ícone está pressionado. title define o rótulo de acessibilidade, style e as outras props chegam ao Svg, e os refs são repassados. O Metro resolve o export glyphfox/native com package exports, ativado por padrão desde o React Native 0.79.
Ember
import { FileIcon, BellIcon, Glyph, Fusion } from 'glyphfox/ember';
<template>
{{FileIcon size=20 weight=1.5 class="toolbar-icon"}}
{{BellIcon animate="shake" trigger="hover"}}
{{Glyph "file+check@tr" variant="duotone"}}
{{Fusion "cloud" "lock" layout="overlap"}}
</template>Helpers de função simples (Ember 4.5 ou mais recente), então não precisam de configuração de addon e funcionam em .gjs, .gts e templates clássicos. Eles devolvem markup confiável: as props compartilhadas, class, style e outros atributos são argumentos nomeados. Nomes usados por Glyph, morphTo e Fusion precisam ser registrados: os helpers de ícone registram o próprio ícone, e registerIcons([iconCloud]) (ou registerIcons(icons)) cobre o resto. Os gatilhos hover, mount e state rodam em CSS; trigger="click" usa um pequeno handler inline.