Flutter实用工具插件mabe_utils的使用

Flutter实用工具插件mabe_utils的使用

安装 💻

要开始使用Mabe Utils,您必须在机器上安装Flutter SDK。

通过以下命令安装:

dart pub add mabe_utils

Widgets

您可以查看example文件夹来了解如何使用这些小部件。

  • ReactOnTap

    • 支持缩放
    • 支持透明度(待实现)
  • Disabled

    • 将子组件标记为禁用,将其不透明度减半并忽略指针。
  • KeyboardHeightProvider

    • 当添加到小部件树时,跟踪键盘高度,并通过context.maxKeyboardHeightcontext.keyboardHeight提供这些值。
  • LoadingManager

    • 在加载时在所有子小部件树顶部添加覆盖层。允许添加加载任务。
  • AlertManager

    • 提供功能以在子小部件树上方添加或删除警报。使用方式类似于context.alert(msg: msg)

Types

以下是定义的类型:

/// 字符串键和字符串值的映射
typedef StringMap = Map<String, String>;

/// 字符串键和动态值的映射
typedef JSON = Map<String, dynamic>;

/// 返回Future的VoidCallback
typedef FutureVoidCallback = Future<void> Function();

/// 接受int参数的回调
typedef IntCallback = void Function(int);

/// 接受String参数的回调
typedef StringCallback = void Function(String value);

/// 接受BuildContext参数的回调
typedef VoidContextCallback = void Function(BuildContext context);

/// 底部弹出窗口构建器
typedef BottomSheetBuilder = Future<T?> Function<T>(Widget child);

Extensions

扩展包括对迭代器和列表的操作。

/// 移除空值
List<T> removeNull()

/// 如果条件为真则反转
List<T> reverseIf(bool b);

/// 返回值之后的下一个元素
T after(T value);

/// 使用分隔符分割列表
List<T> separateBy(T separator, {bool wrap = false});

/// 括号括起来
Iterable<T> hugBy(T hugger);

/// 映射函数
Iterable<S> indexedMap<S>(S Function(T item, int index) map);

/// 如果不存在则添加
Iterable<T> putIfAbsent(T value, {EqualityBuilder<T>? equalityBuilder});

/// 切换元素
List<T> toggle(T value);

/// 检查是否存在指定类型的元素
bool anyType<S extends T>();

/// 随机提取一个元素
T random();

/// 随机提取多个元素
List<T> randomSublist(int count);

/// 返回不是指定类型的元素
List<T> whereTypeNot<S extends T>();

/// 返回指定类型的元素
List<T> whereTypes<S extends T, R extends T>();

/// 返回满足测试的第一个元素,如果没有返回null
T? firstWhereOrNull(bool Function(T element) test);

/// 获取最后一个元素,如果为空返回null
T? get lastOrNull;

/// 获取第一个元素,如果为空返回null
T? get firstOrNull;

/// 按键函数分组
Map<K, List<T>> groupBy<K>(K Function(T) keyFunction);

/// 循环取模
T loop(int index);

/// 返回索引为i的元素,如果不存在返回null
T? elementAtOrNull(int i);

/// 返回长度为length的连续切片
Iterable<List<T>> slices(int length);

Context

提供了一些与上下文相关的扩展方法。

/// 等同于`Navigator.of(context)`
NavigatorState get navigator => Navigator.of(this);

/// 等同于`MediaQuery.sizeOf(context)`
Size get screen => MediaQuery.sizeOf(this);

/// 等同于`MediaQuery.of(context)`
MediaQueryData get mediaQuery => MediaQuery.of(this);

/// 返回最近的MediaQuery的填充
EdgeInsets get padding => MediaQuery.paddingOf(this);

/// 等同于`Theme.of(context)`
ThemeData get theme => Theme.of(this);

/// 返回基于屏幕设备大小的当前布局断点
LayoutBreakpoint get breakpoint;

/// 返回是否为移动设备
bool get isMobile;

/// 返回是否为平板设备
bool get isTablet;

/// 返回是否为桌面设备
bool get isDesktop;

/// 返回最大键盘高度变化的通知器
ValueNotifier<double> get maxKeyboardHeight;

/// 返回键盘高度变化的通知器
ValueNotifier<double> get keyboardHeight;

