上一篇: Flutter 实现钉钉消息列表效果(一)

pubspec.yaml 依赖
  1. flutter_screenutil: ^2.3.0 # 屏幕适配
  2. flutter_svg: ^0.18.0 # svg 图片加载
  3. nine_grid_view: ^1.0.5 # 显示九宫格头像(QQ头像、微信头像 ....)

实现效果如图

Flutter 实现钉钉消息列表效果(二) - 图1

创建 DTMessageScreen
  • 构建 AppBar

  • 使用 Flutter 原生的 AppBar 进行对应属性设置
    Flutter 实现钉钉消息列表效果(二) - 图2

    1. AppBar buildAppBar(BuildContext context) {
    2. return AppBar(
    3. automaticallyImplyLeading: false,
    4. title: Row(
    5. mainAxisAlignment: MainAxisAlignment.start,
    6. children: <Widget>[
    7. GestureDetector(
    8. child: CircleAvatar(
    9. backgroundColor: kPrimaryColor,
    10. radius: kSize40,
    11. child: Text(
    12. "江景",
    13. style: TextStyle(color: Colors.white),
    14. ),
    15. ),
    16. onTap: () {
    17. Scaffold.of(context).openDrawer();
    18. },
    19. ),
    20. Padding(
    21. padding: EdgeInsets.only(left: kSize24),
    22. child: Text(
    23. "未连接",
    24. style: TextStyle(color: kColor33, fontSize: kSize30),
    25. ),
    26. )
    27. ],
    28. ),
    29. );
    30. }
  • 构建搜索输入框 Widget

    • 创建 DTMessageSearchDecoration
    • 自定义设置视图,使用 Container, 设置上 decoration
    • 没有使用 TextFiled,原因是想点击之后跳转到另外一个界面 (TODO:)

Flutter 实现钉钉消息列表效果(二) - 图3```dart class DTMessageSearchDecoration extends StatelessWidget { @override Widget build(BuildContext context) { return Container( height: kSize70, margin: EdgeInsets.symmetric(horizontal: kSize36), decoration: BoxDecoration( color: kColorECEDED, borderRadius: BorderRadius.circular(kSize35)), child: Row( crossAxisAlignment: CrossAxisAlignment.center, children: [ Padding( padding: EdgeInsets.only(left: kSize20, right: kSize16), child: Icon(Icons.search, color: kColor99), ), Text(“搜索”, style: TextStyle(color: kColor99)) ], ), ); } }

  1. -
  2. 实现日历 + 待办 + DING Widget
  3. - 创建 DTMessageTopQuick Widget
  4. - 使用 Column + Row 实现
  5. -
  6. 封装子组件 DTTopQuickItem,每个组件样式都是一样的,内容不一样,可以根据数据去渲染实现不同的 Item
  7. <br />![](https://gitee.com/shizidada/moose-resource/raw/master/blog/image-20201211093407909.png#alt=)
  8. ```dart
  9. class DTMessageTopQuick extends StatelessWidget {
  10. @override
  11. Widget build(BuildContext context) {
  12. return Column(
  13. children: <Widget>[
  14. Padding(
  15. padding: EdgeInsets.symmetric(vertical: kSize32),
  16. child: Row(
  17. mainAxisAlignment: MainAxisAlignment.spaceEvenly,
  18. children: <Widget>[
  19. DTTopQuickItem(
  20. iconPath: "assets/icons/icon_calendar.svg",
  21. title: "日历",
  22. showDivider: true),
  23. DTTopQuickItem(
  24. iconPath: "assets/icons/icon_backlog.svg",
  25. title: "待办",
  26. showDivider: true),
  27. DTTopQuickItem(
  28. iconPath: "assets/icons/icon_ding.svg", title: "DING"),
  29. ],
  30. ),
  31. ),
  32. Divider(height: kSize1, color: kColorECEDED, indent: kSize36)
  33. ],
  34. );
  35. }
  36. }
  • 单个 DTTopQuickItem

    • 自定义基础 StatelessWidget
    • 根据不同参数

      • iconPath 显示图片
      • title 显示文本
      • showDivider 是否需要显示后面竖杠
    • 小红圆点,Container 组件设置 BoxDecoration

