likes
comments
collection
share

flutter + curved_navigation_bar (底部导航栏)

作者站长头像
站长
· 阅读数 29

初始化的底部导航栏没有什么特色,项目开发又比较着急,因此我从pub.dev中找到了一个简单、动效还比较好看的底部导航栏接入,它就是 curved_navigation_bar,具体效果可查看下图,本文简单介绍一下该插件的接入方式,十分简单方便。

官方插件地址:pub.dev/packages/cu…

flutter + curved_navigation_bar (底部导航栏)

插件接入

大家按照官方文档去接入即可,虽然插件中代码最后一次更新是2年前,但是不影响最新版本的使用

// 命令行运行
flutter pub add curved_navigation_bar
// 或者在pubspec.yaml文件中添加
curved_navigation_bar: ^1.0.3

插件使用

底部bar的插件使用还是非常简单的,官方的例子也十分简洁明了,我这里使用了getx作为项目的底部框架,因此我主要介绍一下在getx中如何导入此插件

1. 创建数据列表

做简单事例,我创建了如下3个页面

  1. WebviewPage (H5交互的webview页面)
  2. DownloadPage (之前文档中创建的下载页面)
  3. UserPage (用户页面)

2. 实现角标和页面跳转绑定

controller.dart的代码:

// 创建类型MainTabModel
class MainTabModel {
  late String tabName;
  late String tabImg;
  late String tabImgActivated;
  late bool isDefault;

  MainTabModel(
      {required this.tabName,
      required this.tabImg,
      required this.tabImgActivated,
      required this.isDefault});

  MainTabModel.fromJson(Map<String, dynamic> json) {
    tabName = json['tabName'];
    tabImg = json['tabImg'];
    tabImgActivated = json['tabImgActivated'];
    isDefault = json['isDefault'];
  }

  Map<String, dynamic> toJson() {
    final Map<String, dynamic> data = <String, dynamic>{};
    data['tabName'] = tabName;
    data['tabImg'] = tabImg;
    data['tabImgActivated'] = tabImgActivated;
    data['isDefault'] = isDefault;
    return data;
  }
}

// main的controller中代码:

class MainController extends GetxController {
  MainController();
  // 创建页面controller,控制页面显示
  final PageController pageController = PageController();

  
  int currentIndex = 0;

  
  List<Widget> pages = <Widget>[
    const WebviewPage(),
    const DownloadPage(),
    const UserPage(),
  ];

  // 填充页面角标变化数据
  List<MainTabModel> mainTabs = <MainTabModel>[
    MainTabModel(
        tabName: "webview",
        tabImg:
            'https://miaohuapp-web.oss-cn-hangzhou.aliyuncs.com/beta/resources/main_tab/img/1688549054466833616.png',
        tabImgActivated:
            'https://miaohuapp-web.oss-cn-hangzhou.aliyuncs.com/beta/resources/main_tab/img_activated/1688549051061152900.png',
        isDefault: false),
    MainTabModel(
        tabName: "下载",
        tabImg:
            'https://miaohuapp-web.oss-cn-hangzhou.aliyuncs.com/beta/resources/main_tab/img/1688549041307537463.png',
        tabImgActivated:
            'https://miaohuapp-web.oss-cn-hangzhou.aliyuncs.com/beta/resources/main_tab/img_activated/1688549034218176064.png',
        isDefault: true),
    MainTabModel(
        tabName: "我",
        tabImg:
            'https://miaohuapp-web.oss-cn-hangzhou.aliyuncs.com/beta/resources/main_tab/img/1688549085949980932.png',
        tabImgActivated:
            'https://miaohuapp-web.oss-cn-hangzhou.aliyuncs.com/beta/resources/main_tab/img_activated/1688549082947472903.png',
        isDefault: false),
  ];

  void onTap() {}

  @override
  void onReady() {
    //
    super.onReady();
  }

  @override
  void onClose() {
    //
    super.onClose();
  }

  // 导航栏切换
  void onIndexChanged(int index) {
    currentIndex = index;
    update(["main"]);
  }
  // 点击角标跳转页面
  void setCurrentIndex(index) {
    currentIndex = index;
    pageController.jumpToPage(index);
    update(["main"]);
  }
}

view.dart 中代码

class MainPage extends StatefulWidget {
  const MainPage({super.key});

  @override
  State<MainPage> createState() => _MainPageState();
}

class _MainPageState extends State<MainPage>
    with AutomaticKeepAliveClientMixin {
  @override
  bool get wantKeepAlive => true;

  @override
  Widget build(BuildContext context) {
    super.build(context);
    return const _MainViewGetX();
  }
}

// 上述可忽略,目的是为了缓存页面不被销毁

class _MainViewGetX extends GetView<MainController> {
  const _MainViewGetX({super.key});

  // 主视图
  Widget _buildView() {
    return Scaffold(
      extendBody: true,
      resizeToAvoidBottomInset: false,
      // 内容页
      // body: DownloadPage(),
      body: PageView(
        physics: const NeverScrollableScrollPhysics(),
        controller: controller.pageController,
        onPageChanged: controller.onIndexChanged,
        children: controller.pages,
      ),
      // 在底部bar中添加组件,执行各项参数
      bottomNavigationBar: CurvedNavigationBar(
          onTap: (index) {
            controller.setCurrentIndex(index);
          },
          letIndexChange: (index) => true,
          color: const Color(0xFFF2FAFC),
          buttonBackgroundColor: const Color(0xFFF2FAFC),
          backgroundColor: Colors.transparent,
          animationCurve: Curves.easeInOut,
          animationDuration: const Duration(milliseconds: 500),
          height: 60,
          items: _randerItem()),
    );
  }

  List<Widget> _randerItem() {
    List<Widget> list = [];
    for (var i = 0; i < controller.mainTabs.length; i++) {
      MainTabModel info = controller.mainTabs[i];
      list.add(Stack(
        clipBehavior: Clip.none,
        children: [
          ImageWidget.url(
            controller.currentIndex == i ? info.tabImgActivated : info.tabImg,
            width: 30,
            height: 30,
            fit: BoxFit.cover,
          ),
        ],
      ));
    }
    return list;
  }

  @override
  Widget build(BuildContext context) {
    return GetBuilder<MainController>(
      // init: Get.find<MainController>(),
      id: "main",
      builder: (_) => _buildView(),
    );
  }
}

如上,只需要简单的引入便可以获得一个动效还不错的底部bar效果。

flutter + curved_navigation_bar (底部导航栏)

转载自:https://juejin.cn/post/7356237910364078089
评论
请登录