10天用Flutter撸了个高仿携程App(附小技巧积累总结),面试官不讲武德

banner使用的是flutter的 flutter_swiper 插件实现的,代码如下:

Swiper(
itemCount: bannerList.length, // 滚动图片的数量
autoplay: true, // 自动播放
pagination: SwiperPagination( // 指示器
builder: SquareSwiperPagination(
size: 6, // 指示器的大小
activeSize: 6, // 激活状态指示器的大小
color: Colors.white.withAlpha(80), // 颜色
activeColor: Colors.white, // 激活状态的颜色
),
alignment: Alignment.bottomRight, // 对齐方式
margin: EdgeInsets.fromLTRB(0, 0, 14, 28), // 边距
),
itemBuilder: (BuildContext context, int index) { // 构造器
return GestureDetector(
onTap: () {
CommonModel model = bannerList[index];
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => WebView(
url: model.url,
),
),
);
},
child: Image.network(
bannerList[index].icon,
fit: BoxFit.fill,
),
);
},
),

具体使用方法,可以去 flutter的官方插件库 pub.dev 查看:点击flutter_swiper查看

Tips: 
需要注意的是,我稍改造了一下指示器的样式,flutter_swiper 只提供了 3 种指示器样式,如下:

  • dots = const DotSwiperPaginationBuilder(),圆形
  • fraction = const FractionPaginationBuilder(),百分数类型的,如:1/6,表示6页的第一页
  • rect = const RectSwiperPaginationBuilder(),矩形

并没有上图的激活状态的长椭圆形,其实就是按葫芦画瓢,自己实现一个长椭圆类型,如知详情,可点击查看长椭圆形指示器源码

浮动的 icon 导航

icon导航效果如图:

icon导航浮动在banner之上,其实用的是 flutter 的 Stack 组件,Stack 组件能让其子组件堆叠显示,它通常和 Positioned 组件配合使用,布局结构代码如下:

ListView(
children: [
Container(
child: Stack(
children: [
Container( … ), //这里放的是banner的代码
Positioned( … ), //这个就是icon导航,通过 Positioned 固定显示位置
],
),
),
Container( … ), // 这里放的网格导航及其他
],
),

渐变不规则带有背景图的网格导航

网格导航效果如图:

如图,网格导航分为三行四栏,而第一行分为三栏,每一行的第一栏宽度大于其余三栏,其余三栏均等,每一行都有渐变色,而且第一、二栏都有背景图;
flutter 里 Column 组件能让子组件竖轴排列, Row 组件能让子组件横轴排列,布局代码如下:

Column( // 最外面放在 Column 组件
children: [
Container( // 第一行包裹 Container 设置其渐变色
height: 72,
decoration: BoxDecoration(
gradient: LinearGradient(colors: [ //设置渐变色
Color(0xfffa5956),
Color(0xffef9c76).withAlpha(45)
]),
),
child: Row( … ), // 第一行
),
Padding(
padding: EdgeInsets.only(top: 1), // 设置行直接的间隔
),
Container(
height: 72,
decoration: BoxDecoration(
gradient: LinearGradient(colors: [ //设置渐变色
Color(0xff4b8fed),
Color(0xff53bced),
]),
),
child: Row( … ), // 第二行
),
Padding(
padding: EdgeInsets.only(top: 1), // 设置行直接的间隔
),
Container(
height: 72,
decoration: BoxDecoration(
gradient: LinearGradient(colors: [ //设置渐变色
Color(0xff34c2aa),
Color(0xff6cd557),
]),
),
child: Row( … ), // 第三行
),
],
),

其实,具体实现的细节还是很多的,比如:

  • 怎么设置第一栏宽度偏大,其他均等;
  • 第一行最后一栏宽度是其他的2倍;
  • 第一、二栏的别截图及浮动的红色气泡tip等;

在这里就不细讲,否则篇幅太长,如想了解详情 点击查看源码

