首页 > 解决方案 > 如何在这个 Flutter 应用中实现搜索

问题描述

我正在尝试向这个颤振应用程序添加搜索功能,因为它从中提取数据的 json 文件有 7000 个结果。

主要是我正在尝试搜索“ctry”和“peopnameincountry”。这是从https://www.youtube.com/watch?v=EwHMSxSWIvQ撕下来的

照原样..它在获取 json 列表时效果很好,点击显示详细信息页面也可以。

我只需要在主页上实现搜索,这样我就不必滚动浏览成千上万的结果。

感谢任何帮助..谢谢大家。

import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'dart:async';
import 'package:http/http.dart' as http;
import 'dart:convert';

void main() => runApp(new UnReached());

class UnReached extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new MaterialApp(
      title: 'Flutter Demo',
      theme: new ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: new MyHomePage(title: 'Unreached'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key key, this.title}) : super(key: key);

  final String title;

  @override
  _MyHomePageState createState() => new _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {

  Future<List<User>> _getUsers() async {

    var data = await http.get("https://cmfiflutterapp.s3-ap-southeast-2.amazonaws.com/UnreachedPeoplesGroup.json");

    var jsonData = json.decode(data.body);

    List<User> users = [];

    for(var u in jsonData){

      User user = User(u["ctry"], u["peopnameincountry"], u["population"], u["primarylanguagename"], u["biblestatus"],  u["primaryreligion"],  u["continent"]);

      users.add(user);

    }

    print(users.length);

    return users;

  }



  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      appBar: new AppBar(
        title: Text(widget.title),
      ),
      body: Container(
        child: FutureBuilder(
          future: _getUsers(),
          builder: (BuildContext context, AsyncSnapshot snapshot){
            print(snapshot.data);
            if(snapshot.data == null){
              return Container(
                  child: Center(
                      child: Text("Loading...")
                  )
              );
            } else {
              return ListView.builder(
                itemCount: snapshot.data.length,
                itemBuilder: (BuildContext context, int index) {
                  return ListTile(
                    leading: Icon(Icons.arrow_forward_ios),
//                    leading: CircleAvatar(
//                      backgroundImage: NetworkImage(
//                          snapshot.data[index].picture
//                      ),
//                    ),
                    title: Text(snapshot.data[index].peopnameincountry),
                    subtitle: Text(snapshot.data[index].ctry),
                    onTap: (){

                      Navigator.push(context,
                          new MaterialPageRoute(builder: (context) => DetailPage(snapshot.data[index]))
                      );

                    },
                  );
                },
              );
            }
          },
        ),
      ),
    );
  }
}


标签: searchflutter

解决方案


Try adding these function in your code:
import 'package:flutter/material.dart';
import 'dart:core';

class HomeScreen1 extends StatefulWidget {
  @override
  HomeScreenState createState() => HomeScreenState();
}

class HomeScreenState extends State<HomeScreen1> {
  var searchController = new TextEditingController();
  String search;
  List<String> _filterList;
  String _query = "";
  bool _firstSearch = true;

  @override
  void initState() {
    super.initState();
  }

  HomeScreenState() {
    searchController.addListener(() {
      if (searchController.text.isEmpty) {
        setState(() {
          _firstSearch = true;
          _query = "";
        });
      } else {
        setState(() {
          _firstSearch = false;
          _query = searchController.text;
        });
      }
    });
  }
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(widget.title),
      ),
      body: new Container(
        margin: EdgeInsets.only(left: 10.0, right: 10.0, top: 10.0),
        child: new Column(
          children: <Widget>[
            _createSearchView(),
            new Expanded(
              child: _firstSearch ? _createListView() : _performSearch(),
            ),
          ],
        ),
      ),
    );
  }

  Widget _createSearchView() {
    return new Container(
      decoration: BoxDecoration(border: Border.all(width: 1.0)),
      child: new TextField(
        controller: searchController,
        decoration: InputDecoration(
          icon: Icon(Icons.search),
          hintText: "Search",
          hintStyle: new TextStyle(color: Colors.grey[300]),
        ),
        //textAlign: TextAlign.center,
      ),
    );
  }

  Widget _createListView() {
    return FutureBuilder(
          future: _getUsers(),
          builder: (BuildContext context, AsyncSnapshot snapshot){
            print(snapshot.data);
            if(snapshot.data == null){
              return Container(
                  child: Center(
                      child: Text("Loading...")
                  )
              );
            } else {
              return ListView.builder(
                itemCount: snapshot.data.length,
                itemBuilder: (BuildContext context, int index) {
                  return ListTile(
                    leading: Icon(Icons.arrow_forward_ios),
//                    leading: CircleAvatar(
//                      backgroundImage: NetworkImage(
//                          snapshot.data[index].picture
//                      ),
//                    ),
                    title: Text(snapshot.data[index].peopnameincountry),
                    subtitle: Text(snapshot.data[index].ctry),
                    onTap: (){

                      Navigator.push(context,
                          new MaterialPageRoute(builder: (context) => DetailPage(snapshot.data[index]))
                      );

                    },
                  );
                },
              );
            }
          },
        ),
  }


  Widget _performSearch() {
    return FutureBuilder<List>(builder: (context, snapshot) {
      _filterList = new List<String>();
      for (int i = 0; i < snapshot.data.length; i++) {
        var item = snapshot.data[i];
        if ((item.toString().toLowerCase()).contains(_query.toLowerCase())) {

          _filterList.add(item.toString());
        }
      }
      return _createFilteredListView();
    });
  }

  Widget _createFilteredListView() {
    return ListView.builder(
        itemCount: _filterList.length,
        itemBuilder: (BuildContext context, int index) {
          return new Card(
            color: Colors.white,
            elevation: 5.0,
            child: new Container(
              margin: EdgeInsets.all(15.0),
              child: new Text("${_filterList[index]}"),
            ),
          );
        });
  }
}

推荐阅读