--- name: developing-with-flutter description: Flutter SDK for cross-platform development targeting iOS, Android, and Web. Use for widget architecture, state management, platform channels, and multi-platform deployment. --- # Flutter SDK Skill ## Quick Reference Flutter is Google's UI toolkit for building natively compiled applications for mobile (iOS, Android), web, and desktop from a single Dart codebase. --- ## Table of Contents 1. [Critical: Avoiding Interactive Mode](#critical-avoiding-interactive-mode) 2. [Prerequisites](#prerequisites) 3. [CLI Decision Tree](#cli-decision-tree) 4. [Project Structure](#project-structure) 5. [State Management](#state-management) 6. [Widget Patterns](#widget-patterns) 7. [Navigation (GoRouter)](#navigation-gorouter) 8. [Platform-Specific Code](#platform-specific-code) 9. [Web-Specific Considerations](#web-specific-considerations) 10. [Testing](#testing) 11. [Error Handling](#error-handling) 12. [CI/CD Integration](#cicd-integration) 13. [Auto-Detection Triggers](#auto-detection-triggers) 14. [Agent Integration](#agent-integration) 15. [Sources](#sources) --- ## Critical: Avoiding Interactive Mode **Flutter CLI can enter interactive mode which will hang Claude Code.** Always use flags to bypass prompts: | Command | WRONG (Interactive) | CORRECT (Non-Interactive) | |---------|---------------------|---------------------------| | Create project | `flutter create` (prompts) | `flutter create my_app --org com.example` | | Run app | `flutter run` (prompts for device) | `flutter run -d ` | | Build | `flutter build` (may prompt) | `flutter build apk --release` | | Emulators | `flutter emulators --launch` | `flutter emulators --launch ` | **Always include**: - `-d ` for device selection (use `flutter devices` to list) - Explicit build targets (`apk`, `appbundle`, `ios`, `web`) - `--no-pub` when pub get is not needed - `--suppress-analytics` in CI/CD environments **Never use in Claude Code**: - Commands that open GUI (Android Studio, Xcode) - Interactive device selection prompts - Commands without explicit targets --- ## Prerequisites ```bash flutter --version # Expected: Flutter 3.x.x flutter doctor # Check all requirements flutter devices # List available devices flutter emulators # List available emulators ``` --- ## CLI Decision Tree ### Project Setup ``` ├── Create new project ────────────────► flutter create --org ├── Get dependencies ──────────────────► flutter pub get ├── Upgrade dependencies ──────────────► flutter pub upgrade ├── Clean build artifacts ─────────────► flutter clean └── Check project health ──────────────► flutter doctor ``` ### Development ``` ├── Run on device ─────────────────────► flutter run -d ├── Run in release mode ───────────────► flutter run --release -d ├── Attach to running app ─────────────► flutter attach -d └── View logs ─────────────────────────► flutter logs -d ``` ### Building ``` ├── Build Android APK ─────────────────► flutter build apk --release ├── Build Android App Bundle ──────────► flutter build appbundle --release ├── Build iOS ─────────────────────────► flutter build ios --release ├── Build iOS (no codesign) ───────────► flutter build ios --release --no-codesign └── Build Web ─────────────────────────► flutter build web --release ``` ### Testing ``` ├── Run all tests ─────────────────────► flutter test ├── Run specific test file ────────────► flutter test test/widget_test.dart ├── Run with coverage ─────────────────► flutter test --coverage └── Run integration tests ─────────────► flutter test integration_test/ ``` ### Code Quality ``` ├── Analyze code ──────────────────────► flutter analyze ├── Format code ───────────────────────► dart format . └── Fix lint issues ───────────────────► dart fix --apply ``` > **See [REFERENCE.md](REFERENCE.md#complete-cli-reference)** for complete CLI options, flavors, and advanced build configurations. --- ## Project Structure ``` my_app/ ├── lib/ │ ├── main.dart # Entry point │ ├── app.dart # App widget │ ├── features/ # Feature modules │ │ └── auth/ │ │ ├── data/ # Repositories, data sources │ │ ├── domain/ # Entities, use cases │ │ └── presentation/ # Widgets, providers │ ├── core/ # Shared utilities │ └── l10n/ # Localization ├── test/ # Unit and widget tests ├── integration_test/ # Integration tests ├── android/ # Android platform code ├── ios/ # iOS platform code ├── web/ # Web platform code ├── pubspec.yaml # Dependencies └── analysis_options.yaml # Lint rules ``` > **See [REFERENCE.md](REFERENCE.md#project-configuration)** for complete pubspec.yaml and analysis_options.yaml configurations. --- ## State Management ### Riverpod (Recommended) ```dart // Provider definition @riverpod class Counter extends _$Counter { @override int build() => 0; void increment() => state++; void decrement() => state--; } // Usage in widget class CounterWidget extends ConsumerWidget { @override Widget build(BuildContext context, WidgetRef ref) { final count = ref.watch(counterProvider); return Text('Count: $count'); } } ``` ### Provider (Simple apps) ```dart class CartNotifier extends ChangeNotifier { final List _items = []; List get items => List.unmodifiable(_items); void addItem(Item item) { _items.add(item); notifyListeners(); } } // Usage final cart = context.watch(); ``` ### Bloc (Enterprise apps) ```dart // Events and States sealed class AuthEvent {} class LoginRequested extends AuthEvent { final String email, password; LoginRequested(this.email, this.password); } sealed class AuthState {} class AuthLoading extends AuthState {} class AuthSuccess extends AuthState { final User user; AuthSuccess(this.user); } // Bloc class AuthBloc extends Bloc { AuthBloc() : super(AuthInitial()) { on(_onLoginRequested); } } ``` > **See [REFERENCE.md](REFERENCE.md#state-management-deep-dive)** for complete Riverpod architecture, Bloc patterns, and provider types. --- ## Widget Patterns ### StatelessWidget ```dart class UserCard extends StatelessWidget { final User user; final VoidCallback? onTap; const UserCard({required this.user, this.onTap, super.key}); @override Widget build(BuildContext context) { return Card( child: ListTile( leading: CircleAvatar(backgroundImage: NetworkImage(user.avatarUrl)), title: Text(user.name), subtitle: Text(user.email), onTap: onTap, ), ); } } ``` ### StatefulWidget ```dart class SearchField extends StatefulWidget { final ValueChanged onChanged; const SearchField({required this.onChanged, super.key}); @override State createState() => _SearchFieldState(); } class _SearchFieldState extends State { final _controller = TextEditingController(); Timer? _debounce; @override void dispose() { _debounce?.cancel(); _controller.dispose(); super.dispose(); } void _onSearchChanged(String value) { _debounce?.cancel(); _debounce = Timer(const Duration(milliseconds: 300), () { widget.onChanged(value); }); } @override Widget build(BuildContext context) { return TextField(controller: _controller, onChanged: _onSearchChanged); } } ``` > **See [REFERENCE.md](REFERENCE.md#widget-architecture)** for compound widgets, builder patterns, and hook widgets. --- ## Navigation (GoRouter) ```dart final router = GoRouter( initialLocation: '/', routes: [ GoRoute( path: '/', builder: (context, state) => const HomeScreen(), routes: [ GoRoute( path: 'user/:id', builder: (context, state) { final id = state.pathParameters['id']!; return UserScreen(userId: id); }, ), ], ), ], errorBuilder: (context, state) => ErrorScreen(error: state.error), ); // Usage context.go('/user/123'); context.push('/user/123'); context.pop(); ``` > **See [REFERENCE.md](REFERENCE.md#navigation-patterns)** for deep linking, shell routes, and platform-specific configuration. --- ## Platform-Specific Code ### Platform Checks ```dart import 'dart:io' show Platform; import 'package:flutter/foundation.dart' show kIsWeb; Widget build(BuildContext context) { if (kIsWeb) return WebSpecificWidget(); if (Platform.isIOS) return CupertinoWidget(); if (Platform.isAndroid) return MaterialWidget(); return DefaultWidget(); } ``` ### Platform Channels (Native Integration) ```dart class BatteryLevel { static const platform = MethodChannel('com.example.app/battery'); Future getBatteryLevel() async { try { return await platform.invokeMethod('getBatteryLevel'); } on PlatformException catch (e) { throw Exception('Failed: ${e.message}'); } } } ``` > **See [REFERENCE.md](REFERENCE.md#platform-specific-development)** for iOS/Android native code, conditional imports, and event channels. --- ## Web-Specific Considerations ### Build Renderers ```bash flutter build web --web-renderer canvaskit # Better fidelity, larger flutter build web --web-renderer html # Smaller size flutter build web --web-renderer auto # Auto-detect ``` **Best for**: Internal tools, dashboards, PWAs, authenticated apps **Note**: Flutter web renders to canvas - limited SEO by default --- ## Testing ### Widget Tests ```dart void main() { testWidgets('Counter increments', (tester) async { await tester.pumpWidget(const MyApp()); expect(find.text('0'), findsOneWidget); await tester.tap(find.byIcon(Icons.add)); await tester.pump(); expect(find.text('1'), findsOneWidget); }); } ``` ### Golden Tests ```dart testWidgets('Button matches golden', (tester) async { await tester.pumpWidget(MaterialApp(home: MyButton(label: 'Submit'))); await expectLater(find.byType(MyButton), matchesGoldenFile('goldens/my_button.png')); }); // Update: flutter test --update-goldens ``` > **See [REFERENCE.md](REFERENCE.md#testing-strategies)** for integration tests, provider testing, and complete test patterns. --- ## Error Handling | Error | Solution | |-------|----------| | `No connected devices` | Run `flutter devices`, start emulator | | `Gradle build failed` | Run `flutter doctor`, check Android Studio | | `CocoaPods not installed` | `sudo gem install cocoapods` | | `pub get failed` | Check `pubspec.yaml`, run `flutter clean` | ### Debug Commands ```bash flutter run -v # Verbose output flutter doctor -v # Check for issues flutter clean && flutter pub get # Clean rebuild ``` > **See [REFERENCE.md](REFERENCE.md#troubleshooting)** for complete troubleshooting guide and CI/CD issues. --- ## CI/CD Integration ```yaml - uses: subosito/flutter-action@v2 with: flutter-version: "3.24.0" channel: stable cache: true - run: flutter pub get - run: flutter analyze - run: flutter test --coverage - run: flutter build apk --release ``` > **See [REFERENCE.md](REFERENCE.md#cicd-integration)** for complete GitHub Actions workflows and multi-platform builds. --- ## Auto-Detection Triggers This skill auto-loads when Flutter context is detected: **File-based triggers**: - `pubspec.yaml` with `flutter` dependency - `lib/main.dart` present - `.dart` files in project - `android/` and `ios/` directories **Context-based triggers**: - User mentions "Flutter" - User runs flutter CLI commands - Widget development discussions --- ## Agent Integration | Agent | Use Case | |-------|----------| | `mobile-developer` | Primary agent for Flutter development | | `deep-debugger` | Performance profiling, crash analysis | | `code-reviewer` | Dart code review, accessibility audit | | `deployment-orchestrator` | App store submissions | **Handoff to Deep-Debugger**: - Performance profiling needed - Crash analysis required - Memory leak investigation - Platform-specific bugs --- ## Sources - [Flutter CLI Reference](https://docs.flutter.dev/reference/flutter-cli) - [Flutter Documentation](https://docs.flutter.dev) - [Effective Dart](https://dart.dev/effective-dart) - [Flutter State Management](https://docs.flutter.dev/data-and-backend/state-mgmt)