Bootstrap

2025跨平台Flutter3.27+Dart3+Getx仿携程/飞猪app旅游酒店预订系统

Flutter3-weTrip自研仿携程旅行酒店预订app应用。

2025原创自研新作flutter3.27+dart3.6+getx+flutter_datepicker实战仿携程/同程/飞猪旅行app酒店客房查询预订系统。实现首页、酒店预订、列表/详情、动态、订单、消息聊天、我的等模块。

在这里插入图片描述
在这里插入图片描述

使用技术

  • 编码工具:vscode
  • 技术框架:flutter3.27.1+dart3.6.0
  • 状态管理:get: ^4.6.6
  • 缓存服务:get_storage: ^2.1.1
  • 轮播图组件:card_swiper^3.0.1
  • 日期区间插件:syncfusion_flutter_datepicker^28.2.5
  • toast提示插件:shirne_dialog^4.8.3
  • 瀑布流组件:flutter_staggered_grid_view^0.7.0
  • 滚动定位组件:scrollable_positioned_list^0.3.8

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

预订模块包含了热门城市/位置品牌选择、入住离店日期区间选择、价格/星级筛选等功能。

在这里插入图片描述

项目结构目录

使用vscode编辑器开发,基于最新版跨平台框架flutter3.27构建项目模板。

在这里插入图片描述
在这里插入图片描述

目前flutter3-trip项目已经同步到我的原创作品店,感兴趣的可以去看看。

原创flutter3.27仿携程旅行酒店客房预订app应用

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
分享几个flutter3.x实战项目案例。

原创flutter3.27实战抖音app商城|flutter3.x+getX短视频+直播+聊天实例
基于Flutter3+bitsdojo_window+Getx桌面端仿微信EXE
基于flutter3.x+dart3聊天实例|flutter3仿微信App界面

flutter3主入口文件

import 'dart:io';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:get_storage/get_storage.dart';
import 'package:intl/date_symbol_data_local.dart';
import 'package:shirne_dialog/shirne_dialog.dart';

import 'utils/common.dart';

// 引入布局页面
import 'layouts/index.dart';

// 引入路由配置
import 'router/index.dart';

void main() async {
  // 初始化get_storage存储
  await GetStorage.init();
  // 初始化国际化语言
  initializeDateFormatting('zh_CN');
  
  runApp(const App());
}

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

  
  Widget build(BuildContext context) {
    return GetMaterialApp(
      title: 'Flutter3 Trip',
      debugShowCheckedModeBanner: false,
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: Color(0xFF006ff6)),
        useMaterial3: true,
        // 修正windows下字体不一致情况
        fontFamily: Platform.isWindows ? 'Microsoft YaHei' : null
      ),
      home: const Layout(),
      // 初始化路由
      initialRoute: Common.isLogin() ? '/' : '/login',
      // 路由页面
      getPages: routePages,
      // 初始化弹窗key
      navigatorKey: MyDialog.navigatorKey,
    );
  }
}

flutter3布局模板

在这里插入图片描述

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

  
  State<Layout> createState() => _LayoutState();
}

class _LayoutState extends State<Layout> {
  // page索引
  int pageCurrent = 0;
  // page页面
  List pageList = [IndexPage(), HotelPage(), ExplorePage(), OrderPage(), MyPage()];
  // tabs选项
  List navItems = [
    BottomNavigationBarItem(
      icon: Icon(Icons.rocket_launch_sharp),
      label: '首页'
    ),
    BottomNavigationBarItem(
      icon: Stack(
        alignment: Alignment(1.5, -1),
        children: [
          Icon(Icons.location_city_sharp),
          FStyle.badge(0, isdot: true)
        ],
      ),
      label: '酒店'
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.hotel, color: Colors.transparent,),
      label: ''
    ),
    BottomNavigationBarItem(
      icon: Stack(
        alignment: Alignment(4, -2),
        children: [
          Icon(Icons.list_alt_rounded),
          FStyle.badge(1)
        ],
      ),
      label: '订单'
    ),
    BottomNavigationBarItem(
      icon: Icon(Icons.person_pin),
      label: '我'
    )
  ];

  
  void initState() {
    super.initState();
  }

  
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Colors.grey[50],
      body: pageList[pageCurrent],
      // 底部导航栏
      bottomNavigationBar: Theme(
        // Flutter去掉BottomNavigationBar底部导航栏的水波纹
        data: ThemeData(
          splashColor: Colors.transparent,
          highlightColor: Colors.transparent,
          hoverColor: Colors.transparent,
        ),
        child: Stack(
          children: [
            Container(
              decoration: BoxDecoration(
                border: Border(top: BorderSide(color: Colors.black45, width: .1)),
              ),
              child: BottomNavigationBar(
                backgroundColor: Colors.white,
                fixedColor: FStyle.primaryColor,
                unselectedItemColor: Colors.black54,
                type: BottomNavigationBarType.fixed,
                elevation: 1.0,
                unselectedFontSize: 12.0,
                selectedFontSize: 12.0,
                currentIndex: pageCurrent,
                items: [
                  ...navItems
                ],
                onTap: (index) {
                  setState(() {
                    pageCurrent = index;
                  });
                },
              ),
            ),
            // 自定义底部导航栏中间按钮
            Positioned(
              left: MediaQuery.of(context).size.width / 2 - 18,
              top: 0,
              bottom: 0,
              child: InkWell(
                child: Column(
                  mainAxisAlignment: MainAxisAlignment.center,
                  children: [
                    Image.asset('assets/images/logo.png', width: 36.0, isAntiAlias: true, fit: BoxFit.contain,),
                  ],
                ),
                onTap: () {
                  setState(() {
                    pageCurrent = 2;
                  });
                },
              ),
            ),
          ],
        ),
      ),
    );
  }
}

