首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >Flutter | 一个超级酷炫的登录页是怎样炼成的

Flutter | 一个超级酷炫的登录页是怎样炼成的

作者头像
用户6256742
发布于 2024-05-17 01:23:14
发布于 2024-05-17 01:23:14
48700
代码可运行
举报
文章被收录于专栏:网络日志网络日志
运行总次数:0
代码可运行

近些日子在 UIMovement 上看到了一个比较酷炫的登录页效果,如下:

Flutter | 一个超级酷炫的登录页是怎样炼成的
Flutter | 一个超级酷炫的登录页是怎样炼成的

觉得很酷炫,就自己实现了一下,效果如下:

Flutter | 一个超级酷炫的登录页是怎样炼成的
Flutter | 一个超级酷炫的登录页是怎样炼成的

下面就来一步一步的分析是如何做出来的。

需求分析

首先还是老套路,看一下都需要做什么事情:

  1. 首先我们最清晰明了的需求就是点击「注册」弹出 Dialog
  2. 弹出 Dialog 后延迟一段时间弹出 Dialog 里的内容
  3. Dialog 内说明文字有两种颜色
  4. 点击 「Accepter」按钮会变色缩小回弹并展示 ok图标
  5. 点击「Accepter」按钮时 Dialog 内其他文字都被「白色遮罩」
  6. 「Accepter」按钮 动画结束后 dismiss 掉当前dialog 并把 logo向上移
  7. 跳转到第二页,文字呈波浪形弹出
  8. 文字弹出后显示对话框并弹出键盘

开始实现

需求了解了,下面就是一步一步的实现效果。

1. 点击「注册」弹出 Dialog

在这里我们需要注意的有一点:

在我们使用 showModalBottomSheet 时,默认的背景是白色的,也就是说我们自己设置的圆角是不管用的,

所以要给这个 BottomSheet 一个背景,这个参数在 showModalBottomSheet 方法中就有:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
showModalBottomSheet(
  context: context,
  backgroundColor: Colors.transparent,
  builder: (context) {
    Future.delayed(Duration(milliseconds: 50), () {
      _animationController.forward();
    });
    return AnimatedUserAgreement(
      animation: _animation,
    );
  });
)

设置一个 backgroundColor 就ok了。

2. 弹出 Dialog 后延迟一段时间弹出 Dialog 里的内容

这里我是写了一个 「AnimatedWidget」,对 Dialog 里面的 Widget 同时执行透明度和位置的动画:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
return Container(
  height: 270,
  padding: EdgeInsets.all(30),
  decoration: BoxDecoration(
    borderRadius: BorderRadius.circular(30), color: Colors.white),
  child: Opacity(
    opacity: _opacityTween.evaluate(animation),
    child: Stack(
      children: <Widget>[
        SingleChildScrollView(
          child: Container(
            child: UserAgreementDialog(),
            margin: EdgeInsets.only(top: _offsetTween.evaluate(animation)),
          ),
        )
      ],
    ),
  ),
);

可能细心的同学看出来上面的代码有一些问题:

为什么要加一个 SingleChildScrollView

因为我这里改变位置使用的动画效果是 「动态改变 Container margin 的值」

所以如果不使用 ScrollView 的话,会溢出。

3. Dialog 内说明文字有两种颜色

有两种颜色这个需求还是比较简单的,使用 「TextSpan」就搞定了。

代码我就不贴了。

4. 点击 「Accepter」按钮会变色缩小回弹并展示 ok图标

重点来了,这个功能是相对来说比较复杂的,但是只要我们了解需求,写起来也是比较简单。

首先我们也是把这个功能点拆分一下:

  1. 点击按钮的时候会变色
  2. 点击后会变回原来的颜色并缩小成一个圆形
  3. 变成圆形后动画效果展示 ok 图标

也还是一步一步来。

1. 点击按钮的时候会变色

该功能不用考虑太多,既然有点击手势,那必然会使用 GestureDetector

