Write less, expand more.
A lightweight preprocessor that expands Tailwind-style shorthand into full variant syntax. Write expressive classes like:
<div
class="hover(bg-blue-500 text-blue-50) dark(border-blue-300 hover(bg-blue-400 text-blue-950))"
></div>and automatically transform them into:
<div
class="hover:bg-blue-500 hover:text-blue-50 dark:border-blue-300 dark:hover:bg-blue-400 dark:hover:text-blue-950"
></div>- Expand Tailwind shorthand groups automatically
- Supports nested variants (
hover(),dark(),group-hover(),peer-focus(),not(), etc.) - Fast, zero-runtime — designed for build-time processing
- CLI-friendly — runs before Prettier or dev servers
- Fully verbose logging with
-v/--verboseoption - Colored console output with
picocolors - Works in Node, CLI, and browser environments
pnpm add -D prewind
# or
npm install -D prewind
# or
yarn add -D prewindGlobal install (optional):
pnpm add -g prewind| Flag | Description |
|---|---|
<patterns...> |
File path(s) or glob pattern(s) to process |
-w, --write |
Overwrite files in place |
-o, --out <dir> |
Output transformed files into a directory or file |
-v, --verbose |
Show detailed file processing logs (colored output) |
--dry-run |
Preview changes without writing (default) |
--ignore <patterns> |
Glob patterns to ignore |
-h, --help |
Show CLI help |
prewind src/test.html
prewind "src/**/*.html" --dry-runOutputs transformed files to console without modifying them.
prewind -w src/test.html
prewind src/**/*.html --writePrompts confirmation before overwriting files.
prewind src/**/*.html -o dist
prewind src/test.html -o out.htmlprewind src/**/*.html --dry-run -v
prewind src/**/*.html --write -v
prewind src/**/*.html -o dist -vPrints Changed/Unchanged for each file, showing input → output paths in colored console.
Prewind also works in the browser via ESM modules.
<script type="module">
import { transform } from 'https://cdn.jsdelivr.net/npm/prewind/dist/main.js'
const html = `
<div
class="hover(bg-blue-500 text-blue-50) dark(border-blue-300 hover(bg-blue-400 text-blue-950))"
></div>
`
console.log(transform(html))
</script><div id="btn" class="hover(bg-blue-500 text-white)"></div>
<script type="module">
import { transformDOM } from 'https://cdn.jsdelivr.net/npm/prewind/dist/main.js'
const el = document.getElementById('btn')
transformDOM(el)
// <div id="btn" class="hover:bg-blue-500 hover:text-white"></div>
</script><div id="app"></div>
<script type="module">
import { observeDOM } from 'https://cdn.jsdelivr.net/npm/prewind/dist/main.js'
const app = document.getElementById('app')
observeDOM(app)
const btn = document.createElement('button')
btn.className = 'hover(bg-red-500 text-white)'
app.appendChild(btn)
// observeDOM auto-transforms new elements
</script>import { transform } from 'prewind'
const jsx = `<div class="hover(bg-blue-500 text-white)"></div>`
console.log(transform(jsx))
// <div class="hover:bg-blue-500 hover:text-white"></div>Works in React, Vue, Svelte, or any frontend framework. Integrate as a build-time step with Vite/Webpack/Rollup.
Writing full Tailwind variants is verbose:
<div
class="hover:bg-blue-500 hover:text-blue-50 dark:hover:bg-blue-400 dark:hover:text-blue-950"
></div>Prewind lets you express them structurally:
<div class="hover(bg-blue-500 text-blue-50) dark(hover(bg-blue-400 text-blue-950))"></div>No conflicts with Prettier or Tailwind JIT — works before formatters or dev servers.
pnpm install
pnpm run try tests/test.html # Run CLI locally
pnpm run build # Build CLI + browser
pnpm link --global # Test global CLI
prewind src/**/*.html # Run globally- v2.1: Verbose logging, colored CLI, safe
--outhandling - Config file support (
prewind.config.json) - Add
--dryand--silentmodes
art70x — MIT License © 2025 GitHub Repository →
🌀 Prewind — write less, expand more