npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@tdm-design/icons

v0.0.21

Published

TDM Design Icon Library - React icon components with tree-shaking support

Readme

Icon Generator

A Node.js script to automatically generate React TypeScript icon components from SVG files.

Overview

This tool reads SVG files from the svg/ directory and generates corresponding TSX React components in the icons/ directory. Each generated component follows a consistent pattern, making it easy to use and maintain icons across your project.

Directory Structure

icon/
├── svg/                    # Source SVG files
│   ├── filled/            # Filled style icons
│   ├── outlined/          # Outlined style icons
│   ├── color/             # Color icons
│   └── *.svg              # Other icons
├── icons/                  # Generated TSX components (output)
├── components/
│   └── TdmIcon.tsx        # Base icon component
├── utils.ts               # Utility functions
└── generate-icons.js      # The generator script

Usage

Basic Usage

Generate new icon components (skips existing files):

node generate-icons.js

Force Regenerate

Overwrite existing icon components in the icons/ directory:

node generate-icons.js --force
# or
node generate-icons.js -f

How It Works

  1. Scans the svg/ directory (including subdirectories) for .svg files
  2. Parses each SVG file and extracts the content
  3. Generates a TSX component with:
    • JSX-formatted SVG content
    • Icon definition using svgToIconDefinition
    • ForwardRef component wrapper
    • Base64 encoded SVG preview in comments
  4. Outputs the component to icons/{IconName}.tsx

Generated Component Structure

Each generated component follows this structure:

// GENERATE BY ./scripts/generate-icons.js
// DON NOT EDIT IT MANUALLY

import * as React from 'react';

import TdmIcon from '../components/TdmIcon';
import type { TdmIconProps } from '../components/TdmIcon';
import { svgToIconDefinition } from '../utils';

const iconNameSvg = (
  <svg
    width="24"
    height="24"
    viewBox="0 0 24 24"
    fill="#cacaca"
    xmlns="http://www.w3.org/2000/svg"
  >
    <path d="..." />
  </svg>
);

const iconNameIconDefinition = svgToIconDefinition(
  iconNameSvg,
  'icon-name'
);

/**![IconNameIcon](data:image/svg+xml;base64,...) */
const RefIcon: React.ForwardRefExoticComponent<
  Omit<TdmIconProps, 'ref'> & React.RefAttributes<HTMLSpanElement>
> = React.forwardRef<HTMLSpanElement, TdmIconProps>((props, ref) => {
  return <TdmIcon {...props} ref={ref} icon={iconNameIconDefinition} />;
});

if (process.env.NODE_ENV !== 'production') {
  RefIcon.displayName = 'IconNameIcon';
}

export default RefIcon;

Naming Conventions

| SVG Filename | Component Name | Variable Name | Kebab Name | |--------------|----------------|---------------|------------| | AddressBookFilledIcon.svg | AddressBookFilledIcon | addressBookFilledSvg | address-book-filled | | BellOutlinedIcon.svg | BellOutlinedIcon | bellOutlinedSvg | bell-outlined | | SocialGoogleColorIcon.svg | SocialGoogleColorIcon | socialGoogleColorSvg | social-google-color |

Adding New Icons

1. Chuẩn bị file SVG

Đảm bảo file SVG của bạn có các thuộc tính chuẩn:

<svg width="24" height="24" viewBox="0 0 24 24" fill="#cacaca" xmlns="http://www.w3.org/2000/svg">
  <path d="..." />
</svg>

2. Đặt file SVG vào thư mục phù hợp

Thêm file vào thư mục tương ứng trong svg/:

  • svg/filled/ - Icon kiểu filled (ví dụ: BellFilledIcon.svg)
  • svg/outlined/ - Icon kiểu outlined (ví dụ: BellOutlinedIcon.svg)
  • svg/color/ - Icon có màu (ví dụ: LogoColorIcon.svg)
  • svg/ - Icon không thuộc style cụ thể

3. Generate icon components

Chạy script để tạo các component React từ file SVG:

node generate-icons.js

Hoặc dùng --force để ghi đè các file đã tồn tại:

node generate-icons.js --force

4. Tạo changeset

Tạo changeset để ghi nhận thay đổi cho version tiếp theo:

pnpm changeset

Chọn loại thay đổi:

  • patch - Sửa lỗi hoặc thay đổi nhỏ (0.0.x)
  • minor - Thêm tính năng mới (0.x.0)
  • major - Thay đổi breaking changes (x.0.0)

Nhập mô tả thay đổi (ví dụ: "Add new BellFilledIcon")

5. Build package

Build package để tạo các file output:

pnpm build

Lệnh này sẽ:

  • Compile TypeScript sang JavaScript
  • Tạo type definitions (.d.ts)
  • Bundle các file theo cấu trúc trong tsup.config.ts

6. Publish lên npm

Cách 1: Sử dụng changeset (Khuyến nghị)

pnpm changeset version

Lệnh này sẽ:

  • Cập nhật version trong package.json
  • Tạo/cập nhật CHANGELOG.md
  • Xóa các changeset files đã được áp dụng

Sau đó publish:

pnpm publish

Cách 2: Publish trực tiếp

npm publish

Lưu ý: Đảm bảo bạn đã đăng nhập npm (npm login) và có quyền publish package.

7. Sử dụng icon mới

Sau khi publish, bạn có thể sử dụng icon trong project:

Import trực tiếp (Recommended)

import BellFilledIcon from '@tdm-design/icons/BellFilledIcon';

function App() {
  return <BellFilledIcon />;
}

Sử dụng Barrel Export (Hỗ trợ Tree-shaking)

import { BellFilledIcon } from '@tdm-design/icons';

Tùy chỉnh Icon

<BellFilledIcon style={{ color: 'red' }} spin />

Output Status

When running the script, you'll see the following status indicators:

| Status | Description | |--------|-------------| | [OK] | New component generated successfully | | [OVERWRITE] | Existing component overwritten (with --force) | | [SKIP] | Component already exists, skipped | | [ERROR] | Failed to parse SVG file |

Example Output

$ node generate-icons.js --force

Force mode enabled: will overwrite existing files in icons/

[OVERWRITE] ArrowLeftIcon.tsx
[OK] BellFilledIcon.tsx
[SKIP] ChartSimpleIcon.tsx already exists in icons/
[ERROR] Failed to parse InvalidIcon.svg

=== Done ===
Generated: 15
Overwritten: 5
Skipped: 100
Errors: 1
Total SVG files: 121

Troubleshooting

SVG Not Parsing

Ensure your SVG file:

  • Has valid XML structure
  • Contains a <svg> root element
  • Does not have extra characters (like trailing dots)

Component Not Generating

Check that:

  • The SVG file is in the svg/ directory or its subdirectories
  • The file has a .svg extension
  • The SVG content is valid

Overwriting Protected Files

By default, existing files are protected. Use --force to overwrite:

node generate-icons.js --force

License

MIT