Flutter平台适配插件flutter_platform_widgets的使用

发布于 1周前 作者 sinazl 来自 Flutter

Flutter平台适配插件flutter_platform_widgets的使用

Flutter是一个用于开发跨平台移动应用的框架,它允许开发者使用一套代码库构建iOS和Android应用。然而,在实际开发中,不同平台有着不同的设计语言(如Material Design for Android和Cupertino for iOS),这可能导致开发者需要为每个平台编写特定的UI代码。flutter_platform_widgets插件旨在简化这一过程,通过提供一组包装器来自动选择适当的平台特定小部件,从而减少冗余代码。

一、简介

Flutter Platform Widgets

  • Pub 上的最新版本:
  • 许可证:

TL;DR;

这是一个包装库,使得更容易针对所选平台的设计语言使用单个组件。

更多信息

对于刚开始使用Flutter构建应用程序的人来说,选择正确的组件非常重要。通常情况下,这会从使用默认外观和感觉为Android设计的Material组件开始。但是当为iOS设计屏幕时,就需要额外努力去适应Cupertino设计语言的一套新组件。该项目最初是一个实验,后来发展成为一个完整的包,支持使用Material和Cupertino设计的组件,以单一平台组件的形式呈现。

如果你想要构建一个具有相似功能的Material和Cupertino风格的应用程序,那么这个包可以为你节省时间和精力。


此包支持稳定的发布版本。测试版通道可能会在有预发布版本时得到支持,请查看更改日志以检查版本兼容性。由于主分支处于快速开发中,所以该包无法支持主通道。如果需要此支持,则最好分叉仓库并在本地引用分叉版本,在那里你可以根据需要进行更改。


二、安装

按照pub.dev上的说明进行安装。

dependencies:
  flutter_platform_widgets: ^latest_version # 替换为最新版本号

然后运行 flutter pub get 或者点击IDE中的“Packages get”。

三、工作原理

不再需要编写条件语句来判断当前平台并返回相应的按钮类型:

if (Platform.isAndroid) {
  return ElevatedButton(onPressed: onPressed, child: child);
} else if (Platform.isIOS) {
  return CupertinoButton.filled(onPressed: onPressed, child: child);
}

而是可以直接使用PlatformElevatedButton,它会根据ThemeData.platform属性自动渲染正确的底层组件:

return PlatformElevatedButton(onPressed: onPressed, child: child);

这样做的好处是减少了代码量,并且使代码更易于维护。

此外,还可以指定任何受支持平台的设计语言,包括但不限于:

  • Android
  • iOS
  • Web
  • MacOS
  • Windows
  • Linux

四、文档

更多关于如何使用的详细信息以及可用组件列表,请参阅官方Wiki

五、示例Demo

下面是一个完整的例子,展示了如何设置一个基本的应用程序,其中包括了主题切换的功能:

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_platform_widgets/flutter_platform_widgets.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatefulWidget {
  @override
  State<MyApp> createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  ThemeMode? themeMode = ThemeMode.light; // 初始亮度模式

  @override
  Widget build(BuildContext context) {
    final materialLightTheme = ThemeData.light();
    final materialDarkTheme = ThemeData.dark();

    const darkDefaultCupertinoTheme =
        CupertinoThemeData(brightness: Brightness.dark);
    final cupertinoDarkTheme = MaterialBasedCupertinoThemeData(
      materialTheme: materialDarkTheme.copyWith(
        cupertinoOverrideTheme: CupertinoThemeData(
          brightness: Brightness.dark,
          barBackgroundColor: darkDefaultCupertinoTheme.barBackgroundColor,
          textTheme: CupertinoTextThemeData(
            primaryColor: Colors.white,
            navActionTextStyle:
                darkDefaultCupertinoTheme.textTheme.navActionTextStyle.copyWith(
              color: const Color(0xF0F9F9F9),
            ),
            navLargeTitleTextStyle: darkDefaultCupertinoTheme
                .textTheme.navLargeTitleTextStyle
                .copyWith(color: const Color(0xF0F9F9F9)),
          ),
        ),
      ),
    );
    final cupertinoLightTheme =
        MaterialBasedCupertinoThemeData(materialTheme: materialLightTheme);

    return PlatformProvider(
      settings: PlatformSettingsData(
        iosUsesMaterialWidgets: true,
        iosUseZeroPaddingForAppbarPlatformIcon: true,
      ),
      builder: (context) => PlatformTheme(
        themeMode: themeMode,
        materialLightTheme: materialLightTheme,
        materialDarkTheme: materialDarkTheme,
        cupertinoLightTheme: cupertinoLightTheme,
        cupertinoDarkTheme: cupertinoDarkTheme,
        matchCupertinoSystemChromeBrightness: true,
        onThemeModeChanged: (themeMode) {
          this.themeMode = themeMode; /* 可以保存到存储 */
        },
        builder: (context) => PlatformApp(
          localizationsDelegates: [
            DefaultMaterialLocalizations.delegate,
            DefaultWidgetsLocalizations.delegate,
            DefaultCupertinoLocalizations.delegate,
          ],
          title: 'Flutter Platform Widgets',
          home: Scaffold(
            appBar: PlatformAppBar(
              title: Text('Flutter Platform Widgets'),
            ),
            body: Center(
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: <Widget>[
                  PlatformElevatedButton(
                    onPressed: () {},
                    child: Text('Press Me'),
                  ),
                  SizedBox(height: 20),
                  PlatformSwitch(
                    value: themeMode == ThemeMode.dark,
                    onChanged: (value) {
                      setState(() {
                        themeMode = value ? ThemeMode.dark : ThemeMode.light;
                      });
                    },
                  ),
                ],
              ),
            ),
          ),
        ),
      ),
    );
  }
}