flutter3自定义预订模块

在这里插入图片描述
预订模块封装成 一个组件。
在这里插入图片描述
支持热门城市/位置品牌选择、入住离店日期区间、价格/星级等功能。

在这里插入图片描述
实现滑动字母索引滚动到指定列表位置。

ItemScrollController itemScrollController = ItemScrollController();

ScrollablePositionedList.builder(
  itemScrollController: itemScrollController,
  itemCount: citylist.length,
  itemBuilder: (context, index) {
    // ...
  }
)

// 侧边索引
Align(
  alignment: Alignment.centerRight,
  child: GestureDetector(
    child: Container(
      color: Colors.transparent,
      width: 25.0,
      child: Column(
        mainAxisSize: MainAxisSize.min,
        mainAxisAlignment: MainAxisAlignment.center,
        children: List.generate(pinyinList.length, (index) {
          return GestureDetector(
            child: Container(
              ...
            ),
            onTapDown: (details) {
              // 跳转指定索引位置
              itemScrollController.jumpTo(index: index);
              setState(() {
                selectedLetter = pinyinList[index];
                showBubble = true;
              });
              Future.delayed(Duration(milliseconds: 200), () {
                setState(() {
                  selectedLetter = '';
                  showBubble = false;
                });
              });
            },
          );
        }),
      ),
    ),
    onVerticalDragUpdate: (details) {
      updateSelectedLetter(details.localPosition);
    },
    onVerticalDragEnd: (details) {
      setState(() {
        selectedLetter = '';
        showBubble = false;
      });
    },
  ),
),

在这里插入图片描述

// 入住日期
DateTime startDate = DateTime.now();
// 离店日期
DateTime endDate = DateTime.now().add(Duration(days: 1));

GestureDetector(
  child: Container(
    padding: EdgeInsets.all(10.0),
    decoration: BoxDecoration(
      border: Border(bottom: BorderSide(color: Color(0xfff5f5f5))),
    ),
    child: Row(
      spacing: 10.0,
      children: [
        Icon(Icons.calendar_month_outlined),
        Expanded(
          child: Row(
            mainAxisAlignment: MainAxisAlignment.spaceBetween,
            children: [
              Column(
                crossAxisAlignment: CrossAxisAlignment.start,
                spacing: 3.0,
                children: [
                  Text('入住', style: TextStyle(color: Colors.grey, fontSize: 12.0)),
                  Text('${DateFormat('MM-dd').format(startDate)} ${DateFormat('E', 'zh_CN').format(startDate)}'),
                ],
              ),
              Container(
                color: Colors.grey[50],
                padding: EdgeInsets.symmetric(horizontal: 5.0, vertical: 1.0),
                // DateTime 类提供了 difference 方法,可以计算两个日期之间的时间差,返回一个 Duration 对象。通过 Duration 的 inDays 属性,可以获取天数差。
                child: Text('共${endDate.difference(startDate).inDays}晚'),
              ),
              Column(
                crossAxisAlignment: CrossAxisAlignment.end,
                spacing: 3.0,
                children: [
                  Text('离店', style: TextStyle(color: Colors.grey, fontSize: 12.0)),
                  Text('${DateFormat('MM-dd').format(endDate)} ${DateFormat('E', 'zh_CN').format(endDate)}'),
                ],
              ),
            ],
          ),
        ),
        Icon(Icons.arrow_forward_ios_rounded, color: Colors.grey, size: 12.0,)
      ],
    ),
  ),
  onTap: () {
    handleCalendar();
  },
),

