Skip to main content

wind-ui

Build Flutter UI with Wind's utility-first className system. W-prefix widgets, design culture, enforcement gates, theming, component-first workflow.

설치로 이동

소스 정보

저장소
anilcancakir/uptizm-app
최근 소스 활동
2026년 4월 17일 11:45
감지된 SKILL.md 언어
영어
스타
0
포크
0

설치 방법

기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.

소스 파일 검토

설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.

파일 탐색기
10 개 파일

SKILL.md 표시 중

SKILL.md
소스 지침 · 읽기 전용 미리보기
name
wind-ui
description
Build Flutter UI with Wind's utility-first className system. W-prefix widgets, design culture, enforcement gates, theming, component-first workflow.
when_to_use
TRIGGER: WDiv, WText, WButton, WInput, WSelect, WCheckbox, WIcon, WImage, WSvg, WPopover, WAnchor, WFormInput, WFormSelect, WFormMultiSelect, WFormCheckbox, WDatePicker, WFormDatePicker, WSpacer, WDynamic, className, WindTheme, WindThemeData, wind-ui, Flutter styling, Flutter layout, mobile UI, app design, component design. DO NOT TRIGGER: general Flutter questions without className usage, pure Dart logic without UI, backend/API code.
version
1.0.0-alpha.6
<!-- Wind UI v1.0.0-alpha.6 | Skill updated: 2026-04-16 | Last lib/ change: 2026-04-04 --> # Wind UI v1 Utility-first styling for Flutter UI. Translate Tailwind-like classes to Flutter render tree semantics via `className` string parsing. ## 1. Core Laws 1. **W-prefix mandate**: Use `WDiv` (not Container), `WText` (not Text), `WButton` (not ElevatedButton/GestureDetector). 2. **className-first**: ALL styling via `className` string. Never inline BoxDecoration, TextStyle, or EdgeInsets when a Wind equivalent exists. 3. **dark: is mandatory**: Every `bg-`, `text-`, and `border-` class MUST have a `dark:` counterpart. 4. **Trailing commas**: Always on the last constructor parameter and list item. 5. **Multi-line**: Constructor parameters must always be multi-line when 3 or more. 6. **No theory output**: When applying styling, provide the code directly. Do not explain the classes. ## 2. Flutter Layout Reality Flutter constraint resolution differs fundamentally from CSS. Wind UI maps `className` syntax to native Flutter semantics. Follow these rules to avoid overflows and unbounded height errors. **Space-filling** | Goal | Use | Why | |------|-----|-----| | Fill remaining space in Row/Column | `flex-1` | Maps to `Expanded`, negotiates available space | | Full width in Column context | `w-full` | `SizedBox(width: double.infinity)`, works here | | Full width in Row context | `flex-1` (NOT `w-full`!) | `w-full` causes `RenderFlex` overflow in Rows | | `flex-none` / `shrink-0` | No flex shrink. Unlike CSS, Flutter Row/Column children do not auto-shrink; use `flex-1` to allow growth | Row child stays fixed width | **Scrollable layouts** | Goal | className | Required context | |------|-----------|-----------------| | Vertical scroll | `overflow-y-auto` + `scrollPrimary: true` | Parent MUST have bounded height | | Bounded height for scroll | `flex-1` on the scrollable `WDiv` | Inside a Column/Flex parent | | Horizontal scroll | `overflow-x-auto` | Same rules | | Flex children inside scrollable main axis | `flex-1` on child works (Wind skips `Expanded` automatically when parent scrolls that axis) | `flex flex-row + overflow-x-auto` or `flex flex-col + overflow-y-auto` — no unbounded-constraints assertion | **WDiv Composition Rules** | className contains | Flutter widget | Notes | |-------------------|----------------|-------| | `flex flex-col` | Column | `flex` alone defaults to Row | | `flex flex-row` or `flex` | Row | Direction default | | `flex-row-reverse` / `flex-col-reverse` | Row/Column with flipped main axis | Uses `textDirection` / `verticalDirection` so `justify-start` mirrors (matches CSS) | | `order-{0..12}` / `order-first` / `order-last` / `order-[n]` | Child reorder inside flex parent | Parent stable-sorts; children without `order-*` default to 0 | | `wrap` or `grid` | Wrap | NOT `flex-wrap` (no-op!) | | `overflow-y-auto` | SingleChildScrollView | Needs bounded height | | `relative` | Stack(clipBehavior: Clip.none) | Children split: normal layout + Positioned | | `absolute top-4 right-4` | Positioned(top: 16, right: 16) | Must be inside a `relative` parent | | `absolute inset-0` | Positioned(top: 0, right: 0, bottom: 0, left: 0) | Full overlay pattern | | `hidden` | SizedBox.shrink() | | **Critical Layout Gotchas:** ```dart // ❌ WRONG: overflow in Row WDiv( className: 'flex flex-row', children: [ WDiv(className: 'w-full', child: WText('Long text')), // OVERFLOW ], ) // ✅ CORRECT WDiv( className: 'flex flex-row', children: [ WDiv(className: 'flex-1', child: WText('Long text')), // Fills remaining space ], ) ``` ```dart // ❌ WRONG: unbounded height scroll Column( children: [ WDiv(className: 'overflow-y-auto', children: [...]) // ERROR: infinite height ], ) // ✅ CORRECT WDiv( className: 'flex flex-col h-full', // Bounded children: [ WDiv( className: 'flex-1 overflow-y-auto', scrollPrimary: true, // iOS tap-to-top children: [...], ), ], ) ``` ```dart // ❌ WRONG: truncate without bounded width WDiv( className: 'flex flex-row', children: [ WText('Very long title', className: 'truncate'), // OVERFLOW ], ) // ✅ CORRECT WDiv( className: 'flex flex-row', children: [ WDiv( className: 'flex-1', // Bounds the text child: WText('Very long title', className: 'truncate'), ), ], ) ``` ```dart // ❌ WRONG: absolute without relative parent WDiv( className: 'flex flex-row', children: [ WDiv(className: 'absolute top-0 right-0', child: badge), // No Stack! ], ) // ✅ CORRECT: relative parent creates Stack WDiv( className: 'relative flex flex-row', children: [ WDiv(className: 'flex-1', child: content), WDiv(className: 'absolute top-0 right-0', child: badge), // Positioned overlay ], ) ``` **Note:** `h-full` inside a scrollable parent results in an infinite height error. Use `min-h-screen` instead. Native Flutter widgets (e.g., `ListView.builder`, charts) inside a `Row` or `Column` MUST be wrapped in `Expanded()` (allowed exception to Gate 1 for non-Wind widget bounding). `absolute` children only work inside a `relative` parent. Only `WDiv` and `WText` are detected as absolute; wrap other widgets in a `WDiv`. ## 3. Widget Quick Reference | Widget | Required Props | Key Optional Props | Use For | |--------|---------------|-------------------|---------| | `WDiv` | - | `className`, `child`/`children`, `states`, `scrollPrimary` | Any container, layout | | `WText` | `data` | `className`, `selectable`, `states` | All text rendering | | `WButton` | `child` | `onTap`, `isLoading`, `disabled`, `className` | All interactive buttons | | `WInput` | `value`, `onChanged`| `type`, `placeholder`, `className`, `placeholderClassName`| Standalone inputs | | `WSelect` | `options`, `value`/`values`, `onChange` | `searchable`, `isMulti`, `onCreateOption`, `className`| Dropdowns | | `WCheckbox`| `value`, `onChanged`| `className` | Toggle checkboxes | | `WIcon` | `icon` | `className` | Icons with styling | | `WImage` | `src` | `className` | Images with object-fit | | `WSvg` | `src` | `className`, `preserve-colors` | SVG with fill/stroke/preserve | | `WPopover` | `triggerBuilder`, `contentBuilder`| `alignment`, `className` | Dropdowns, menus, tooltips| | `WAnchor` | `child` | `onTap`, `className` | Raw interactive wrapper | | `WFormInput`| (FormField) | `controller`, `type`, `placeholder`, `className`, `validator` | MagicForm-integrated input| | `WFormSelect`| (FormField) | `options`, `searchable`, `className` | MagicForm-integrated select| | `WFormMultiSelect`| (FormField) | `options`, `onCreateOption`, `className` | MagicForm multi-select | | `WFormCheckbox`| (FormField) | `label`, `className` | MagicForm-integrated checkbox| | `WDatePicker`| `mode`, `onDateSelected`/`onRangeSelected` | `className`, `initialDate`, `firstDate`, `lastDate`| Single date or date range picker| | `WFormDatePicker`| (FormField) | `mode`, `className`, `firstDate`, `lastDate` | MagicForm-integrated date picker| | `WSpacer` | - | `className` | Semantic spacing between siblings | | `WDynamic` | `json` | `actions`, `controller`, `customIcons`, `builders`, `denyWidgets` | Server-driven UI from JSON | | `WBreakpoint` | `base` (builder) | `sm`, `md`, `lg`, `xl`, `xxl`, `custom` | Render a fully different widget tree per breakpoint — escape hatch when className prefixes + `hidden` aren't enough | **Rules:** - `child` and `children` are mutually exclusive on `WDiv`. - `WDiv` auto-wraps in `WAnchor` if `hover:`, `focus:`, or `active:` is present in the `className`. - `WButton` with `isLoading: true` activates `loading:` prefix classes and disables interaction. - `WSelect` with `isMulti: true` must use `values` + `onMultiChange` instead of `value` + `onChange`. - `WSpacer` is a `const`-friendly semantic spacer. Prefer over `SizedBox` or empty `WDiv` for gaps between siblings. - `WDatePicker` `mode`: `DatePickerMode.single` or `DatePickerMode.range`. Range mode uses `onRangeSelected` callback. ## 4. Token System **Spacing Formula:** `n × 4px` (e.g., `p-4` = 16px, `gap-6` = 24px, `m-2` = 8px) **Color Syntax:** `{role}-{color}-{shade}` (e.g., `bg-blue-500`, `text-gray-900`, `border-red-300`) - **Opacity:** `bg-primary/50`, `text-gray-500/75` - **Arbitrary:** `bg-[#FF5733]`, `w-[200px]`, `text-[18px]` **Responsive:** Prefix with breakpoint (e.g., `md:flex-row`, `lg:p-6`, `xl:hidden`) - Breakpoints: `sm` (640px), `md` (768px), `lg` (1024px), `xl` (1280px), `2xl` (1536px) **Typography Sizes:** `xs` (12), `sm` (14), `base` (16), `lg` (18), `xl` (20), `2xl` (24), `3xl` (30), `4xl` (36) **Border Radius:** `rounded` (4), `rounded-md` (6), `rounded-lg` (8), `rounded-xl` (12), `rounded-2xl` (16), `rounded-full` (9999) **Position Types:** `relative` (renders Stack), `absolute` (renders Positioned inside a Stack) **Offsets (spacing scale):** `top-{n}` `right-{n}` `bottom-{n}` `left-{n}` (e.g., `top-4` = 16px) **Insets:** `inset-{n}` (all sides), `inset-x-{n}` (left+right), `inset-y-{n}` (top+bottom) **Negative offsets:** `-top-{n}`, `-inset-{n}` (prefix with `-`) **Arbitrary offsets:** `top-[24px]`, `left-[24px]` (px only; `%` is unsupported) **Note:** `fixed` and `sticky` are not implemented. Absolute children must be inside a `relative` parent. ## 5. State & Modifier Prefixes | Prefix | Trigger | Example | |--------|---------|---------| | `dark:` | Dark mode (MANDATORY on all colors) | `bg-white dark:bg-gray-800` |
GitHub에서 보기
이 SKILL.md는 매우 커서 SkillsMP가 여기에는 첫 섹션만 미리 보여줍니다. GitHub에서 보기