在这个例子中,我们创建了一个简单的应用界面,包含一个按钮和一个开关。当用户切换开关状态时,应用程序的主题会在浅色模式和深色模式之间切换。同时,所有组件都会根据当前平台自动调整样式,确保用户体验一致。

六、问题与反馈

如果您有任何问题或建议,请直接在GitHub上创建issue

七、许可证

本项目采用MIT许可证,详情请见LICENSE文件。

八、贡献者

感谢所有在过去五年里为此项目做出贡献的人们!

Contributors

contrib.rocks生成。

受到Swav Kulinski(链接)项目的启发。


更多关于Flutter平台适配插件flutter_platform_widgets的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter平台适配插件flutter_platform_widgets的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


当然,以下是如何在Flutter项目中使用flutter_platform_widgets插件来进行平台适配的示例代码。flutter_platform_widgets插件允许你根据运行平台(iOS、Android、Web等)来显示不同的UI组件或样式。

1. 添加依赖

首先,你需要在pubspec.yaml文件中添加flutter_platform_widgets依赖:

dependencies:
  flutter:
    sdk: flutter
  flutter_platform_widgets: ^x.y.z  # 请替换为最新版本号

然后运行flutter pub get来安装依赖。

2. 导入插件

在你的Dart文件中导入flutter_platform_widgets

import 'package:flutter_platform_widgets/flutter_platform_widgets.dart';

3. 使用平台特定的组件

flutter_platform_widgets提供了多种平台特定的组件,例如PlatformAppBarPlatformButtonPlatformCupertinoSwitch等。以下是一些示例代码:

示例:PlatformAppBar

import 'package:flutter/material.dart';
import 'package:flutter_platform_widgets/flutter_platform_widgets.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return PlatformApp(
      material: (context) => MaterialApp(
        home: MyHomePage(),
      ),
      cupertino: (context) => CupertinoApp(
        home: MyHomePage(),
      ),
    );
  }
}

class MyHomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: PlatformAppBar(
        title: Text('Platform App Bar'),
        material: (_, __) => AppBar(
          title: Text('Material App Bar'),
          centerTitle: true,
        ),
        cupertino: (_, __) => CupertinoNavigationBar(
          middle: Text('Cupertino App Bar'),
        ),
      ),
      body: Center(
        child: PlatformButton(
          material: (_, __) => ElevatedButton(
            onPressed: () {},
            child: Text('Material Button'),
          ),
          cupertino: (_, __) => CupertinoButton(
            color: CupertinoColors.activeBlue,
            onPressed: () {},
            child: Text('Cupertino Button'),
          ),
        ),
      ),
    );
  }
}

示例:PlatformCupertinoSwitch

import 'package:flutter/material.dart';
import 'package:flutter_platform_widgets/flutter_platform_widgets.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return PlatformApp(
      material: (context) => MaterialApp(
        home: MyHomePage(),
      ),
      cupertino: (context) => CupertinoApp(
        home: MyHomePage(),
      ),
    );
  }
}

class MyHomePage extends StatefulWidget {
  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  bool isSwitched = false;

  void handleSwitchChange(bool value) {
    setState(() {
      isSwitched = value;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: PlatformCupertinoSwitch(
          value: isSwitched,
          onChanged: handleSwitchChange,
          material: (_, __) => Switch(
            value: isSwitched,
            onChanged: handleSwitchChange,
          ),
        ),
      ),
    );
  }
}

4. 运行应用

完成上述步骤后,你可以运行你的Flutter应用,并根据不同的平台(iOS模拟器、Android模拟器或Web浏览器)查看适配效果。

这些示例展示了如何使用flutter_platform_widgets插件来根据平台显示不同的UI组件。你可以根据需要进一步自定义和扩展这些组件。

回到顶部