Flutter 实现钉钉消息列表效果(二) - 图4

  1. class DTTopQuickItem extends StatelessWidget {
  2. final String iconPath;
  3. final String title;
  4. final bool showDivider;
  5. DTTopQuickItem(
  6. {@required this.iconPath,
  7. @required this.title,
  8. this.showDivider = false});
  9. @override
  10. Widget build(BuildContext context) {
  11. return Row(
  12. children: <Widget>[
  13. SvgPicture.asset(
  14. iconPath,
  15. width: kSize38,
  16. height: kSize38,
  17. color: kColor99,
  18. ),
  19. Padding(
  20. padding: EdgeInsets.only(left: kSize14),
  21. child: Text(
  22. title,
  23. style: TextStyle(
  24. color: kColor99,
  25. ),
  26. ),
  27. ),
  28. Padding(
  29. padding: EdgeInsets.only(left: kSize16),
  30. child: Container(
  31. width: kSize32,
  32. height: kSize32,
  33. alignment: Alignment.topCenter,
  34. decoration: BoxDecoration(
  35. color: Colors.red,
  36. borderRadius: BorderRadius.circular(kSize20)),
  37. child: Text(
  38. "6",
  39. style: TextStyle(color: Colors.white, fontSize: kSize24),
  40. )),
  41. ),
  42. showDivider
  43. ? Container(
  44. width: kSize1,
  45. height: kSize38,
  46. margin: EdgeInsets.only(left: kSize56),
  47. color: kColorECEDED,
  48. )
  49. : SizedBox(),
  50. ],
  51. );
  52. }
  53. }
  • 实现待办事项

    • 创建 DTMessageTopMask Widget
    • Column + Row 来添加不同的组件
    • 添加的小组件都是不同的 svg 图片

Flutter 实现钉钉消息列表效果(二) - 图5

  1. class DTMessageTopMask extends StatelessWidget {
  2. @override
  3. Widget build(BuildContext context) {
  4. return Column(
  5. children: <Widget>[
  6. Padding(
  7. padding: EdgeInsets.symmetric(vertical: kSize32),
  8. child: Row(
  9. mainAxisAlignment: MainAxisAlignment.spaceBetween,
  10. children: <Widget>[
  11. Container(
  12. width: kSize160,
  13. child: Row(
  14. mainAxisAlignment: MainAxisAlignment.center,
  15. children: <Widget>[
  16. SvgPicture.asset(
  17. 'assets/icons/icon_computer.svg',
  18. width: kSize38,
  19. height: kSize38,
  20. ),
  21. Container(
  22. width: kSize1,
  23. height: kSize38,
  24. margin: EdgeInsets.only(left: kSize36),
  25. color: kColorECEDED,
  26. )
  27. ],
  28. ),
  29. ),
  30. Expanded(
  31. child: Row(
  32. mainAxisAlignment: MainAxisAlignment.spaceBetween,
  33. children: <Widget>[
  34. SvgPicture.asset(
  35. 'assets/icons/icon_at.svg',
  36. width: kSize38,
  37. color: Colors.orangeAccent,
  38. ),
  39. SvgPicture.asset(
  40. 'assets/icons/icon_star.svg',
  41. width: kSize38,
  42. color: kColor99,
  43. ),
  44. SvgPicture.asset(
  45. 'assets/icons/icon_timer.svg',
  46. width: kSize38,
  47. color: kColor99,
  48. ),
  49. SvgPicture.asset(
  50. 'assets/icons/icon_red_packet.svg',
  51. width: kSize38,
  52. color: kColor99,
  53. ),
  54. SvgPicture.asset(
  55. 'assets/icons/icon_list.svg',
  56. width: kSize38,
  57. color: kColor99,
  58. ),
  59. ],
  60. ),
  61. ),
  62. GestureDetector(
  63. child: Container(
  64. width: kSize160,
  65. alignment: Alignment.centerRight,
  66. padding: EdgeInsets.only(right: kSize24),
  67. child: SvgPicture.asset(
  68. 'assets/icons/icon_more.svg',
  69. width: kSize38,
  70. color: kColor99,
  71. ),
  72. ),
  73. onTap: () {
  74. Navigator.push(context,
  75. MaterialPageRoute(builder: (BuildContext context) {
  76. return DTMessageSetting();
  77. }));
  78. },
  79. ),
  80. ],
  81. ),
  82. ),
  83. Divider(height: kSize1, color: kColorECEDED, indent: kSize36)
  84. ],
  85. );
  86. }
  87. }

代码地址: https://gitee.com/shizidada/flutter_dingtalk/blob/master/lib/ui/screens/message/message_screen.dart