然后使用 GestureDetectoronTapDown 参数,该参数是在「点击按下」时回调:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
onTapDown: (d) {
  setState(() {
    btnColor = btnColors[1];
  });

也没有多余复杂的东西,就是改变按钮的颜色。

2. 点击后会变回原来的颜色并缩小成一个圆形

如何处理点击后?或者没有点击?

GestureDetector 也帮我们封装好了:

  • onTapUp:在点击抬起时回调
  • onTapCancel:在取消点击时回调

首先我们处理取消点击:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
onTapCancel: () {
  setState(() {
    btnColor = btnColors[0];
  });
}

把颜色变回去就行了。

然后处理抬起时的逻辑,在抬起时也有两个逻辑:

  1. 按钮会缩小成圆形
  2. 缩小成圆形的时候会弹出 ok 图标

首先说一下第一点:

缩小成圆形的时候是有一个回弹效果的,所以不能使用 AnimatedContainer 这种,必须要使用 Animation 才有这种效果。

所以我使用了 AnimatedBuilder 来包装这个 Widget。

然后说一下第二点:

如何在缩小成圆形的时候弹出 ok 图标?

我们可以使用 IndexStack,在开始缩小动画的时候切换 index,因为 ok 图标开始时的缩放状态是 0,所以页面上是没有图标的,方便我们后续做动画。

Widget 代码如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
AnimatedBuilder(
  animation: _widthAnimation,
  builder: (BuildContext context, Widget child) {
    return Container(
      width: _widthAnimation.value,
      alignment: Alignment.center,
      decoration: BoxDecoration(
        borderRadius: BorderRadius.all(Radius.circular(40)),
        color: btnColor),
      margin: EdgeInsets.only(top: btnMargin),
      height: btnHeight,
      child: IndexedStack(
        alignment: Alignment.center,
        index: index,
        children: <Widget>[
          Text(
            'Accepteer',
            style: TextStyle(fontSize: 18),
          ),
          ScaleTransition(
            scale: _scaleTween.animate(_animation),
            child: Image.asset(
              'images/ok.png',
              width: 35,
              height: 35,
            ),
          )
        ],
      ),
    );
  },
),

5. 点击「Accepter」按钮时 Dialog 内其他文字都被「白色遮罩」

这个也很简单,Container 默认就有一个参数是:foregroundDecoration,我们只需要在这个参数里设置上我们想要遮罩的颜色就可以了。

但是也需要注意一点,如果最开始使用的遮罩颜色为「透明色」,那么会整体变黑一下,这个具体的原因我也没研究明白,有知道的大佬可以告知一下。

这样按钮点击后的效果就全部完成,代码如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
onTapUp: (d) {
  Future.delayed(Duration(milliseconds: 60), () {
    setState(() {
      foregroundColor = Colors.white70;
      btnColor = btnColors[0];
      index = 1;
    });
    _widthController.forward();
    Future.delayed(Duration(milliseconds: 200), () {
      _controller.forward().then((va) {
        Navigator.pop(context);
      });
    });
  });
}

6. 动画结束后 dismiss 掉当前dialog 并把 logo向上移

这个相对来说就更简单了,我们只需要在 logo 的上方套一个 AnimatedContainer

然后监听 dialog 是否已经 dismiss,如果已经 dismiss 那么则调整 margin 的值就好了。

代码如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
setState(() {
  logoMargin = 100;
});

这样正好 dialog 会有一个下移的动画,而 logo 上移,就达到了我们想要的效果。

7. 跳转到第二页,文字呈波浪形弹出

如何把文字呈波浪形弹出?

我们最先想到的肯定就是动画,因为也只有动画才有这种回弹的效果,

那这么多文字,每一个都要设置动画?

答案是肯定的。

既然知道了,那我们也只能按部就班的做了。

可以看到,每一个文字都是由透明转为不透明,并且还会更改位置,

那我们还是先来封装一个 AnimatedWidget

代码如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
class AnimatedStrWidget extends AnimatedWidget {
  final Tween<double> _opacityTween = Tween(begin: 0, end: 1);
  final Tween<Offset> _offsetTween =
      Tween(begin: Offset(0, 3), end: Offset(0, 0));
  final Widget child;

  AnimatedStrWidget(
      {Key key, @required Animation<double> animation, @required this.child})
      : super(key: key, listenable: animation);

  @override
  Widget build(BuildContext context) {
    final Animation<double> animation = listenable;
    return Opacity(
      opacity: _opacityTween.evaluate(animation) < 0
          ? 0
          : _opacityTween.evaluate(animation) > 1
              ? 1
              : _opacityTween.evaluate(animation),
      child: SlideTransition(
        position: _offsetTween.animate(animation),
        child: child,
      ),
    );
  }
}

这里也有两点需要注意:

  1. 透明度不能有负数并且不能大于1,因为我们这个效果是要有回弹的效果,所以要做判断。
  2. Tween<Offset> 这里的值是整个高度的倍数,所以不要以为是像素值。

封装好以后我们就可以愉快的玩耍了:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
void startAnim() async {
  for (int i = 0; i < strs.length; i++) {
    Future.delayed(
      Duration(
        milliseconds: i * 100,
      ), () {
        _strController[i].forward();
      });
  }
}

文字弹出效果时间为 600ms,这里设置每隔100ms做一个动画,

这样的效果是比较好的,更像波浪形弹出。

8. 文字弹出后显示对话框并弹出键盘

主动弹出键盘我们应该都有所了解,使用 FocusNode

这里我们也是只需要判断最后一个动画何时做完,然后把隐藏的键盘弹出,并且把键盘弹出就ok了。

代码如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
_strPositionAnimation[strs.length - 1].addStatusListener((status){
  if(status == AnimationStatus.completed){
    setState(() {
      opacity = 1;
      FocusScope.of(context).requestFocus(myFocusNode);
    });
  }
});

总结

实现这个页面耗费了我一个晚上的时间,不得不说,东西还是不少的。

想要实现这样酷炫的登录页,还是比较复杂。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2024-04-21 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
【BootStrap】栅格系统、表单样式与按钮样式-附有源码
Bootstrap 提供了一套响应式、移动设备优先的流式栅格系统,随着屏幕或视口(viewport)尺寸的增加,系统会自动分为最多12列。
谙忆
2021/01/21
1.6K0
【BootStrap】栅格系统、表单样式与按钮样式-附有源码
bootstrap快速入门笔记(二)-栅格系统,响应式类
1,行row必须包含在 .container (固定宽度)或 .container-fluid (100% 宽度)中,一行有12列
用户3055976
2018/09/12
1.3K0
BootStarp常用标签
1 栅格系统 <!DOCTYPE html> <!-- 让其支持html5类型 --> <html lang="zh-CN"> <head> <meta charset="UTF-8"> <!-- 申明文档的兼容模式 ,表示使用ie浏览器的最新模式 --> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <!-- 让其首先对移动设备友好 user-scalable=no 可以禁用其缩放(zooming)功能 --> <meta n
用户5927264
2019/07/31
4880
01_Bootstrap基础组件01
Bootstrap,来自 Twitter,是目前很受欢迎的前端框架。Bootstrap 是基于 HTML、CSS、JavaScript 的,它简洁灵活,使 Web 开发更加快捷。它对 HTML、CSS 和 JavaScript 进行了封装,使它们使用起来更方便。我们只需要使用它已经设定好的类,或规则,即可快速应用它提供的功能。
张哥编程
2024/12/13
4220
BootStrap
为了增强跨浏览器渲染的一致性,我们使用了 Normalize.css,这是由 Nicolas Gallagher 和 Jonathan Neal 维护的一个CSS 重置样式库
HammerZe
2022/03/25
3.7K0
BootStrap
BootStrap初始
Bootstrap是Twitter开源的基于HTML、CSS、JavaScript的前端框架。
全栈程序员站长
2022/07/21
4.9K0
BootStrap初始
bootstrap快速入门笔记(四)-less用法指南, mixin和变量
这是主要的 Less 文件。该文件中导入了一些其他的 less 文件。该文件中没有任何代码。
用户3055976
2019/02/25
2.2K0
vue 实现一个简单的栅格组件
参考iview, ant-design 的栅格组件,发现两者的基础思路是一致的。 这里通过实现一个简化版的栅格组件做总结.
copy_left
2019/08/30
2.4K0
从零开始学 Web 之 移动Web(七)Bootstrap
随着Web应用变的越来越复杂,在大量的开发过程中我们发现有许多功能模块非常相似,比如轮播图、分页、选项卡、导航栏等,开发中往往会把这些具有通用性的功能模块进行一系列封装,使之成为一个个组件应用到项目中,可以极大的节约开发成本,将这些通用的组件缩合到一起就形成了前端框架。
Daotin
2018/08/31
5.9K0
从零开始学 Web 之 移动Web(七)Bootstrap
【Java 进阶篇】深入了解 Bootstrap 栅格系统
在网页开发中,创建响应式的布局是至关重要的,因为不同设备和屏幕尺寸需要不同的布局来呈现内容。Bootstrap 提供了一个强大的栅格系统,使开发者能够轻松创建适应不同屏幕的网页布局。本文将深入介绍 Bootstrap 栅格系统,面向初学者,帮助您充分了解如何使用它来构建响应式网页。
繁依Fanyi
2023/10/22
7180
【Java 进阶篇】深入了解 Bootstrap 栅格系统
bootstrap入门
​ 2、.container-fluid类用于100% 宽度,占据全部视口(viewport)的容器。(通栏)
用户9603238
2022/03/31
1.2K0
bootstrap入门
响应式布局
原理:在不同屏幕下,通过媒体查询来改变布局容器的大小,再改变里面子元素的排列方式和大小,从而实现在不同大小的屏幕下,看到不同的页面布局和样式。
赤蓝紫
2023/01/01
3.3K0
响应式布局
Web-第五天 BootStrap学习
将使用Bootstrap重写首页,整个案例中将使用到Bootstrap各种模块,为了方便编程,将采用拆分的原则,各个模块单独编写,最后组合。
Java帮帮
2018/07/27
5.5K0
Web-第五天 BootStrap学习
移动开发-响应式
移动开发-响应式布局 响应式开发原理: 使用媒体查询针对不同宽度的设备进行布局和样式设置,从而适配不同设备 设备划分 尺寸区间 超小屏幕 (手机) < 768px 小屏设备 (平板) >= 768px ~ < 992px 中等屏幕 (桌面显示器) >= 992px ~ <1200px 宽屏设备 (大桌面显示器) >= 1200px 响应式布局容器: 响应式需要一个父级做为布局容器,来配合子级元素来实现变化效果 原理就是在不同屏幕下,通过媒体查询来改变这个布局容器的大小,再改变里面子元素的排列方式和大小,从
小城故事
2022/11/24
2.8K0
Bootstrap(前端开发框架)——入门基础
1.什么是Bootstrap?       1.Bootstrap是2011年Twitter团队为了方便维护PC端和手机端二研发的一个响应式前端框架。 2.用于快速开发Web应用程序和网站的前端框架 3.Bootstrap是基于HTML、CSS、JS的,简介灵活,使Web开发更加快捷 4.总结:Bootstrap是一个建立在一个页面,可以在三个中断(PC、平板、手机)上完美战士的响应式前端框架   2.Bootstrap的环境配置: 19:021.到Bootstrap官网下载Bootstrap
用户10196776
2022/11/18
1.2K0
Bootstrap(前端开发框架)——入门基础
Bootstrap响应式前端框架笔记一——强大的栅格布局
    Bootstrap是一款HTML,Css和JavaScript开发框架,其也支持开发者进行自定义构建,开发者也可以只打包自己需要的功能模块使用。Bootstrap的中文网址如下:
珲少
2018/08/15
2.5K0
Bootstrap响应式前端框架笔记一——强大的栅格布局
Bootstrap入门【人类的天堂】
<button class="btn">Bootstrap的button</button>
天蝎座的程序媛
2022/11/18
9260
bootstrap笔记(五)——栅格参数
col-md-数字: xs:手机设备大小 sm:平板设备大小 md:笔记本设备大小 lg:台式电脑设备大小 数字:代表着在一行12列中所占的单元格数。
兮动人
2021/06/11
1.6K0
bootstrap笔记(五)——栅格参数
Bootstrap学习文档(一)
Bootstrap 是最受欢迎的 HTML、CSS 和 JS 框架,用于开发响应式布局、移动设备优先的 WEB 项目,使用这个框架可以简单高效的开发出适配各种屏幕的网站应用,即是编写一套代码,适用多重平台(PC,平板,手机等)。Bootstrap 相比其他框架,自由度更高,它提供了基本的样式和基本的组件,而不会在创造上约束开发者的思维。
Wizey
2018/08/30
2.9K0
Bootstrap学习文档(一)
移动端WEB开发之响应式布局
原理就是在不同屏幕下,通过媒体查询来改变这个布局容器的大小,再改变里面子元素的排列方式和大小,从而实现不同屏幕下,看到不同的页面布局和样式变化。
星辰_大海
2020/09/30
4.4K0
相关推荐
【BootStrap】栅格系统、表单样式与按钮样式-附有源码
更多 >
LV.3
这个人很懒,什么都没有留下~
目录
  • 需求分析
  • 开始实现
    • 1. 点击「注册」弹出 Dialog
    • 2. 弹出 Dialog 后延迟一段时间弹出 Dialog 里的内容
    • 3. Dialog 内说明文字有两种颜色
    • 4. 点击 「Accepter」按钮会变色缩小回弹并展示 ok图标
      • 1. 点击按钮的时候会变色
      • 2. 点击后会变回原来的颜色并缩小成一个圆形
    • 5. 点击「Accepter」按钮时 Dialog 内其他文字都被「白色遮罩」
    • 6. 动画结束后 dismiss 掉当前dialog 并把 logo向上移
    • 7. 跳转到第二页,文字呈波浪形弹出
    • 8. 文字弹出后显示对话框并弹出键盘
  • 总结
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档