### flutter install Source: https://docs.flutter.cn/reference/flutter-cli Installs a Flutter application on a connected device. ```APIDOC ## flutter install ### Description Installs a Flutter application on a connected device. ### Command flutter install ### Parameters #### Arguments - **-d ** (string) - Optional - Specifies the device ID on which to install the application. ### Example Usage ```bash flutter install -d ``` ### Output Confirmation of successful application installation. ``` -------------------------------- ### Validate Flutter web setup with flutter devices command Source: https://docs.flutter.cn/platform-integration/web/setup Run the flutter devices command in terminal to verify that Flutter can detect installed web browsers. This command lists all connected devices including Chrome (web) or Edge (web) for web development. Ensure at least one web browser device is shown in the output. ```bash $ flutter devices Found 1 connected devices: Chrome (web) • chrome • web-javascript • Google Chrome ``` -------------------------------- ### Build Flutter plugin example for platform editing Source: https://docs.flutter.cn/packages-and-plugins/developing-packages Commands to initialize and build the example application for different platforms before opening the project in platform-specific IDEs like Xcode, Visual Studio, or VS Code. ```bash # iOS cd hello/example; flutter build ios --no-codesign --config-only # Linux cd hello/example; flutter build linux # macOS cd hello/example; flutter build macos --config-only # Windows cd hello/example; flutter build windows ``` -------------------------------- ### Install Package Dependencies Using flutter pub get Source: https://docs.flutter.cn/packages-and-plugins/using-packages Illustrates the command-line method to install package dependencies after manually adding them to pubspec.yaml. This command fetches and installs all dependencies declared in the pubspec.yaml file. ```bash flutter pub get ``` -------------------------------- ### Create and setup basic Flutter app Source: https://docs.flutter.cn/testing/native-debugging?tab=from-vscode-to-xcode-ios Initialize a new Flutter project and navigate to the project directory. This creates a basic Flutter app structure with dependencies resolved and generates 129 files including the main.dart entry point. ```bash $ flutter create my_app ``` ```bash $ cd my_app ``` -------------------------------- ### Complete Flutter App with Isolate Data Loading Source: https://docs.flutter.cn/flutter-for/xamarin-forms-devs A complete working example of a Flutter application that loads data from a network API using an Isolate. Includes the main app structure, StatefulWidget setup, Isolate communication, and UI rendering with a loading indicator and ListView. Demonstrates best practices for handling asynchronous data loading without blocking the UI. ```dart import 'dart:async'; import 'dart:convert'; import 'dart:isolate'; import 'package:flutter/material.dart'; import 'package:http/http.dart' as http; void main() { runApp(const SampleApp()); } class SampleApp extends StatelessWidget { const SampleApp({super.key}); @override Widget build(BuildContext context) { return const MaterialApp(title: 'Sample App', home: SampleAppPage()); } } class SampleAppPage extends StatefulWidget { const SampleAppPage({super.key}); @override State createState() => _SampleAppPageState(); } class _SampleAppPageState extends State { List> data = []; @override void initState() { super.initState(); loadData(); } bool get showLoadingDialog => data.isEmpty; Future loadData() async { final ReceivePort receivePort = ReceivePort(); await Isolate.spawn(dataLoader, receivePort.sendPort); // The 'echo' isolate sends its SendPort as the first message final SendPort sendPort = await receivePort.first as SendPort; final List> msg = await sendReceive( sendPort, 'https://jsonplaceholder.typicode.com/posts', ); setState(() { data = msg; }); } // The entry point for the isolate static Future dataLoader(SendPort sendPort) async { // Open the ReceivePort for incoming messages. final ReceivePort port = ReceivePort(); // Notify any other isolates what port this isolate listens to. sendPort.send(port.sendPort); await for (final dynamic msg in port) { final String url = msg[0] as String; final SendPort replyTo = msg[1] as SendPort; final Uri dataURL = Uri.parse(url); final http.Response response = await http.get(dataURL); // Lots of JSON to parse replyTo.send(jsonDecode(response.body) as List>); } } Future>> sendReceive(SendPort port, String msg) { final ReceivePort response = ReceivePort(); port.send([msg, response.sendPort]); return response.first as Future>>; } Widget getBody() { if (showLoadingDialog) { return getProgressDialog(); } return getListView(); } Widget getProgressDialog() { return const Center(child: CircularProgressIndicator()); } ListView getListView() { return ListView.builder( itemCount: data.length, itemBuilder: (context, index) { return getRow(index); }, ); } Widget getRow(int index) { return Padding( padding: const EdgeInsets.all(10), child: Text('Row ${data[index]}'), ); } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar(title: const Text('Sample App')), body: getBody(), ); } } ``` -------------------------------- ### Example of Well-Structured LICENSE File with Multiple Packages Source: https://docs.flutter.cn/packages-and-plugins/developing-packages This example illustrates a recommended structure for a `LICENSE` file containing multiple package licenses. Each package's license text is preceded by its name and separated from other licenses by a line of 80 hyphens, ensuring clarity and proper attribution. ```text package_1 -------------------------------------------------------------------------------- package_2 ``` -------------------------------- ### 创建没有动画的菜单 - Flutter Dart Source: https://docs.flutter.cn/cookbook/effects/staggered-menu-animation 定义一个名为 `Menu` 的 stateful widget,该 widget 在固定位置显示列表和按钮。这个菜单包含一个Flutter logo(待实现)、一个列表项(`_menuTitles`)和一个“Get started”按钮。它构建了一个静态的侧边栏菜单结构,作为后续添加交错动画的基础。 ```dart class Menu extends StatefulWidget { const Menu({super.key}); @override State createState() => _MenuState(); } class _MenuState extends State { static const _menuTitles = [ 'Declarative Style', 'Premade Widgets', 'Stateful Hot Reload', 'Native Performance', 'Great Community', ]; @override Widget build(BuildContext context) { return Container( color: Colors.white, child: Stack( fit: StackFit.expand, children: [_buildFlutterLogo(), _buildContent()], ), ); } Widget _buildFlutterLogo() { // TODO: We'll implement this later. return Container(); } Widget _buildContent() { return Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ const SizedBox(height: 16), ..._buildListItems(), const Spacer(), _buildGetStartedButton(), ], ); } List _buildListItems() { final listItems = []; for (var i = 0; i < _menuTitles.length; ++i) { listItems.add( Padding( padding: const EdgeInsets.symmetric(horizontal: 36, vertical: 16), child: Text( _menuTitles[i], textAlign: TextAlign.left, style: const TextStyle(fontSize: 24, fontWeight: FontWeight.w500), ), ), ); } return listItems; } Widget _buildGetStartedButton() { return SizedBox( width: double.infinity, child: Padding( padding: const EdgeInsets.all(24), child: ElevatedButton( style: ElevatedButton.styleFrom( shape: const StadiumBorder(), backgroundColor: Colors.blue, padding: const EdgeInsets.symmetric(horizontal: 48, vertical: 14), ), onPressed: () {}, child: const Text( 'Get Started', style: TextStyle(color: Colors.white, fontSize: 22), ), ), ), ); } } ``` -------------------------------- ### Create and Run a Flutter UWP Application Source: https://docs.flutter.cn/posts/whats-new-in-flutter-2-2 Steps to initialize a new Flutter project with UWP support, install dependencies, and launch the application in the Windows UWP container. ```bash $ flutter create uwp_fun $ cd uwp_fun $ flutter pub get $ flutter run -d winuwp ``` -------------------------------- ### List Installed Java Versions (macOS) Source: https://docs.flutter.cn/release/breaking-changes/android-java-gradle-migration-guide Lists all installed Java Development Kit (JDK) versions and their paths on a macOS system. This command is useful for identifying available Java environments when troubleshooting Java-related build issues or configuring Flutter's JDK path. ```sh /usr/libexec/java_home -V ``` -------------------------------- ### TextInputClient Interface Migration Guide Source: https://docs.flutter.cn/release/breaking-changes/add-showAutocorrectionPromptRect Provides migration guidance for implementing the new showAutocorrectionPromptRect method in TextInputClient implementations. Includes examples for both minimal and full implementations. ```APIDOC ## TextInputClient Interface - Migration Guide ### Overview The TextInputClient interface now includes the showAutocorrectionPromptRect method. Migration requirements depend on your application's platform targets and autocorrect support. ### Migration Scenarios #### Scenario 1: No TextInputClient Implementation **Requirement**: None - No migration needed #### Scenario 2: Non-iOS or No Autocorrect Support **Requirement**: Add empty method implementation ```dart class CustomTextInputClient implements TextInputClient { @override void showAutocorrectionPromptRect(int start, int end) {} } ``` #### Scenario 3: iOS with Autocorrect Support **Requirement**: Implement with state management ```dart class CustomTextInputClient extends State<...> implements TextInputClient { TextRange? _currentPromptRectRange; @override void updateEditingValue(TextEditingValue value) { // Dismiss highlight when text changes if (value.text != _value.text) { setState(() { _currentPromptRectRange = null; }); } } void _handleFocusChanged() { // Dismiss highlight when focus is lost if (!_hasFocus) { setState(() { _currentPromptRectRange = null; }); } } @override void showAutocorrectionPromptRect(int start, int end) { // Update highlight range as requested by iOS setState(() { _currentPromptRectRange = TextRange(start: start, end: end); }); } } ``` ### Implementation Notes - The highlight should be dismissed when text content changes - The highlight should be dismissed when the text input loses focus - iOS does not call this method to dismiss highlights; dismissal is handled by state changes ``` -------------------------------- ### Agree to Xcode Licenses for macOS Development Source: https://docs.flutter.cn/platform-integration/macos/setup This command allows you to review and accept the Xcode software licenses. Accepting these licenses is a mandatory step before you can use Xcode and its associated tools for development. ```bash sudo xcodebuild -license ``` -------------------------------- ### Bundler Installation and Dependency Management in CI Source: https://docs.flutter.cn/deployment/cd Commands for setting up Bundler in a CI environment: first, installing Bundler itself, and then using it to install Fastlane's dependencies as defined in the Gemfile for the respective platform directories. ```bash gem install bundler ``` ```bash bundle install ``` -------------------------------- ### Complete Flutter Animation Example with AnimatedBuilder Source: https://docs.flutter.cn/ui/animations/tutorial Demonstrates a complete animation setup combining LogoWidget, GrowTransition, and LogoApp. The LogoApp is a stateful widget that initializes an AnimationController and Tween in initState(), then builds a GrowTransition with the LogoWidget as a child. This example shows the separation of concerns: widget rendering, animation definition, and transition effects. ```dart void main() => runApp(const LogoApp()); class LogoWidget extends StatelessWidget { const LogoWidget({super.key}); @override Widget build(BuildContext context) { return Container( margin: const EdgeInsets.symmetric(vertical: 10), child: const FlutterLogo(), ); } } class GrowTransition extends StatelessWidget { const GrowTransition({ required this.child, required this.animation, super.key, }); final Widget child; final Animation animation; @override Widget build(BuildContext context) { return Center( child: AnimatedBuilder( animation: animation, builder: (context, child) { return SizedBox( height: animation.value, width: animation.value, child: child, ); }, child: child, ), ); } } class LogoApp extends StatefulWidget { const LogoApp({super.key}); @override State createState() => _LogoAppState(); } class _LogoAppState extends State with SingleTickerProviderStateMixin { late Animation animation; late AnimationController controller; @override void initState() { super.initState(); controller = AnimationController( duration: const Duration(milliseconds: 2000), vsync: this, ); animation = Tween(begin: 0, end: 300).animate(controller); controller.forward(); } @override Widget build(BuildContext context) { return GrowTransition( animation: animation, child: const LogoWidget(), ); } @override void dispose() { controller.dispose(); super.dispose(); } } ``` -------------------------------- ### Implement dynamic input validation and error messages Source: https://docs.flutter.cn/flutter-for/xamarin-forms-devs This example demonstrates how to validate an email address in a TextField and display an error message by updating the state and passing a value to the errorText property of InputDecoration. ```dart import 'package:flutter/material.dart'; void main() { runApp(const SampleApp()); } class SampleApp extends StatelessWidget { const SampleApp({super.key}); @override Widget build(BuildContext context) { return const MaterialApp(title: 'Sample App', home: SampleAppPage()); } } class SampleAppPage extends StatefulWidget { const SampleAppPage({super.key}); @override State createState() => _SampleAppPageState(); } class _SampleAppPageState extends State { String? _errorText; String? _getErrorText() { return _errorText; } bool isEmail(String em) { const String emailRegexp = r'^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|' r'(\" .+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|' r'(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$'; final RegExp regExp = RegExp(emailRegexp); return regExp.hasMatch(em); } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar(title: const Text('Sample App')), body: Center( child: TextField( onSubmitted: (text) { setState(() { if (!isEmail(text)) { _errorText = 'Error: This is not an email'; } else { _errorText = null; } }); }, decoration: InputDecoration( hintText: 'This is a hint', errorText: _getErrorText(), ), ), ), ); } } ``` -------------------------------- ### Enable Windows UWP Desktop Support Source: https://docs.flutter.cn/posts/whats-new-in-flutter-2-2 Commands to switch to the Flutter development channel, upgrade the SDK, and enable the experimental Windows UWP desktop feature. ```bash $ flutter channel dev $ flutter upgrade $ flutter config — enable-windows-uwp-desktop ``` -------------------------------- ### Provider Context Hierarchy Issue - Problem Example in Flutter Source: https://docs.flutter.cn/community/tutorials/state-management-package-getx-provider-analysis Demonstrates the ProviderNotFoundException error that occurs when Provider and Consumer are at the same nesting level. The context from MyApp cannot access Provider nodes positioned below it in the widget tree. ```dart class MyApp extends StatelessWidget { const MyApp({Key? key}) : super(key: key); @override Widget build(BuildContext context) { return Provider( create: (_) => const Count(), child: MaterialApp( home: Scaffold( body: Center(child: Text('${Provider.of(context).count}')), ), ), ); } } ``` -------------------------------- ### Create Flutter Sample Project from Widget Documentation Source: https://docs.flutter.cn/posts/announcing-flutter-1-7-9 This command generates a new Flutter project named 'mysample' that includes the sample code for the 'widgets.Form.1' widget directly from the Flutter documentation. This is useful for developers who want to quickly explore or test specific widget examples. ```bash flutter create --sample=widgets.Form.1 mysample ``` -------------------------------- ### Create Custom Widgets via Composition in Flutter Source: https://docs.flutter.cn/flutter-for/xamarin-forms-devs In Flutter, custom widgets are created by composing smaller widgets rather than inheriting from a base class like VisualElement. This example shows a CustomButton that wraps an ElevatedButton and a Text widget. ```dart class CustomButton extends StatelessWidget { const CustomButton(this.label, {super.key}); final String label; @override Widget build(BuildContext context) { return ElevatedButton(onPressed: () {}, child: Text(label)); } } // Usage @override Widget build(BuildContext context) { return const Center(child: CustomButton('Hello')); } ``` -------------------------------- ### Create a new Flutter project using CLI Source: https://docs.flutter.cn/learn/pathway/tutorial/set-up-state-project Initializes a new Flutter project named 'wikipedia_reader' using the --empty flag to generate a minimal project structure without boilerplate code. ```bash $ flutter create wikipedia_reader --empty ``` -------------------------------- ### Create a new Flutter application Source: https://docs.flutter.cn/cookbook/navigation/set-up-app-links This command initializes a new Flutter project with the specified name, creating the necessary directory structure and basic files for a Flutter application. ```bash flutter create deeplink_cookbook ``` -------------------------------- ### Implement HTTP GET and PUT requests in a Flutter application Source: https://docs.flutter.cn/cookbook/networking/update-data This Dart snippet provides a complete Flutter application demonstrating how to fetch and update data from a REST API. It defines an 'Album' data model, includes 'fetchAlbum' for GET requests and 'updateAlbum' for PUT requests using the 'http' package, and integrates these functionalities into a Flutter UI with a 'FutureBuilder' to display data and allow user interaction for updates. ```dart import 'dart:async'; import 'dart:convert'; import 'package:flutter/material.dart'; import 'package:http/http.dart' as http; Future fetchAlbum() async { final response = await http.get( Uri.parse('https://jsonplaceholder.typicode.com/albums/1'), ); if (response.statusCode == 200) { // If the server did return a 200 OK response, // then parse the JSON. return Album.fromJson(jsonDecode(response.body) as Map); } else { // If the server did not return a 200 OK response, // then throw an exception. throw Exception('Failed to load album'); } } Future updateAlbum(String title) async { final response = await http.put( Uri.parse('https://jsonplaceholder.typicode.com/albums/1'), headers: { 'Content-Type': 'application/json; charset=UTF-8', }, body: jsonEncode({'title': title}), ); if (response.statusCode == 200) { // If the server did return a 200 OK response, // then parse the JSON. return Album.fromJson(jsonDecode(response.body) as Map); } else { // If the server did not return a 200 OK response, // then throw an exception. throw Exception('Failed to update album.'); } } class Album { final int id; final String title; const Album({required this.id, required this.title}); factory Album.fromJson(Map json) { return switch (json) { {'id': int id, 'title': String title} => Album(id: id, title: title), _ => throw const FormatException('Failed to load album.'), }; } } void main() { runApp(const MyApp()); } class MyApp extends StatefulWidget { const MyApp({super.key}); @override State createState() { return _MyAppState(); } } class _MyAppState extends State { final TextEditingController _controller = TextEditingController(); late Future _futureAlbum; @override void initState() { super.initState(); _futureAlbum = fetchAlbum(); } @override Widget build(BuildContext context) { return MaterialApp( title: 'Update Data Example', theme: ThemeData( colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple), ), home: Scaffold( appBar: AppBar(title: const Text('Update Data Example')), body: Container( alignment: Alignment.center, padding: const EdgeInsets.all(8), child: FutureBuilder( future: _futureAlbum, builder: (context, snapshot) { if (snapshot.connectionState == ConnectionState.done) { if (snapshot.hasData) { return Column( mainAxisAlignment: MainAxisAlignment.center, children: [ Text(snapshot.data!.title), TextField( controller: _controller, decoration: const InputDecoration( hintText: 'Enter Title', ), ), ElevatedButton( onPressed: () { setState(() { _futureAlbum = updateAlbum(_controller.text); }); }, child: const Text('Update Data'), ), ], ); } else if (snapshot.hasError) { return Text('${snapshot.error}'); } } return const CircularProgressIndicator(); }, ), ), ), ); } } ``` -------------------------------- ### Add Hint Text to Flutter TextField Source: https://docs.flutter.cn/flutter-for/android-devs This example shows how to add a 'hint' or placeholder text to a `TextField` widget in Flutter. By providing an `InputDecoration` object to the `decoration` property of the `TextField`, you can set the `hintText` to guide users on the expected input. ```dart Center( child: TextField(decoration: InputDecoration(hintText: 'This is a hint')), ) ``` -------------------------------- ### Initialize and Inject Repositories in Flutter main() Source: https://docs.flutter.cn/app-architecture/design-patterns/key-value-data Demonstrates how to instantiate services and repositories at the application root and pass them as constructor arguments to the main app widget. ```dart void main() { // ··· runApp( MainApp( themeRepository: ThemeRepository(SharedPreferencesService()), // ··· ), ); } ``` -------------------------------- ### Implement Fade Transition Animation in Flutter Source: https://docs.flutter.cn/flutter-for/xamarin-forms-devs This Flutter example illustrates how to create a fade transition for a widget using an AnimationController and FadeTransition. It sets up an animation controller with a TickerProviderStateMixin, defines a CurvedAnimation for non-linear interpolation, and applies it to a FlutterLogo widget. The animation is triggered by a FloatingActionButton. ```dart import 'package:flutter/material.dart'; void main() { runApp(const FadeAppTest()); } class FadeAppTest extends StatelessWidget { /// This widget is the root of your application. const FadeAppTest({super.key}); @override Widget build(BuildContext context) { return const MaterialApp( title: 'Fade Demo', home: MyFadeTest(title: 'Fade Demo'), ); } } class MyFadeTest extends StatefulWidget { const MyFadeTest({super.key, required this.title}); final String title; @override State createState() => _MyFadeTest(); } class _MyFadeTest extends State with TickerProviderStateMixin { late final AnimationController controller; late final CurvedAnimation curve; @override void initState() { super.initState(); controller = AnimationController( duration: const Duration(milliseconds: 2000), vsync: this, ); curve = CurvedAnimation(parent: controller, curve: Curves.easeIn); } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar(title: Text(widget.title)), body: Center( child: FadeTransition( opacity: curve, child: const FlutterLogo(size: 100), ), ), floatingActionButton: FloatingActionButton( onPressed: () { controller.forward(); }, tooltip: 'Fade', child: const Icon(Icons.brush), ), ); } } ``` -------------------------------- ### Alternative Valid LICENSE File Structure for Shared Licenses Source: https://docs.flutter.cn/packages-and-plugins/developing-packages This example shows another acceptable format for a `LICENSE` file, particularly useful when multiple packages share the same license text. Package names are listed before the license content, and distinct license blocks are separated by a line of 80 hyphens. ```text package_1 -------------------------------------------------------------------------------- package_1 package_2 ``` -------------------------------- ### Initialize Database and Inject Dependencies in Main Source: https://docs.flutter.cn/app-architecture/design-patterns/sql Configures the DatabaseService for different platforms (Mobile vs Desktop) and injects it into the TodoRepository during the application startup. ```dart void main() { late DatabaseService databaseService; if (kIsWeb) { throw UnsupportedError('Platform not supported'); } else if (Platform.isLinux || Platform.isWindows || Platform.isMacOS) { // Initialize FFI SQLite sqfliteFfiInit(); databaseService = DatabaseService(databaseFactory: databaseFactoryFfi); } else { // Use default native SQLite databaseService = DatabaseService(databaseFactory: databaseFactory); } runApp( MainApp( todoRepository: TodoRepository(database: databaseService), ), ); } ``` -------------------------------- ### Creating a Custom Page Type in Flutter Navigator 2.0 Source: https://docs.flutter.cn/community/tutorials/understanding-navigator-v2 This example demonstrates how to create a custom `Page` type by extending the `Page` class. By overriding the `createRoute()` method, developers can define how their custom page generates a `Route` instance, such as a `MaterialPageRoute`. ```dart class MyPage extends Page { final Veggie veggie; MyPage({ this.veggie, }) : super(key: ValueKey(veggie)); Route createRoute(BuildContext context) { return MaterialPageRoute( settings: this, builder: (BuildContext context) { return VeggieDetailsScreen(veggie: veggie); }, ); } } ``` -------------------------------- ### Conditional Page Popping in Flutter Navigator Source: https://docs.flutter.cn/community/tutorials/understanding-navigator-v2 This example illustrates how to conditionally prevent a page from being popped by returning `false` from the `onPopPage` callback. This gives developers fine-grained control over navigation flow, allowing them to implement custom logic before a page is dismissed. ```dart bool _onPopPage(Route route, dynamic result) { if (...) { return false; } setState(() => pages.remove(route.settings)); return route.didPop(result); } ``` -------------------------------- ### Add Package Dependency Using flutter pub add Command Source: https://docs.flutter.cn/packages-and-plugins/using-packages Demonstrates how to add a package dependency to a Flutter app using the flutter pub add command. This method automatically updates the pubspec.yaml file and installs the package. The example shows adding the css_colors package. ```bash flutter pub add css_colors ``` -------------------------------- ### Generate API Documentation for Flutter Packages Source: https://docs.flutter.cn/packages-and-plugins/developing-packages These commands demonstrate how to use the `dart doc` tool, included with the Flutter SDK, to generate API documentation for a Dart package. After setting the `FLUTTER_ROOT` environment variable, these commands execute `dart doc` to produce comprehensive documentation for public APIs, suitable for publishing to `pub.dev/documentation` or for local review. ```bash $FLUTTER_ROOT/bin/cache/dart-sdk/bin/dart doc # 适用于 macOS 或 Linux 操作系统 ``` ```batch %FLUTTER_ROOT%\bin\cache\dart-sdk\bin\dart doc # 适用于 Windows 操作系统 ``` -------------------------------- ### Create a New Flutter FFI Package Project Source: https://docs.flutter.cn/packages-and-plugins/developing-packages This command demonstrates how to initialize a new Flutter FFI (Foreign Function Interface) package project. Using `flutter create --template=package_ffi` generates the basic directory structure and files required for a package that interacts with native APIs via Dart's FFI. ```bash $ flutter create --template=package_ffi hello ``` -------------------------------- ### Implement Double Tap Gesture for Rotation in Flutter Source: https://docs.flutter.cn/flutter-for/xamarin-forms-devs This Flutter example demonstrates how to use a `GestureDetector` to respond to a double-tap event. It animates a `FlutterLogo` to rotate forward or reverse based on the double-tap, showcasing basic gesture handling and animation with `AnimationController` and `RotationTransition` within a `StatefulWidget`. ```dart class RotatingFlutterDetector extends StatefulWidget { const RotatingFlutterDetector({super.key}); @override State createState() => _RotatingFlutterDetectorState(); } class _RotatingFlutterDetectorState extends State with SingleTickerProviderStateMixin { late final AnimationController controller; late final CurvedAnimation curve; @override void initState() { super.initState(); controller = AnimationController( duration: const Duration(milliseconds: 2000), vsync: this, ); curve = CurvedAnimation(parent: controller, curve: Curves.easeIn); } @override Widget build(BuildContext context) { return Scaffold( body: Center( child: GestureDetector( onDoubleTap: () { if (controller.isCompleted) { controller.reverse(); } else { controller.forward(); } }, child: RotationTransition( turns: curve, child: const FlutterLogo(size: 200), ), ), ), ); } } ``` -------------------------------- ### Implement State with setState() Method Source: https://docs.flutter.cn/flutter-for/xamarin-forms-devs Demonstrates implementing a State class for a stateful widget with state management using setState(). The example shows a counter that increments when a button is pressed, triggering a rebuild of the affected widget tree. setState() should only be called when necessary to avoid performance issues. ```dart class _MyHomePageState extends State { int _counter = 0; void _incrementCounter() { setState(() { _counter++; }); } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( title: Text(widget.title), ), body: Center( child: Column( mainAxisAlignment: MainAxisAlignment.center, children: [ const Text('You have pushed the button this many times:'), Text( '$_counter', style: Theme.of(context).textTheme.headlineMedium, ), ], ), ), floatingActionButton: FloatingActionButton( onPressed: _incrementCounter, tooltip: 'Increment', child: const Icon(Icons.add), ), ); } } ``` -------------------------------- ### Check Flutter macOS Development Setup Issues Source: https://docs.flutter.cn/platform-integration/macos/setup Run this command to perform a comprehensive check of your Flutter development environment for macOS. It identifies any missing dependencies, configuration issues, or potential problems that might hinder Flutter app development. ```bash flutter doctor -v ```