• Flutter 实现简单搜索功能


    先建立一个主文件,继承StatelessWidget,然后在home属性中加入SearchBarDemo,这是一个自定义的Widget,主要代码都在这个文件中。

    import 'package:flutter/material.dart';
    import 'search_bar_demo.dart';
    
    void main() =>runApp(MyApp());
    
    class MyApp extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          title:'Flutter Demo',
          theme: ThemeData.light(),
          home: SearchBarDemo()
        );
      }
    }

    然后是搜索页面,里面包含数据及搜索功能。

    工作中这些数据是后台传递给我们,或者写成配置文件的,这里我们就以List的方式代替了。我们在这个文件中定义了两个List:

    const searchList = [
      'jiejie-大长腿',
      'jiejie-水蛇腰',
      'gege-帅气欧巴',
      'gege-小鲜肉'
    ];
    
    const recentSuggest = [
      '推荐-1',
      '推荐-2',
    ];

    点击搜索按钮

    class SearchBarDemo extends StatefulWidget {
      _SearchBarDemoState createState() => _SearchBarDemoState();
    }
    
    class _SearchBarDemoState extends State<SearchBarDemo> {
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: Text('SearchBarDemo'),
            actions: <Widget>[
              IconButton(
                icon: Icon(Icons.search),
                onPressed: (){
                  showSearch(context: context,delegate: SearchBarDelegate());
                },
              )
            ],
            ),
          
        );
      }
    }

    在点击图标时执行SearchBarDelegate 类,这个类继承与SearchDelegate类,继承后要重写里边的四个方法。

    重写buildActions方法:

    buildActions方法时搜索条右侧的按钮执行方法,我们在这里方法里放入一个clear图标。 当点击图片时,清空搜索的内容。

    buildLeading 方法重写

    这个时搜索栏左侧的图标和功能的编写,这里我们才用AnimatedIcon,然后在点击时关闭整个搜索页面。

    buildResults方法重写

    buildResults方法,是搜到到内容后的展现,因为我们的数据都是模拟的,所以我这里就使用最简单的Container+Card组件进行演示了。

    buildSuggestions方法重写

    这个方法主要的作用就是设置推荐,就是我们输入一个字,然后自动为我们推送相关的搜索结果。

    class SearchBarDelegate extends SearchDelegate<String>{
      //清空按钮
      @override
      List<Widget>buildActions(BuildContext context){
        return [
          IconButton(
            icon: Icon(Icons.clear),
            onPressed: () => query = "", //搜索值为空
          )
        ]; 
      }
      //返回上级按钮
      @override
      Widget buildLeading(BuildContext context) {
        return IconButton(
          icon: AnimatedIcon(
            icon: AnimatedIcons.menu_arrow, progress: transitionAnimation
          ),
          onPressed: () => close(context, null)  //点击时关闭整个搜索页面
        );
      }
      //搜到到内容后的展现
      @override
      Widget buildResults(BuildContext context){
        return Container(
           100.0,
          height:100.0,
          child: Card(
            color:Colors.redAccent,
            child: Center(
              child: Text(query),
            ),
          ),
        );
      }
      //设置推荐
      @override
      Widget buildSuggestions(BuildContext context){
        final suggestionsList= query.isEmpty
          ? recentSuggest 
          : searchList.where((input)=> input.startsWith(query)).toList();
    
        return ListView.builder(
          itemCount:suggestionsList.length,
          itemBuilder: (context,index) => ListTile(
            title: RichText( //富文本
              text: TextSpan(
                text: suggestionsList[index].substring(0,query.length),
                style: TextStyle(color: Colors.black,fontWeight: FontWeight.bold),
                children: [
                  TextSpan(
                    text: suggestionsList[index].substring(query.length),
                    style: TextStyle(color: Colors.grey)
                  )
                ]
              ),
            ),
          ),
        );  
      }
    
    }

    完整的search_bar_demo.dart文件代码如下:

    import 'package:flutter/material.dart';
    
    const searchList = [
      'jiejie-大长腿',
      'jiejie-水蛇腰',
      'gege-帅气欧巴',
      'gege-小鲜肉'
    ];
    
    const recentSuggest = [
      '推荐-1',
      '推荐-2',
    ];
    
    class SearchBarDemo extends StatefulWidget {
     
      _SearchBarDemoState createState() => _SearchBarDemoState();
    }
    
    class _SearchBarDemoState extends State<SearchBarDemo> {
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: Text('SearchBarDemo'),
            actions: <Widget>[
              IconButton(
                icon: Icon(Icons.search),
                onPressed: (){
                  showSearch(context: context,delegate: SearchBarDelegate());
                },
              )
            ],
            ),
          
        );
      }
    }
    
    class SearchBarDelegate extends SearchDelegate<String>{
      //清空按钮
      @override
      List<Widget>buildActions(BuildContext context){
        return [
          IconButton(
            icon: Icon(Icons.clear),
            onPressed: () => query = "", //搜索值为空
          )
        ]; 
      }
      //返回上级按钮
      @override
      Widget buildLeading(BuildContext context) {
        return IconButton(
          icon: AnimatedIcon(
            icon: AnimatedIcons.menu_arrow, progress: transitionAnimation
          ),
          onPressed: () => close(context, null)  //点击时关闭整个搜索页面
        );
      }
      //搜到到内容后的展现
      @override
      Widget buildResults(BuildContext context){
        return Container(
           100.0,
          height:100.0,
          child: Card(
            color:Colors.redAccent,
            child: Center(
              child: Text(query),
            ),
          ),
        );
      }
      //设置推荐
      @override
      Widget buildSuggestions(BuildContext context){
        final suggestionsList= query.isEmpty
          ? recentSuggest 
          : searchList.where((input)=> input.startsWith(query)).toList();
    
        return ListView.builder(
          itemCount:suggestionsList.length,
          itemBuilder: (context,index) => ListTile(
            title: RichText( //富文本
              text: TextSpan(
                text: suggestionsList[index].substring(0,query.length),
                style: TextStyle(color: Colors.black,fontWeight: FontWeight.bold),
                children: [
                  TextSpan(
                    text: suggestionsList[index].substring(query.length),
                    style: TextStyle(color: Colors.grey)
                  )
                ]
              ),
            ),
          ),
        );  
      }
    
    }
  • 相关阅读:
    裴蜀定理
    上下界网络流
    寻找符合子序列要求的区间个数
    小猪分配 , 最大流
    floyd + 最大流 (奶牛分配问题)
    抛硬币问题
    消消乐
    Entity Framework(1)
    冒泡排序
    二分法查找数据
  • 原文地址:https://www.cnblogs.com/joe235/p/11224772.html
Copyright © 2020-2023  润新知