/// 返回最近的KeyboardHeightProvider,如果没有返回null
KeyboardHeightProviderState? get maybeKeyboardHeightProvider;

// * 管理器
/// 添加一个加载层
void showLoading({required String tag, String? message});

/// 移除加载任务
void hideLoading({required String tag});

/// 添加一个新的警告
void alert({
  required String msg,
  AlertType? type,
  String? id,
  Duration? duration,
});

/// 显示对话框并处理相应的动作
Future<AppDialogAction> popup(
  Widget dialog, {
  Color? barrierColor,
  bool? isDismissable,
});

/// 显示底部弹出窗口
Future<T?> bottomsheet<T>(Widget child, {Color? barrierColor});

GlobalKey

提供了全局键的相关扩展方法。

/// 返回与此键关联的部件的全局偏移量
Offset? get offset;

/// 返回与此键关联的部件的大小
Size? get size;

/// 返回基于全局偏移量和其大小的此部件的Rect
Rect? get rect;

String

提供了字符串操作的扩展方法。

/// 返回颜色
Color get color;

/// 返回每个单词的首字母
String get initials;

/// 返回首字母大写的字符串
String get capitalized;

/// 将驼峰命名转换为句子格式
/// 例如: camelToSentence -> Camel To Sentence
String get camelCaseToSentenceCase;

示例代码

以下是example文件夹中的示例代码,演示了如何使用mabe_utils

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

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

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  [@override](/user/override)
  Widget build(BuildContext context) {
    final theme = ThemeData(
      colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
      useMaterial3: true,
    );
    return MaterialApp(
      title: 'Mabe Utils Demo',
      theme: theme,
      builder: (context, child) => DefaultTextStyle(
        style: theme.textTheme.bodyMedium!,
        child: KeyboardHeightProvider(
          child: LoaderManager(
            loadingOverlay: (context) => const LoadingOverlay(),
            child: AlertManager(
              child: child!,
              alertBuilder: (alert) => Alert(data: alert),
            ),
          ),
        ),
      ),
      home: const HomePage(),
    );
  }
}

class HomePage extends StatelessWidget {
  const HomePage({super.key});

  [@override](/user/override)
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Mabe Utils Example'),
        backgroundColor: Colors.transparent,
        elevation: 0.0,
      ),
      backgroundColor: Colors.blueGrey.shade50,
      body: Padding(
        padding: const EdgeInsets.symmetric(horizontal: 16.0),
        child: ListView(
          children: [
            /// 访问键盘高度
            ValueListenableBuilder(
              valueListenable: context.keyboardHeight,
              builder: (context, height, _) => Container(
                padding: const EdgeInsets.symmetric(vertical: 16),
                color: Colors.green.shade50,
                alignment: Alignment.center,
                child: Text.rich(
                  TextSpan(
                    children: [
                      const TextSpan(text: 'Current Keyboard Height: '),
                      TextSpan(
                        text: height.toString(),
                        style: context.theme.textTheme.bodyMedium?.copyWith(
                          fontWeight: FontWeight.bold,
                          color: Colors.green.shade700,
                        ),
                      ),
                    ],
                  ),
                  style: context.theme.textTheme.bodyMedium?.copyWith(
                    color: Colors.green.shade700,
                  ),
                ),
              ),
            ),
            ValueListenableBuilder(
              valueListenable: context.maxKeyboardHeight,
              builder: (context, height, _) => Container(
                color: Colors.orange.shade50,
                padding: const EdgeInsets.symmetric(vertical: 16),
                alignment: Alignment.center,
                child: Text.rich(
                  TextSpan(
                    children: [
                      const TextSpan(text: 'Max Keyboard Height: '),
                      TextSpan(
                        text: height.toString(),
                        style: context.theme.textTheme.bodyMedium?.copyWith(
                          fontWeight: FontWeight.bold,
                          color: Colors.orange.shade700,
                        ),
                      ),
                    ],
                  ),
                  style: context.theme.textTheme.bodyMedium?.copyWith(
                    color: Colors.orange.shade700,
                  ),
                ),
              ),
            ),
            const TextField(),

            /// 禁用小部件
            Disabled(
              reason: 'Service is not available',
              child: ElevatedButton(
                onPressed: () {},
                child: const Text('Disabled Button'),
              ),
            ),

            /// 加载小部件
            ElevatedButton(
              onPressed: () async {
                final hideLoading = context.hideLoading;

                context.showLoading(tag: kLoadingTask);
                await Future.delayed(const Duration(seconds: 3));
                hideLoading(tag: kLoadingTask);
              },
              child: const Text('Show Loading'),
            ),
          ].gap(20),
        ),
      ),
    );
  }
}