其次,再来看看目的地页面功能及所用知识点,重点看下以下功能实现:

  • 左右布局tabBarListView
  • 目的地搜索页面

左右布局tabBarListView

具体效果如图:点击左边标签可以切换页面,左右滑动也可切换页面,点击展开显示更多等

其实官方已经提供了 tabBar 和 TabBarView 组件可以实现上下布局的效果*(旅拍页面就是用这个实现的)*,但是它无法实现左右布局,而且不太灵活,所以,我使用的是 vertical_tabs插件, 代码如下:

VerticalTabView(
tabsWidth: 88,
tabsElevation: 0,
indicatorWidth: 0,
selectedTabBackgroundColor: Colors.white,
backgroundColor: Colors.white,
tabTextStyle: TextStyle(
height: 60,
color: Color(0xff333333),
),
tabs: tabs,
contents: tabPages,
),
),

Tips:
这里需要注意的是:展开显示更多span标签组件的实现,因为,这个组件在很多的其他组件里用到而且要根据接口数据动态渲染,且组件自身存在状态的变化,这种情况下,最好是把他单独封装成一个组件(widget),否则,很难控制自身状态的变化,出现点击没有效果,或点击影响其他组件。

目的地搜索页面

效果如图:点击搜索结果,如:点击‘一日游‘,会搜索到‘一日游‘的相关数据

目的地搜索页面,大多都是和布局和对接接口的代码,在这里就不再赘述。

然后就是旅拍页面功能及所用知识点,重点看下以下功能实现:

  • 左右布局tabBarListView
  • 瀑布流卡片
  • 旅拍搜索页

左右布局tabBarListView

效果如图:可左右滑动切换页面,上拉加载更多,下拉刷新等

这个是flutter 提供的组件,tabBar 和 TabBarView,代码如下:

Container(
color: Colors.white,
padding: EdgeInsets.only(left: 2),
child: TabBar(
controller: _controller,
isScrollable: true,
labelColor: Colors.black,
labelPadding: EdgeInsets.fromLTRB(8, 6, 8, 0),
indicatorColor: Color(0xff2FCFBB),
indicatorPadding: EdgeInsets.all(6),
indicatorSize: TabBarIndicatorSize.label,
indicatorWeight: 2.2,
labelStyle: TextStyle(fontSize: 18),
unselectedLabelStyle: TextStyle(fontSize: 15),
tabs: tabs.map((Groups tab) {
return Tab(
text: tab.name,
);
}).toList(),
),
),
Flexible(
child: Container(
padding: EdgeInsets.fromLTRB(6, 3, 6, 0),
child: TabBarView(
controller: _controller,
children: tabs.map((Groups tab) {
return TravelTabPage(
travelUrl: travelParamsModel?.url,
params: travelParamsModel?.params,
groupChannelCode: tab?.code,
);
}).toList()),
)),

瀑布流卡片

瀑布流卡片 用的是 flutter_staggered_grid_view 插件,代码如下:

StaggeredGridView.countBuilder(
controller: _scrollController,
crossAxisCount: 4,
itemCount: travelItems?.length ?? 0,
itemBuilder: (BuildContext context, int index) => _TravelItem(
index: index,
item: travelItems[index],
),
staggeredTileBuilder: (int index) => new StaggeredTile.fit(2),
mainAxisSpacing: 2.0,
crossAxisSpacing: 2.0,
),

旅拍搜索页

效果如图:首先显示热门旅拍标签,点击可搜索相关内容,输入关键字可搜索相关旅拍信息,地点、景点、用户等

小技巧积累总结

以下都是我在项目里使用的知识点,在这里记录分享出来,希望能帮到大家。

PhysicalModel

PhysicalModel 可以裁剪带背景图的容器,如,你在一个 Container 里放了一张图片,想设置图片圆角,设置 Container 的 decoration 的 borderRadius 是无效的,这时候就要用到 PhysicalModel,代码如下:

PhysicalModel(
borderRadius: BorderRadius.circular(6), // 设置圆角
clipBehavior: Clip.antiAlias, // 裁剪行为
color: Colors.transparent, // 颜色
elevation: 5, // 设置阴影
child: Container(
child: Image.network(
picUrl,
fit: BoxFit.cover,
),
),
),

LinearGradient

给容器添加渐变色,在网格导航、appBar等地方都使用到,代码如下:

Container(
height: 72,
decoration: BoxDecoration(
gradient: LinearGradient(colors: [
Color(0xff4b8fed),
Color(0xff53bced),
]),
),
child: …
),

Color(int.parse(‘0xff’ + gridNavItem.startColor))

颜色值转换成颜色,如果,没有变量的话,也可直接这样用 Color(0xff53bced),

  • ox:flutter要求,可固定不变
  • ff:代表透明贴,不知道如何设置的话,可以用取色器,或者 withOpacity(opacity) 、 withAlpha(a)
  • 53bced: 常规的6位RGB值

Expanded、FractionallySizedBox

Expanded 可以让子组件撑满父容器,通常和 Row 及 Column 组件搭配使用;

FractionallySizedBox 可以让子组件撑满或超出父容器,可以单独使用,大小受 widthFactor 和 heightFactor 宽高因子的影响

MediaQuery.removePadding

MediaQuery.removePadding可以移除组件的边距,有些组件自带有边距,有时候布局的时候,不需要边距,这时候就可以用MediaQuery.removePadding,代码如下:

MediaQuery.removePadding(
removeTop: true,
context: context,
child: …
)

MediaQuery.of(context).size.width

MediaQuery.of(context).size.width 获取屏幕的宽度,同理,MediaQuery.of(context).size.height 获取屏幕的高度;
如,想一行平均3等分: 0.3 * MediaQuery.of(context).size.width,在目的地页面的标签组件就使用到它,代码如下:

自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。

深知大多数Android工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!

因此收集整理了一份《2024年Android移动开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。
img
img
img
img
img
img
img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上Android开发知识点,真正体系化!

由于文件比较大,这里只是将部分目录大纲截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且后续会持续更新

如果你觉得这些内容对你有帮助,可以添加V获取:vip204888 (备注Android)
img

如何做好面试突击,规划学习方向?

面试题集可以帮助你查漏补缺,有方向有针对性的学习,为之后进大厂做准备。但是如果你仅仅是看一遍,而不去学习和深究。那么这份面试题对你的帮助会很有限。最终还是要靠资深技术水平说话。

网上学习 Android的资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。建议先制定学习计划,根据学习计划把知识点关联起来,形成一个系统化的知识体系。

学习方向很容易规划,但是如果只通过碎片化的学习,对自己的提升是很慢的。

同时我还搜集整理2020年字节跳动,以及腾讯,阿里,华为,小米等公司的面试题,把面试的要求和技术点梳理成一份大而全的“ Android架构师”面试 Xmind(实际上比预期多花了不少精力),包含知识脉络 + 分支细节

image

在搭建这些技术框架的时候,还整理了系统的高级进阶教程,会比自己碎片化学习效果强太多。

image

网上学习 Android的资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。希望这份系统化的技术体系对大家有一个方向参考。

,阿里,华为,小米等公司的面试题,把面试的要求和技术点梳理成一份大而全的“ Android架构师”面试 Xmind(实际上比预期多花了不少精力),包含知识脉络 + 分支细节

[外链图片转存中…(img-GNFedHmz-1711606700746)]

在搭建这些技术框架的时候,还整理了系统的高级进阶教程,会比自己碎片化学习效果强太多。

[外链图片转存中…(img-Rhh5XXur-1711606700747)]

网上学习 Android的资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。希望这份系统化的技术体系对大家有一个方向参考。

本文已被CODING开源项目:《Android学习笔记总结+移动架构视频+大厂面试真题+项目实战源码》收录

  • 27
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值