在这里插入图片描述

void handleCalendar() {
  showModalBottomSheet(
    backgroundColor: Colors.white,
    shape: RoundedRectangleBorder(borderRadius: BorderRadius.vertical(top: Radius.circular(0.0))),
    context: context,
    builder: (BuildContext context) {
      return Column(
        children: [
          Expanded(
            child: SfDateRangePicker(
              selectionMode: DateRangePickerSelectionMode.range,
              selectionShape: DateRangePickerSelectionShape.rectangle,
              // 初始日期范围
              initialSelectedRange: PickerDateRange(startDate, endDate),
              minDate: DateTime.now(),
              maxDate: DateTime.now().add(Duration(days: 450)),
              backgroundColor: Colors.white,
              // 日期区间颜色
              startRangeSelectionColor: Color(0xFF006ff6),
              endRangeSelectionColor: Color(0xFF006ff6),
              rangeSelectionColor: Color(0xFFe3f0f9),
              // 选中颜色
              selectionColor: Color(0xFF006ff6),
              rangeTextStyle: TextStyle(color: Color(0xFF006ff6)),
              monthViewSettings: DateRangePickerMonthViewSettings(
                // 改变一周的第一天
                firstDayOfWeek: 1,
                viewHeaderStyle: DateRangePickerViewHeaderStyle(
                  textStyle: TextStyle(color: Color(0xFF130438), fontSize: 12, fontFamily: 'Arial'),
                ),
                dayFormat: 'EE',
              ),
              // 自定义头部样式
              headerStyle: DateRangePickerHeaderStyle(
                backgroundColor: Colors.white,
                textAlign: TextAlign.center
              ),
              // 日期单元格样式
              monthCellStyle: DateRangePickerMonthCellStyle(
                cellDecoration: BoxDecoration(
                  // color: Color(0xFFf7f4ff),
                ),
                todayTextStyle: TextStyle(color: Color(0xFF006ff6)),
                disabledDatesTextStyle: TextStyle(color: Colors.black26),
                weekendTextStyle: TextStyle(color: Colors.red.withAlpha(200)),
              ),
              // showTodayButton: true,
              // showActionButtons: true,
              onSelectionChanged: (DateRangePickerSelectionChangedArgs args) {
                setState(() {
                  if(args.value.startDate != null && args.value.endDate != null) {
                    startDate = args.value.startDate;
                    endDate = args.value.endDate;
                    Future.delayed(Duration(seconds: 1), () {
                      Get.back();
                    });
                  }
                });
              },
            ),
          ),
        ],
      );
    },
  );
}

flutter3酒店预订列表筛选

筛选下拉框使用 SizeTransitionFadeTransition 组件实现下拉动画效果。
在这里插入图片描述

// 筛选下拉框
if(dropdownVisible)
Positioned(
  top: dropdownOffset,
  height: MediaQuery.of(context).size.height - dropdownOffset,
  width: MediaQuery.of(context).size.width,
  child: ScrollConfiguration(
    behavior: CustomScrollBehavior(),
    child: Material(
      color: Colors.transparent,
      child: Column(
        children: [
          SizeTransition(
            sizeFactor: animation, // 高度展开动画
            axis: Axis.vertical, // 垂直方向展开
            child: Container(
              color: Colors.white,
              width: double.infinity,
              child: Column(
                crossAxisAlignment: CrossAxisAlignment.start,
                children: [
                  if(dropdownIndex == 0)
                  dropOption1(),
                  if(dropdownIndex == 1)
                  dropOption2(),
                  if(dropdownIndex == 2)
                  dropOption3(),
                  if(dropdownIndex == 3)
                  dropOption4(),
                ],
              ),
            ),
          ),
          Expanded(
            child: FadeTransition(
              opacity: animation,
              child: GestureDetector(
                child: Container(
                  color: Colors.black54,
                ),
                onTap: () {
                  setState(() {
                    closeDropdown();
                  });
                },
              ),
            ),
          ),
        ],
      ),
    ),
  ),
),

flutter3客服消息模块

在这里插入图片描述
消息聊天模块,这部分功能是之前开发的一款flutter3.x仿微信app聊天功能的精简版。

flutter3+dart3聊天室|Flutter3跨平台仿微信App语音聊天/朋友圈

在这里插入图片描述
以上就是flutter3.x+dart3实战酒店预订app系统的一些分享,希望对大家有所帮助~

过往热门实战项目实例

在这里插入图片描述

;