class Alert extends StatelessWidget {
  const Alert({
    super.key,
    required this.data,
  });

  final AlertData data;

  [@override](/user/override)
  Widget build(BuildContext context) {
    return ReactOnTap(
      onTap: () {
        AlertManager.of(context).dismiss();
      },
      child: Container(
        margin: const EdgeInsets.symmetric(vertical: 8, horizontal: 24),
        decoration: BoxDecoration(
          color: switch (data.type) {
            _ => Colors.blue.shade100,
          },
          borderRadius: BorderRadius.circular(16),
        ),
        padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 16),
        child: Row(
          children: [
            Icon(switch (data.type) {
              AlertType.success => Icons.check_circle_rounded,
              _ => Icons.info,
            }),
            Expanded(child: Text(data.message)),
          ].gap(16),
        ),
      ),
    );
  }
}

const kLoadingTask = 'image-downloading';

class LoadingOverlay extends StatelessWidget {
  const LoadingOverlay({super.key});

  [@override](/user/override)
  Widget build(BuildContext context) {
    return Container(
      color: Colors.blue.withOpacity(.5),
      alignment: Alignment.center,
      child: const Text('Loading for 3 seconds... '),
    );
  }
}

更多关于Flutter实用工具插件mabe_utils的使用的实战教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

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


当然,mabe_utils 是一个实用的 Flutter 插件,提供了一系列便捷的工具函数,可以帮助开发者简化一些常见的开发任务。下面是一些关于如何使用 mabe_utils 插件的代码示例。

首先,确保在你的 pubspec.yaml 文件中添加 mabe_utils 依赖:

dependencies:
  flutter:
    sdk: flutter
  mabe_utils: ^最新版本号  # 替换为最新的版本号

然后运行 flutter pub get 来获取依赖。

示例代码

1. 字符串工具函数

mabe_utils 提供了一些字符串处理函数,比如判断字符串是否为空或仅包含空白字符。

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

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('mabe_utils Demo'),
        ),
        body: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              Text(
                'Is null or empty: ${StringUtils.isNullOrEmpty(" ")}',
              ),
              Text(
                'Is null, empty, or whitespace: ${StringUtils.isNullOrEmptyOrWhitespace(" ")}',
              ),
            ],
          ),
        ),
      ),
    );
  }
}

2. 日期时间工具函数

mabe_utils 还提供了日期时间的处理函数,比如格式化日期时间。

import 'package:flutter/material.dart';
import 'package:mabe_utils/mabe_utils.dart';
import 'package:intl/intl.dart';

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    DateTime now = DateTime.now();
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('mabe_utils Demo'),
        ),
        body: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              Text(
                'Formatted Date: ${DateTimeUtils.formatDateTime(now, DateFormat("yyyy-MM-dd HH:mm:ss"))}',
              ),
            ],
          ),
        ),
      ),
    );
  }
}

3. 屏幕工具函数

mabe_utils 提供了获取屏幕宽高和密度的函数。

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

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('mabe_utils Demo'),
        ),
        body: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              Text(
                'Screen Width: ${ScreenUtils.screenWidth}',
              ),
              Text(
                'Screen Height: ${ScreenUtils.screenHeight}',
              ),
              Text(
                'Screen Density: ${ScreenUtils.screenDensity}',
              ),
            ],
          ),
        ),
      ),
    );
  }
}

注意事项

  • 请确保你使用的 mabe_utils 版本是最新的,因为插件的 API 可能会随版本更新而发生变化。
  • 在实际项目中,根据需求选择性地使用这些工具函数,避免不必要的依赖。

这些示例展示了如何使用 mabe_utils 插件中的一些常用工具函数。根据项目的具体需求,你可以进一步探索和使用更多功能。

回到顶部