[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6X05M0ET2HKB5HASM7GG02G":3,"skill-same:01M6X05M0ET2HKB5HASM7GG02G":78},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":16,"categories":17,"keywords":18,"publishedAt":39,"linkOnly":40,"markdownContent":41,"markdownBody":42,"frontMatter":43,"refName":51,"commitSha":52,"skillDirectory":53,"forksCount":14,"repositoryHtmlUrl":54,"repositoryHomepageUrl":55,"ownerHtmlUrl":56,"ownerBlogUrl":6,"ownerDescription":6,"updatedAt":57,"install":58,"resources":71},"01M6X05M0ET2HKB5HASM7GG02G","flutter-development",null,"Flutter and Dart development — widget architecture, state management, navigation, and cross-platform layout. Use when building Flutter apps, choosing a state-management approach, designing responsive layouts, or reviewing widget code.","projectious-work\u002Fprocesskit","projectious-work","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F263889726?v=4","01M6N97TJJ118WQ35CHRV8RD0E","projectious.work","01M6N97TPWJPF0BMKYQ4PBY5W8",0,"MIT","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Farchive\u002Fprocesskit-install-20261101\u002Fcontext\u002Ftemplates\u002Fprocesskit\u002Fv0.18.2\u002Fcontext\u002Fskills\u002Fengineering\u002Fflutter-development\u002FSKILL.md",[],[19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38],"development","flutter development","flutter","when","architecture","v1","apps","platform","layout","widget","state-management","navigation","use","management","work","dart","engineering","state","code","state management","2026-11-10 10:12:30",false,"---\nname: flutter-development\ndescription: |\n  Flutter and Dart development — widget architecture, state management, navigation, and cross-platform layout. Use when building Flutter apps, choosing a state-management approach, designing responsive layouts, or reviewing widget code.\nmetadata:\n  processkit:\n    apiVersion: processkit.projectious.work\u002Fv1\n    id: SKILL-flutter-development\n    version: \"1.1.0\"\n    created: 2026-04-06T00:00:00Z\n    category: engineering\n---\n\n# Flutter Development\n\n## Intro\n\nIn Flutter, everything is a widget — compose small `StatelessWidget`s\nand `StatefulWidget`s into screens, prefer `const` constructors, and\nkeep `build()` methods lightweight. Pick the simplest state-management\nsolution that fits the complexity, not the most fashionable one.\n\n## Overview\n\n### Widget architecture\n\nUse `StatelessWidget` when there's no mutable state and\n`StatefulWidget` when the widget owns animations, controllers, or\nform input. Extract sub-widgets into top-level classes (not helper\nmethods) so they can be `const` and rebuild independently. Compose by\nwrapping, never by extending. Name widgets by purpose\n(`UserProfileCard`), not by position or sequence.\n\n### Layout system\n\n`Row` and `Column` are the primary axis-based layouts; `Expanded` and\n`Flexible` distribute space among children. `Stack` plus `Positioned`\nhandles overlap and absolute placement. Use `ListView.builder` \u002F\n`GridView.builder` for any list that may grow — they only build\nvisible items. `SizedBox` for fixed gaps, `Spacer` for flexible gaps,\n`Padding`\u002F`Container` for spacing and decoration. Reach for\n`LayoutBuilder` and `MediaQuery` when the layout depends on the\nviewport.\n\n### State management\n\nPick the smallest tool that fits:\n\n- Local widget state → `StatefulWidget` + `setState`\n- Shared state across a few screens → Provider or Riverpod\n- Complex async flows with many events → BLoC\n\nRiverpod is type-safe and avoids `BuildContext` plumbing; BLoC enforces\nevent-driven structure for large apps. Avoid putting all state in a\nsingle global provider — split by domain so unrelated screens don't\nrebuild together.\n\n### Navigation with GoRouter\n\nDefine routes declaratively and navigate with `context.go(...)` to\nreplace or `context.push(...)` to stack. Use `ShellRoute` \u002F\n`StatefulShellRoute` for tabbed layouts that need to preserve state\nper tab. Authentication guards live in the `redirect` callback. Deep\nlinking works automatically once routes are declared.\n\n### Theming\n\nConfigure theme on `MaterialApp` with\n`ThemeData(useMaterial3: true, colorScheme: ColorScheme.fromSeed(...))`.\nRead theme values via `Theme.of(context)` rather than hardcoding font\nsizes or colors. Provide a matching `darkTheme` and let Flutter pick\nbased on platform brightness.\n\n### Networking and data\n\nUse `http` or `dio` for REST. Serialize JSON via `json_serializable`\nand `build_runner` for type-safe parsing. Wrap APIs in repositories\n(`UserRepository` over a raw client). In the UI, render\nloading\u002Ferror\u002Fdata states explicitly with `FutureBuilder` or\n`StreamBuilder` — never show a blank screen while waiting.\n\n### Testing\n\nThree layers: pure-Dart unit tests with `test()`, widget tests with\n`testWidgets()` and `find.byType()`, and full integration tests with\nthe `integration_test` package. Use `pumpWidget` to mount and `pump`\nto advance frames. Mock external boundaries with `mocktail` or\n`mockito`. Use golden tests (`matchesGoldenFile`) for visual\nregression on critical screens.\n\n## Gotchas\n\nAgent-specific failure modes — provider-neutral pause-and-self-check items:\n\n- **Nested `Scaffold` widgets.** A `Scaffold` inside another `Scaffold` produces double app bars, broken navigation behavior, and unpredictable layout. Each route gets exactly one `Scaffold` at the top level.\n- **`setState` called after `dispose()`.** Calling `setState` on a widget that has been removed from the tree throws a `FlutterError` in debug mode and causes silent bugs in release mode. Guard all async callbacks with `if (!mounted) return;` before calling `setState`.\n- **Forgetting to call `dispose()` on controllers, animations, and stream subscriptions.** Objects that own platform resources or listeners are not garbage-collected automatically. Not disposing them causes memory leaks and \"stream already closed\" errors. Override `dispose()` and clean up every controller and subscription.\n- **Using helper methods instead of top-level `StatelessWidget` classes for sub-widgets.** A helper method returning a `Widget` rebuilds on every parent rebuild regardless of whether its inputs changed. A top-level widget class enables `const` instantiation and independent rebuild boundaries.\n- **Unbounded `Text` or `Column` inside a `Row`.** A `Text` widget without a size constraint in a `Row` throws a \"RenderFlex overflowed\" error. Wrap with `Expanded` or `Flexible` to constrain it, or use `SizedBox` with a fixed width.\n- **Blocking the event loop in a widget's `build()` method.** `build()` is called every frame. Any synchronous heavy computation inside it drops frames and causes jank. Move expensive work into `initState`, an async handler, or a compute isolate.\n- **Using `ListView()` with all items materialized for a long list.** `ListView()` with a `children` list builds all items up front. Use `ListView.builder` so only the visible items are built; this scales to thousands of items.\n\n## Full reference\n\n### Layout widget recipes\n\n```dart\n\u002F\u002F Row — horizontal layout\nRow(\n  mainAxisAlignment: MainAxisAlignment.spaceBetween,\n  crossAxisAlignment: CrossAxisAlignment.center,\n  children: [Text('Left'), Text('Right')],\n)\n\n\u002F\u002F Column — vertical layout\nColumn(\n  mainAxisSize: MainAxisSize.min,  \u002F\u002F shrink-wrap\n  children: [\n    Text('Title'),\n    SizedBox(height: 8),\n    Text('Subtitle'),\n  ],\n)\n\n\u002F\u002F Stack — overlapping children\nStack(\n  children: [\n    Image.network(url),\n    Positioned(\n      bottom: 16, left: 16,\n      child: Text('Overlay text'),\n    ),\n  ],\n)\n\n\u002F\u002F Wrap — flow layout with wrapping\nWrap(\n  spacing: 8, runSpacing: 4,\n  children: tags.map((t) => Chip(label: Text(t))).toList(),\n)\n```\n\n### Scrollable widgets\n\n```dart\n\u002F\u002F ListView.builder — efficient for large lists\nListView.builder(\n  itemCount: items.length,\n  itemBuilder: (context, index) => ListTile(\n    title: Text(items[index].name),\n    subtitle: Text(items[index].description),\n    leading: CircleAvatar(child: Text(items[index].initials)),\n    trailing: Icon(Icons.chevron_right),\n    onTap: () => context.push('\u002Fitems\u002F${items[index].id}'),\n  ),\n)\n\n\u002F\u002F GridView.builder\nGridView.builder(\n  gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(\n    crossAxisCount: 2, crossAxisSpacing: 8, mainAxisSpacing: 8,\n  ),\n  itemCount: products.length,\n  itemBuilder: (context, i) => ProductCard(products[i]),\n)\n\n\u002F\u002F CustomScrollView with slivers\nCustomScrollView(\n  slivers: [\n    SliverAppBar(floating: true, title: Text('Feed')),\n    SliverList.builder(\n      itemCount: posts.length,\n      itemBuilder: (context, i) => PostCard(posts[i]),\n    ),\n  ],\n)\n```\n\n### Form input\n\n```dart\n\u002F\u002F TextField\nTextField(\n  controller: _controller,\n  decoration: InputDecoration(\n    labelText: 'Email',\n    hintText: 'you@example.com',\n    prefixIcon: Icon(Icons.email),\n    border: OutlineInputBorder(),\n    errorText: _hasError ? 'Invalid email' : null,\n  ),\n  keyboardType: TextInputType.emailAddress,\n  onChanged: (value) => setState(() => _email = value),\n)\n\n\u002F\u002F Form with validation\nForm(\n  key: _formKey,\n  child: Column(children: [\n    TextFormField(\n      validator: (v) => v == null || v.isEmpty ? 'Required' : null,\n    ),\n    ElevatedButton(\n      onPressed: () {\n        if (_formKey.currentState!.validate()) { \u002F* submit *\u002F }\n      },\n      child: Text('Submit'),\n    ),\n  ]),\n)\n```\n\n### Async builders\n\n```dart\n\u002F\u002F FutureBuilder — one-shot async\nFutureBuilder\u003CUser>(\n  future: _userFuture,\n  builder: (context, snapshot) {\n    if (snapshot.connectionState == ConnectionState.waiting) {\n      return CircularProgressIndicator();\n    }\n    if (snapshot.hasError) return Text('Error: ${snapshot.error}');\n    final user = snapshot.data!;\n    return Text(user.name);\n  },\n)\n\n\u002F\u002F StreamBuilder — continuous updates\nStreamBuilder\u003Cint>(\n  stream: _counterStream,\n  builder: (context, snapshot) {\n    return Text('Count: ${snapshot.data ?? 0}');\n  },\n)\n```\n\n### Common patterns\n\n```dart\n\u002F\u002F Responsive layout\nLayoutBuilder(\n  builder: (context, constraints) {\n    if (constraints.maxWidth > 600) {\n      return Row(children: [Sidebar(), Expanded(child: Content())]);\n    }\n    return Content();  \u002F\u002F mobile: no sidebar\n  },\n)\n\n\u002F\u002F Pull-to-refresh\nRefreshIndicator(\n  onRefresh: () async => await _loadData(),\n  child: ListView.builder(...),\n)\n\n\u002F\u002F Empty state\nitems.isEmpty\n    ? Center(child: Text('No items yet'))\n    : ListView.builder(\n        itemCount: items.length,\n        itemBuilder: (ctx, i) => ItemTile(items[i]),\n      )\n```\n\n### Material 3 navigation\n\n```dart\nNavigationBar(\n  selectedIndex: _currentIndex,\n  onDestinationSelected: (i) => setState(() => _currentIndex = i),\n  destinations: [\n    NavigationDestination(icon: Icon(Icons.home), label: 'Home'),\n    NavigationDestination(icon: Icon(Icons.search), label: 'Search'),\n    NavigationDestination(icon: Icon(Icons.person), label: 'Profile'),\n  ],\n)\n```\n\n### Platform channels\n\nPrefer existing packages (`camera`, `geolocator`, `path_provider`)\nover hand-rolled channels. When you must call native code, use\n`MethodChannel` for one-off calls and `EventChannel` for streams.\nPlatform-specific source goes in `android\u002F` and `ios\u002F`. Use\n`Platform.isIOS` \u002F `Platform.isAndroid` for branching in Dart.\n\n### Performance\n\n- Use `const` widgets aggressively — they short-circuit rebuilds\n- `ListView.builder` for any non-trivial list\n- Avoid `setState` high in the tree; it rebuilds every descendant\n- Wrap expensive painters in `RepaintBoundary` to isolate them\n- Prefer `Opacity` only when necessary — it forces an off-screen\n  layer\n- Cache network images with `CachedNetworkImage`\n- Profile rebuild counts and frame times in Flutter DevTools\n\n### Common mistakes\n\n- **Nested `Scaffold`s** — leads to double app bars and broken\n  navigation\n- **`setState` after dispose** — guard with `mounted`, cancel timers\n  and stream subscriptions in `dispose()`\n- **Unbounded children in `Row`\u002F`Column`** — wrap with `Expanded` or\n  `Flexible`\n- **Forgetting `dispose()`** — controllers, animation controllers,\n  and stream subscriptions all need explicit disposal\n- **Hardcoded user-facing strings** — use `intl` or\n  `easy_localization`\n\n### Further reading\n\n- [Flutter Documentation](https:\u002F\u002Fdocs.flutter.dev\u002F)\n- [Flutter Widget Catalog](https:\u002F\u002Fdocs.flutter.dev\u002Fui\u002Fwidgets)\n","# Flutter Development\n\n## Intro\n\nIn Flutter, everything is a widget — compose small `StatelessWidget`s\nand `StatefulWidget`s into screens, prefer `const` constructors, and\nkeep `build()` methods lightweight. Pick the simplest state-management\nsolution that fits the complexity, not the most fashionable one.\n\n## Overview\n\n### Widget architecture\n\nUse `StatelessWidget` when there's no mutable state and\n`StatefulWidget` when the widget owns animations, controllers, or\nform input. Extract sub-widgets into top-level classes (not helper\nmethods) so they can be `const` and rebuild independently. Compose by\nwrapping, never by extending. Name widgets by purpose\n(`UserProfileCard`), not by position or sequence.\n\n### Layout system\n\n`Row` and `Column` are the primary axis-based layouts; `Expanded` and\n`Flexible` distribute space among children. `Stack` plus `Positioned`\nhandles overlap and absolute placement. Use `ListView.builder` \u002F\n`GridView.builder` for any list that may grow — they only build\nvisible items. `SizedBox` for fixed gaps, `Spacer` for flexible gaps,\n`Padding`\u002F`Container` for spacing and decoration. Reach for\n`LayoutBuilder` and `MediaQuery` when the layout depends on the\nviewport.\n\n### State management\n\nPick the smallest tool that fits:\n\n- Local widget state → `StatefulWidget` + `setState`\n- Shared state across a few screens → Provider or Riverpod\n- Complex async flows with many events → BLoC\n\nRiverpod is type-safe and avoids `BuildContext` plumbing; BLoC enforces\nevent-driven structure for large apps. Avoid putting all state in a\nsingle global provider — split by domain so unrelated screens don't\nrebuild together.\n\n### Navigation with GoRouter\n\nDefine routes declaratively and navigate with `context.go(...)` to\nreplace or `context.push(...)` to stack. Use `ShellRoute` \u002F\n`StatefulShellRoute` for tabbed layouts that need to preserve state\nper tab. Authentication guards live in the `redirect` callback. Deep\nlinking works automatically once routes are declared.\n\n### Theming\n\nConfigure theme on `MaterialApp` with\n`ThemeData(useMaterial3: true, colorScheme: ColorScheme.fromSeed(...))`.\nRead theme values via `Theme.of(context)` rather than hardcoding font\nsizes or colors. Provide a matching `darkTheme` and let Flutter pick\nbased on platform brightness.\n\n### Networking and data\n\nUse `http` or `dio` for REST. Serialize JSON via `json_serializable`\nand `build_runner` for type-safe parsing. Wrap APIs in repositories\n(`UserRepository` over a raw client). In the UI, render\nloading\u002Ferror\u002Fdata states explicitly with `FutureBuilder` or\n`StreamBuilder` — never show a blank screen while waiting.\n\n### Testing\n\nThree layers: pure-Dart unit tests with `test()`, widget tests with\n`testWidgets()` and `find.byType()`, and full integration tests with\nthe `integration_test` package. Use `pumpWidget` to mount and `pump`\nto advance frames. Mock external boundaries with `mocktail` or\n`mockito`. Use golden tests (`matchesGoldenFile`) for visual\nregression on critical screens.\n\n## Gotchas\n\nAgent-specific failure modes — provider-neutral pause-and-self-check items:\n\n- **Nested `Scaffold` widgets.** A `Scaffold` inside another `Scaffold` produces double app bars, broken navigation behavior, and unpredictable layout. Each route gets exactly one `Scaffold` at the top level.\n- **`setState` called after `dispose()`.** Calling `setState` on a widget that has been removed from the tree throws a `FlutterError` in debug mode and causes silent bugs in release mode. Guard all async callbacks with `if (!mounted) return;` before calling `setState`.\n- **Forgetting to call `dispose()` on controllers, animations, and stream subscriptions.** Objects that own platform resources or listeners are not garbage-collected automatically. Not disposing them causes memory leaks and \"stream already closed\" errors. Override `dispose()` and clean up every controller and subscription.\n- **Using helper methods instead of top-level `StatelessWidget` classes for sub-widgets.** A helper method returning a `Widget` rebuilds on every parent rebuild regardless of whether its inputs changed. A top-level widget class enables `const` instantiation and independent rebuild boundaries.\n- **Unbounded `Text` or `Column` inside a `Row`.** A `Text` widget without a size constraint in a `Row` throws a \"RenderFlex overflowed\" error. Wrap with `Expanded` or `Flexible` to constrain it, or use `SizedBox` with a fixed width.\n- **Blocking the event loop in a widget's `build()` method.** `build()` is called every frame. Any synchronous heavy computation inside it drops frames and causes jank. Move expensive work into `initState`, an async handler, or a compute isolate.\n- **Using `ListView()` with all items materialized for a long list.** `ListView()` with a `children` list builds all items up front. Use `ListView.builder` so only the visible items are built; this scales to thousands of items.\n\n## Full reference\n\n### Layout widget recipes\n\n```dart\n\u002F\u002F Row — horizontal layout\nRow(\n  mainAxisAlignment: MainAxisAlignment.spaceBetween,\n  crossAxisAlignment: CrossAxisAlignment.center,\n  children: [Text('Left'), Text('Right')],\n)\n\n\u002F\u002F Column — vertical layout\nColumn(\n  mainAxisSize: MainAxisSize.min,  \u002F\u002F shrink-wrap\n  children: [\n    Text('Title'),\n    SizedBox(height: 8),\n    Text('Subtitle'),\n  ],\n)\n\n\u002F\u002F Stack — overlapping children\nStack(\n  children: [\n    Image.network(url),\n    Positioned(\n      bottom: 16, left: 16,\n      child: Text('Overlay text'),\n    ),\n  ],\n)\n\n\u002F\u002F Wrap — flow layout with wrapping\nWrap(\n  spacing: 8, runSpacing: 4,\n  children: tags.map((t) => Chip(label: Text(t))).toList(),\n)\n```\n\n### Scrollable widgets\n\n```dart\n\u002F\u002F ListView.builder — efficient for large lists\nListView.builder(\n  itemCount: items.length,\n  itemBuilder: (context, index) => ListTile(\n    title: Text(items[index].name),\n    subtitle: Text(items[index].description),\n    leading: CircleAvatar(child: Text(items[index].initials)),\n    trailing: Icon(Icons.chevron_right),\n    onTap: () => context.push('\u002Fitems\u002F${items[index].id}'),\n  ),\n)\n\n\u002F\u002F GridView.builder\nGridView.builder(\n  gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(\n    crossAxisCount: 2, crossAxisSpacing: 8, mainAxisSpacing: 8,\n  ),\n  itemCount: products.length,\n  itemBuilder: (context, i) => ProductCard(products[i]),\n)\n\n\u002F\u002F CustomScrollView with slivers\nCustomScrollView(\n  slivers: [\n    SliverAppBar(floating: true, title: Text('Feed')),\n    SliverList.builder(\n      itemCount: posts.length,\n      itemBuilder: (context, i) => PostCard(posts[i]),\n    ),\n  ],\n)\n```\n\n### Form input\n\n```dart\n\u002F\u002F TextField\nTextField(\n  controller: _controller,\n  decoration: InputDecoration(\n    labelText: 'Email',\n    hintText: 'you@example.com',\n    prefixIcon: Icon(Icons.email),\n    border: OutlineInputBorder(),\n    errorText: _hasError ? 'Invalid email' : null,\n  ),\n  keyboardType: TextInputType.emailAddress,\n  onChanged: (value) => setState(() => _email = value),\n)\n\n\u002F\u002F Form with validation\nForm(\n  key: _formKey,\n  child: Column(children: [\n    TextFormField(\n      validator: (v) => v == null || v.isEmpty ? 'Required' : null,\n    ),\n    ElevatedButton(\n      onPressed: () {\n        if (_formKey.currentState!.validate()) { \u002F* submit *\u002F }\n      },\n      child: Text('Submit'),\n    ),\n  ]),\n)\n```\n\n### Async builders\n\n```dart\n\u002F\u002F FutureBuilder — one-shot async\nFutureBuilder\u003CUser>(\n  future: _userFuture,\n  builder: (context, snapshot) {\n    if (snapshot.connectionState == ConnectionState.waiting) {\n      return CircularProgressIndicator();\n    }\n    if (snapshot.hasError) return Text('Error: ${snapshot.error}');\n    final user = snapshot.data!;\n    return Text(user.name);\n  },\n)\n\n\u002F\u002F StreamBuilder — continuous updates\nStreamBuilder\u003Cint>(\n  stream: _counterStream,\n  builder: (context, snapshot) {\n    return Text('Count: ${snapshot.data ?? 0}');\n  },\n)\n```\n\n### Common patterns\n\n```dart\n\u002F\u002F Responsive layout\nLayoutBuilder(\n  builder: (context, constraints) {\n    if (constraints.maxWidth > 600) {\n      return Row(children: [Sidebar(), Expanded(child: Content())]);\n    }\n    return Content();  \u002F\u002F mobile: no sidebar\n  },\n)\n\n\u002F\u002F Pull-to-refresh\nRefreshIndicator(\n  onRefresh: () async => await _loadData(),\n  child: ListView.builder(...),\n)\n\n\u002F\u002F Empty state\nitems.isEmpty\n    ? Center(child: Text('No items yet'))\n    : ListView.builder(\n        itemCount: items.length,\n        itemBuilder: (ctx, i) => ItemTile(items[i]),\n      )\n```\n\n### Material 3 navigation\n\n```dart\nNavigationBar(\n  selectedIndex: _currentIndex,\n  onDestinationSelected: (i) => setState(() => _currentIndex = i),\n  destinations: [\n    NavigationDestination(icon: Icon(Icons.home), label: 'Home'),\n    NavigationDestination(icon: Icon(Icons.search), label: 'Search'),\n    NavigationDestination(icon: Icon(Icons.person), label: 'Profile'),\n  ],\n)\n```\n\n### Platform channels\n\nPrefer existing packages (`camera`, `geolocator`, `path_provider`)\nover hand-rolled channels. When you must call native code, use\n`MethodChannel` for one-off calls and `EventChannel` for streams.\nPlatform-specific source goes in `android\u002F` and `ios\u002F`. Use\n`Platform.isIOS` \u002F `Platform.isAndroid` for branching in Dart.\n\n### Performance\n\n- Use `const` widgets aggressively — they short-circuit rebuilds\n- `ListView.builder` for any non-trivial list\n- Avoid `setState` high in the tree; it rebuilds every descendant\n- Wrap expensive painters in `RepaintBoundary` to isolate them\n- Prefer `Opacity` only when necessary — it forces an off-screen\n  layer\n- Cache network images with `CachedNetworkImage`\n- Profile rebuild counts and frame times in Flutter DevTools\n\n### Common mistakes\n\n- **Nested `Scaffold`s** — leads to double app bars and broken\n  navigation\n- **`setState` after dispose** — guard with `mounted`, cancel timers\n  and stream subscriptions in `dispose()`\n- **Unbounded children in `Row`\u002F`Column`** — wrap with `Expanded` or\n  `Flexible`\n- **Forgetting `dispose()`** — controllers, animation controllers,\n  and stream subscriptions all need explicit disposal\n- **Hardcoded user-facing strings** — use `intl` or\n  `easy_localization`\n\n### Further reading\n\n- [Flutter Documentation](https:\u002F\u002Fdocs.flutter.dev\u002F)\n- [Flutter Widget Catalog](https:\u002F\u002Fdocs.flutter.dev\u002Fui\u002Fwidgets)\n",{"name":5,"metadata":44,"description":50},{"processkit":45},{"id":46,"created":47,"version":48,"category":35,"apiVersion":49},"SKILL-flutter-development",1775433600000,"1.1.0","processkit.projectious.work\u002Fv1","Flutter and Dart development — widget architecture, state management, navigation, and cross-platform layout. Use when building Flutter apps, choosing a state-management approach, designing responsive layouts, or reviewing widget code.\n","main","4876a92620ee792aac2ac9a1a806322d8a572367","archive\u002Fprocesskit-install-20261101\u002Fcontext\u002Ftemplates\u002Fprocesskit\u002Fv0.18.2\u002Fcontext\u002Fskills\u002Fengineering\u002Fflutter-development","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit","https:\u002F\u002Fprojectious-work.github.io\u002Fprocesskit\u002F","https:\u002F\u002Fgithub.com\u002Fprojectious-work","2026-11-11 23:24:18",{"source":8,"skillName":5,"commands":59,"prompt":69,"zipAvailable":70},[60,63,66],{"tool":61,"command":62},"npx","npx skills add projectious-work\u002Fprocesskit --skill flutter-development",{"tool":64,"command":65},"bunx","bunx skills add projectious-work\u002Fprocesskit --skill flutter-development",{"tool":67,"command":68},"pnpm","pnpm dlx skills add projectious-work\u002Fprocesskit --skill flutter-development","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Farchive\u002Fprocesskit-install-20261101\u002Fcontext\u002Ftemplates\u002Fprocesskit\u002Fv0.18.2\u002Fcontext\u002Fskills\u002Fengineering\u002Fflutter-development\u002FSKILL.md",true,[72],{"path":73,"resourceType":74,"resourceTypeDesc":75,"sizeBytes":76,"sourceHtmlUrl":77},"references\u002Fwidget-catalog.md","REFERENCE","参考文档",5424,"https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Farchive\u002Fprocesskit-install-20261101\u002Fcontext\u002Ftemplates\u002Fprocesskit\u002Fv0.18.2\u002Fcontext\u002Fskills\u002Fengineering\u002Fflutter-development\u002Freferences\u002Fwidget-catalog.md",[79,104,124,145,162,180],{"skillNo":80,"name":81,"nameZh":6,"description":82,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":83,"categories":84,"keywords":90,"publishedAt":39},"01M6X5MTC89B4ZGXW3JVSQCPF8","skill-management","Manage Skill package manifests as v1 ontology entities.","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Fsrc\u002Fcontext\u002Fskills\u002Fprocesskit\u002Fskill-management\u002FSKILL.md",[85],{"categoryNo":86,"categoryName":87,"taxonomyType":88,"taxonomyTypeDesc":89},"01JBSEEDCAT000000000000023","Skill与智能体开发","SCENARIO","使用场景",[32,91,92,93,94,95,33,96,97,98,81,99,100,101,24,102,103],"skill management","create","update","package","alpha","list","manage","ontology","get","as","manifests","skill package","transition",{"skillNo":105,"name":106,"nameZh":6,"description":107,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":108,"categories":109,"keywords":111,"publishedAt":39},"01M6X5MCV74NHW5MEDNHZRF2C8","schema-management","Manage generated processkit schema contracts through deterministic MCP rebuild and inspection workflows.","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Fsrc\u002Fcontext\u002Fskills\u002Fprocesskit\u002Fschema-management\u002FSKILL.md",[110],{"categoryNo":86,"categoryName":87,"taxonomyType":88,"taxonomyTypeDesc":89},[32,112,113,114,115,116,95,33,117,118,97,119,120,121,99,122,123],"schema","schema management","MCP","workflows","validation","generated","rebuild","contracts","wed","deterministic","contract","mode",{"skillNo":125,"name":126,"nameZh":6,"description":127,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":128,"categories":129,"keywords":130,"publishedAt":39},"01M6X5M5G6YJ96AMZGSCZJ1D13","proposition-management","Record claims, risks, beliefs, world facts, WSJF estimates, and assumptions through the Proposition interface.","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Fsrc\u002Fcontext\u002Fskills\u002Fprocesskit\u002Fproposition-management\u002FSKILL.md",[],[32,131,132,92,93,133,95,33,134,135,136,137,99,138,139,140,141,142,143,144],"proposition","proposition management","index","log","world","record","query","creation","event","interface","updates","facts","claims","WSJF",{"skillNo":146,"name":147,"nameZh":6,"description":148,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":149,"categories":150,"keywords":151,"publishedAt":39},"01M6X5KMQ83QN9M6MPWZM7344F","ontology-management","Manage generated v1 ontology entities that do not require a dedicated domain server.","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Fsrc\u002Fcontext\u002Fskills\u002Fprocesskit\u002Fontology-management\u002FSKILL.md",[],[32,98,152,92,95,153,154,117,155,134,97,156,157,99,158,159,139,160,24,161],"ontology management","lifecycle","archive","roadmap","do","domain","iteration","keep","measurement","generic",{"skillNo":163,"name":164,"nameZh":6,"description":165,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":166,"categories":167,"keywords":168,"publishedAt":39},"01M6X5KCY2DN3SM21RERSFNEBT","okf-compatibility","Import, export, and validate conformant Open Knowledge Format bundles.","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Fsrc\u002Fcontext\u002Fskills\u002Fprocesskit\u002Fokf-compatibility\u002FSKILL.md",[],[169,170,171,172,95,173,174,175,33,176,177,178,179],"okf","compatibility","okf compatibility","validate","open","knowledge","format","export","bundles","bundle","import",{"skillNo":181,"name":182,"nameZh":6,"description":183,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":184,"categories":185,"keywords":186,"publishedAt":39},"01M6X5JA8S5PNGJVFW4EQY8T83","capability-management","Manage versioned Capability entities and their governed lifecycle.","https:\u002F\u002Fgithub.com\u002Fprojectious-work\u002Fprocesskit\u002Fblob\u002Fmain\u002Fsrc\u002Fcontext\u002Fskills\u002Fprocesskit\u002Fcapability-management\u002FSKILL.md",[],[32,187,188,92,93,133,95,153,33,96,134,189,97,136,99,159,139,140,190,103],"capability","capability management","queries","changes"]