Flutter键盘吸附插件keyboard_sticky的使用

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

Flutter键盘吸附插件keyboard_sticky的使用

keyboard_sticky 是一个允许在软键盘顶部粘贴固定组件的UI组件。当只有软键盘显示且原始组件被覆盖时,粘贴组件会显示出来。如果没有任何软键盘或者原始组件未被覆盖,则粘贴组件不会显示。

功能

  • 仅单个 TextField

    如果设置了 floating 参数为 truefieldBuilder 将用于构建由 builder 使用的 TextField;否则,fieldBuilder 将用于构建由 floatingBuilder 使用的 TextField

    • 原始组件将显示在键盘不可见时。
    • 当键盘可见且原始组件不可见时,浮动组件将显示。

    示例:

    KeyboardSticky.single({
      super.key,
      FocusNode? focusNode,
      TextEditingController? controller,
      FocusNode? floatingFocusNode,
      bool floating = false,
      this.useMaterial = true,
      required KeyboardStickyWrapperBuilder builder,
      required KeyboardStickyWrapperBuilder floatingBuilder,
      required KeyboardStickyFieldBuilder fieldBuilder,
    });
    
  • 两个 TextField

    如果没有提供 floatingBuilderbuilder 将用于构建浮动组件。如果没有提供 floatingFieldBuilderfieldBuilder 将用于构建浮动 TextField

    • 原始和浮动 TextField 应该共享相同的 controller,以便它们可以共享相同的文本值。
    • 然而,两个 TextField 应该有不同的 FocusNode,以便它们可以单独聚焦。

    示例:

    KeyboardSticky.both({
      super.key,
      FocusNode? focusNode,
      TextEditingController? controller,
      FocusNode? floatingFocusNode,
      TextEditingController? floatingController,
      this.useMaterial = true,
      required KeyboardStickyWrapperBuilder builder,
      required KeyboardStickyFieldBuilder fieldBuilder,
      KeyboardStickyWrapperBuilder? floatingBuilder,
      KeyboardStickyFieldBuilder? floatingFieldBuilder,
    })
    
  • 手动控制浮动组件

    KeyboardStickyController 是一个混入类,提供了手动显示/隐藏浮动组件的能力。

    示例:

    abstract mixin class KeyboardStickyController {
      bool get visible; // 是否显示原始组件
      double get keyboardHeight; // 当前键盘高度
      void showFloating(); // 手动显示浮动组件
      void hideFloating(); // 手动隐藏浮动组件
    }
    

示例代码

以下是 main.dart 文件的示例代码:

import 'package:example/both.dart';
import 'package:example/only_floating.dart';
import 'package:example/only_original.dart';
import 'package:example/sticky_dropdown.dart';
import 'package:example/test.dart';
import 'package:flutter/material.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:go_router/go_router.dart';

final navigatorKey = GlobalKey<NavigatorState>();

final router = GoRouter(
  navigatorKey: navigatorKey,
  routes: [
    GoRoute(
      path: "/",
      parentNavigatorKey: navigatorKey,
      builder: (context, state) => const AttachableTextFieldExample(),
    ),
    GoRoute(
      path: "/chat",
      parentNavigatorKey: navigatorKey,
      redirect: (context, state) {
        if (state.pathParameters["partyId"] == null) {
          return "/";
        }
        return null;
      },
      routes: [
        GoRoute(
          path: ":partyId",
          parentNavigatorKey: navigatorKey,
          builder: (_, state) {
            print("Party route with partyId");
            final partyId = state.pathParameters["partyId"];
            return Material(
              child: PartyViewPage(
                partyId: partyId ?? "",
              ),
            );
          },
        ),
      ],
    )
  ],
);

