阅读视图

发现新文章,点击刷新页面。

flutter布局(列表组件)

通用ScrollController

  • 控制器加上必先挂载销毁

      /// 初始化
      ScrollController _scrollController = ScrollController();
      
      /// 销毁控制器
      @override
      void dispose(){
          _scrollController.dispose();
          super.dispose();
      }
      
      /// 绑定
      ListView(
          controller:_scrollController, //绑定控制器
      )
    
  • 滚动到顶部/指定位置

      /// 安全判断
      if(!_scrollController.hasClients) return;
      /// 滚动到顶部
      _scrollController.jumpTo(0); /// 跳转到顶部,无动画
      _scrollController.animateTo( /// 动画滚动
          0,
          duration: const Duration(molliseconds:300), //
          curve:Curves.easeOut, // 动画曲线
      )
      
      /// 滚动至底部(_scrollController.position.maxScrollExtent)
      final maxExtent = _scrollController.position.maxScrollExtent;
      _scrollController.jumpTo(maxExtent);
      ...
      
    
  • 滚动吸顶/隐藏导航栏/下拉更多等

      /// 监听+状态
      _scrollController.addListener((){
          /// 底部200px 触发加载
          double maxExtent = _scrollController.position.maxScrollExtent;
          double currentOffset = _scrollController.offset;/// 滚动到的位置
          
          if(currentOffset >= maxExtent - 200 && !isloading) {
              loadMoreDate();
          }
          
          /// 吸顶
          if(currentOffset <= 50){
              setState({
                  isCeilingMounted = true;
              })
          }else{
              setState({
                  isCeilingMounted = false;
              })        
          }
      })
    
  • 常用api

    • 判定是否有挂载

        _scrollController.hasClients
      
    • 卸载

        _scrollController.dispose();
        
      
    • 当前滚动位置

        _scrollController.offset
        _scrollController.position.pixels
      
    • 列表最大滚动位置

        _scrollController.position.maxScrollExtent;
      
    • 滚动

        _scrollController.jumpTo();
        _scrollController.animateTo(
            0,
            duration:const Duration(milliseconds:300),
            curve: Curves.ease
        )
      
    • 滚动监听

        _scrollController.addListener((){
            
        })
      

列表组件

ListView/ListView.builder/ListView.separated

  • 共用api

      scrollDirection //默认Axis.vertical(垂直) Axis.horizontal(水平)
      reverse // 默认false
      padding // 默认null
      shrinkWrap // 高度自适应 默认false,性能慎用!
      controller // 控制器
      itemExtent //固定子项高度/宽度
      cacheExtent // 预渲染缓存区域大小
      prototypeItem // 按照样本组件自适应高度
      addautomaticKeepAlives //默认true 保持已经加载好的子项状态,防止滑出屏幕后重建
      physics // 滚动物理效果 
      ///ClampingScrollPhysics(边界“撞墙”+微光效果 安卓默认)
      ///BouncingScrollPhysics(弹性回弹效果 IOS默认)
      ///NeverScrollableScrollPhysics(禁止滚动)
      ///AlwaysScrollableScrollPhysics(强制可滚动)
      ///PageScrollPhysics(以整页滑动、吸附效果明显)
      
    

补充全局效果设置:MaterialApp( scrollBehavior: MaterialScrollBehavior().copyWith( physics: const ClampingScrollPhysics(), // 全平台强制使用Android效果 ), );

  • 列表不超过15条可用ListView

  • 重点属性

    • ListView.builder——只创建/渲染屏幕可见区域+附近区域(超过15条考虑使用)
    • itemExtent——告知每一项的宽度/高度,提高命中率和性能(必用)
    • control——控制滚动
    • scrollDirection——Axis.horizontal/Axis.vertical控制滚动方向
    • itemExtent——列表长度
    • builder/separated专属(itemCount+itemBuilder)
  • ListView.separated

     ListView.separated(
         itemExtent:,
         itemCount:,
         itemBuilder:(context,index),
         separatorBuilder:(context,index){
             return Padding()
         }
     )
     
    
  • 性能优化相关

    • ListView.builder/ListView.separated(必需)
    • itemExtent (尽量必需,性能最好)
    • cacheExtent (必需,但值不能太大)
    • addAutomaticKeepAlives: true (通常必需)
    • shrinkWrap:true (性能消耗大,慎用!!!)

GridView/GridView.builder/GridView.extent

  • gridDelegate

    SliverGridDelegateWithFixedCrossAxisCount(
        crossAxisCount: 2, // 强制2列
        mainAxisSpacing: 10, // 上下间距10px
        crossAxisSpacing: 10, // 左右间距10px
        childAspectRatio: 1.5, // 子项宽高比
    )
    SliverGridDelegateWithMaxCrossAxisExtent( // 设置子项的最大宽度,即如果屏幕宽度有500,则(150*n)+(10*(n-1))<=500
        maxCrossAxisExtent: 150, // 子项最大宽度150px
        mainAxisSpacing: 10, // 上下间距10px
        crossAxisSpacing: 10, // 左右间距10px
        childAspectRatio: 1.0, // 正方形
    )
    
  • GridView.extent 即透传了 SliverGridDelegateWithMaxCrossAxisExtent,可以直接在GridView.extent中写SliverGridDelegateWithMaxCrossAxisExtent的属性

    GridView.extent(
        controller:_controller,
        children:<Widget>[],
        double maxCrossAxisExtent,
        double mainAxisSpacing,
        double crossAxisSpacing,
        double? childAspectRatio 
    )
    

SingleChildScrollView

  • 较短的滚动页面(长列表情况性能消耗较大)
  • 通常用作页面防溢出或短滚动

CustomScrollView

  • 大部分属性跟ListView和GridView一样,下面只例举较常用的api
  • cacheExtent(默认250)可设置150左右
  • shrinkWrap(是否自适应子组件高度)——会破坏懒加载,性能变差
  • slivers
    • SliverAppBar——折叠式标题栏,支持悬浮、吸顶、折叠
    • SliverList——对应ListView
    • SliverGrid——对应GridView
    • SliverToBoxAdapter——将普通Widget作为child传入Sliver
    • SliverPadding——内边距
    • SliverFillRemaining——填充页面剩余空间
❌