void main() {
  runApp(
    const ScreenUtilInit(
      designSize: Size(428, 926),
      rebuildFactor: RebuildFactors.none,
      minTextAdapt: true,
      splitScreenMode: false,
      child: MyApp(),
    ),
  );
}

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

  [@override](/user/override)
  Widget build(BuildContext context) {
    return MaterialApp.router(
      title: 'Flutter Demo',
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
        useMaterial3: true,
      ),
      builder: EasyLoading.init(),
      routeInformationParser: router.routeInformationParser,
      routerDelegate: router.routerDelegate,
      routeInformationProvider: router.routeInformationProvider,
    );
  }
}

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

  [@override](/user/override)
  Widget build(BuildContext context) {
    return Scaffold(
      resizeToAvoidBottomInset: false,
      appBar: AppBar(
        title: const Text("Keyboard Sticky Example"),
      ),
      body: const Padding(
        padding: EdgeInsets.all(15),
        child: Column(
          children: [
            UnfocusButton(),
            PartyTestButton(),
            Spacer(),
            Text("Text would be sent to the floating widget"),
            SizedBox(height: 5),
            OnlyOriginalExample(),
            SizedBox(height: 20),
            Text("Text would be sent back to the original widget"),
            SizedBox(height: 5),
            OnlyFloatingExample(),
            SizedBox(height: 20),
            Text("Text sync between both fields"),
            SizedBox(height: 5),
            BothFieldsExample(),
            SizedBox(height: 20),
            StickyDropdownExample(),
            SizedBox(height: 20),
            Text("Bottom placeholder"),
          ],
        ),
      ),
    );
  }
}

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

  [@override](/user/override)
  Widget build(BuildContext context) {
    return OutlinedButton(
      onPressed: () {
        context.push("/chat/party");
      },
      child: Text("Test Party"),
    );
  }
}

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

  [@override](/user/override)
  Widget build(BuildContext context) {
    return OutlinedButton(
      onPressed: () {
        FocusScope.of(context).unfocus();
      },
      child: const Text("Unfocus"),
    );
  }
}

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

1 回复

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


当然,以下是如何在Flutter项目中使用keyboard_sticky插件来实现键盘吸附效果的代码示例。keyboard_sticky插件可以帮助你在键盘弹出时,让指定的组件(如输入框下的内容)吸附在键盘上方,从而避免被键盘遮挡。

步骤 1: 添加依赖

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

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

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

步骤 2: 导入插件

在你需要使用keyboard_sticky的Dart文件中导入插件:

import 'package:keyboard_sticky/keyboard_sticky.dart';

步骤 3: 使用KeyboardSticky组件

以下是一个完整的示例,展示如何使用KeyboardSticky组件来实现键盘吸附效果:

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

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('Keyboard Sticky Example'),
        ),
        body: Padding(
          padding: const EdgeInsets.all(16.0),
          child: KeyboardSticky(
            // 设置吸附的视图区域
            containerBuilder: (BuildContext context) {
              return Column(
                crossAxisAlignment: CrossAxisAlignment.start,
                children: [
                  TextField(
                    decoration: InputDecoration(labelText: 'TextField 1'),
                  ),
                  SizedBox(height: 16.0),
                  TextField(
                    decoration: InputDecoration(labelText: 'TextField 2'),
                  ),
                  SizedBox(height: 16.0),
                  // 其他不被吸附的组件可以放在这里
                  Container(
                    decoration: BoxDecoration(
                      border: Border(top: BorderSide(color: Colors.grey, width: 1.0))
                    ),
                    padding: EdgeInsets.symmetric(vertical: 8.0),
                    child: Text(
                      'This is a sticky content below the text fields.',
                      style: TextStyle(color: Colors.grey),
                    ),
                  ),
                ],
              );
            },
            // 吸附的视图内容
            stickyContentBuilder: (BuildContext context) {
              return Column(
                crossAxisAlignment: CrossAxisAlignment.start,
                children: [
                  TextField(
                    decoration: InputDecoration(labelText: 'Sticky TextField'),
                  ),
                ],
              );
            },
            // 可选:设置键盘显示和隐藏时的回调
            onKeyboardVisibleChanged: (bool isVisible) {
              print('Keyboard is ${isVisible ? 'visible' : 'hidden'}');
            },
          ),
        ),
      ),
    );
  }
}

解释

  1. KeyboardSticky 组件包含两个主要的builder参数:

    • containerBuilder:用于构建主要内容区域,这个区域的内容在键盘弹出时可能会被遮挡。
    • stickyContentBuilder:用于构建需要吸附在键盘上方的内容。
  2. TextField 组件用于输入文本,并展示键盘吸附效果。

  3. onKeyboardVisibleChanged 是一个可选的回调,用于在键盘显示或隐藏时执行一些操作。

通过以上步骤,你就可以在Flutter项目中实现键盘吸附效果了。希望这个示例能帮助你更好地理解keyboard_sticky插件的使用。

回到顶部