Search Filter with React Native on FlatList

前端 未结 10 1206
孤街浪徒
孤街浪徒 2020-12-28 08:33

I am trying to search through a flatlist based on a search bar text. The problem I am running into is that when the user mistypes...say they wanted to type \"burger\" but ty

相关标签:
10条回答
  • 2020-12-28 08:42

    My search method; from @metehan-senol

    search = (searchText) => {
     this.setState({searchText: searchText});
    
     let filteredData = this.state.data.filter(function (item) {
       return item.description.includes(searchText);
     });
    
     this.setState({filteredData: filteredData});
    };
    

    the search method of could be simplify and Eslint proof like so

    search = (searchText) => {
      const searched = searchText.toLowerCase();
      this.setState(prevState => ({
        searchText: searched,
        filteredData: prevState.data.filter(item =>
          item.description.toLowerCase().includes(searched)
        ),
      }));
    }; 
    
    0 讨论(0)
  • 2020-12-28 08:46

    Update: This blog can help you better understand the searching in a FlatList.

    FYI: If you have huge online data then you can also use algolia.

    I adjusted the above code for me in order to make it work properly. The reason is that when user removes the last wrong character, code search this new string from a previous search list (state) which does not contain all objects, although it had to search from a full list available. So, I have two list now. One contains full list of objects and second contains only rendered list of objects which is changing upon search.

    handleSearchInput(e){
        let text = e.toLowerCase()
        let fullList = this.state.fullListData;
        let filteredList = fullList.filter((item) => { // search from a full list, and not from a previous search results list
          if(item.guest.fullname.toLowerCase().match(text))
            return item;
        })
        if (!text || text === '') {
          this.setState({
            renderedListData: fullList,
            noData:false,
          })
        } else if (!filteredList.length) {
         // set no data flag to true so as to render flatlist conditionally
           this.setState({
             noData: true
           })
        }
        else if (Array.isArray(filteredList)) {
          this.setState({
            noData: false,
            renderedListData: filteredList
          })
        }
      }
    
    0 讨论(0)
  • 2020-12-28 08:49

    Make Search Bar Filter for List View Data in React Native

    For Real-Time Searching in List View using Search Bar Filter

    • We will load the list from the network call and then show it to the user.
    • The user can search the data by entering the text in TextInput.
    • After inserting the text SearchFilterFunction will be called We will compare the list data with the inserted data and will make a new Data source.
    • We will update the data source attached to the ListView.
    • It will re-render the list and the user will be able to see the filtered data.

    //This is an example code to Add Search Bar Filter on Listview//
    import React, { Component } from 'react';
    //import react in our code.
     
    import {
      Text,
      StyleSheet,
      View,
      FlatList,
      TextInput,
      ActivityIndicator,
      Alert,
    } from 'react-native';
    //import all the components we are going to use.
     
    export default class App extends Component {
      constructor(props) {
        super(props);
        //setting default state
        this.state = { isLoading: true, text: '' };
        this.arrayholder = [];
      }
     
      componentDidMount() {
        return fetch('https://jsonplaceholder.typicode.com/posts')
          .then(response => response.json())
          .then(responseJson => {
            this.setState(
              {
                isLoading: false,
                dataSource: responseJson
              },
              function() {
                this.arrayholder = responseJson;
              }
            );
          })
          .catch(error => {
            console.error(error);
          });
      }
      SearchFilterFunction(text) {
        //passing the inserted text in textinput
        const newData = this.arrayholder.filter(function(item) {
          //applying filter for the inserted text in search bar
          const itemData = item.title ? item.title.toUpperCase() : ''.toUpperCase();
          const textData = text.toUpperCase();
          return itemData.indexOf(textData) > -1;
        });
        this.setState({
          //setting the filtered newData on datasource
          //After setting the data it will automatically re-render the view
          dataSource: newData,
          text: text,
        });
      }
      ListViewItemSeparator = () => {
        //Item sparator view
        return (
          <View
            style={{
              height: 0.3,
              width: '90%',
              backgroundColor: '#080808',
            }}
          />
        );
      };
      render() {
        if (this.state.isLoading) {
          //Loading View while data is loading
          return (
            <View style={{ flex: 1, paddingTop: 20 }}>
              <ActivityIndicator />
            </View>
          );
        }
        return (
          //ListView to show with textinput used as search bar
          <View style={styles.viewStyle}>
            <TextInput
              style={styles.textInputStyle}
              onChangeText={text => this.SearchFilterFunction(text)}
              value={this.state.text}
              underlineColorAndroid="transparent"
              placeholder="Search Here"
            />
            <FlatList
              data={this.state.dataSource}
              ItemSeparatorComponent={this.ListViewItemSeparator}
              renderItem={({ item }) => (
                <Text style={styles.textStyle}>{item.title}</Text>
              )}
              enableEmptySections={true}
              style={{ marginTop: 10 }}
              keyExtractor={(item, index) => index.toString()}
            />
          </View>
        );
      }
    }
    const styles = StyleSheet.create({
      viewStyle: {
        justifyContent: 'center',
        flex: 1,
        marginTop: 40,
        padding: 16,
      },
      textStyle: {
        padding: 10,
      },
      textInputStyle: {
        height: 40,
        borderWidth: 1,
        paddingLeft: 10,
        borderColor: '#009688',
        backgroundColor: '#FFFFFF',
      },
    });

    Click Hear for more idea

    0 讨论(0)
  • 2020-12-28 08:50

    ref - https://medium.freecodecamp.org/how-to-build-a-react-native-flatlist-with-realtime-searching-ability-81ad100f6699

    constructor(props) {
    super(props);
    this.state = {
      data: [],
      value: ""
    };
    
    this.arrayholder = [];
    }
    

    Next fetching data :-

    _fetchdata = async () => {
    const response = await fetch("https://randomuser.me/api?results=10");
    const json = await response.json();
    this.setState({ data: json.results });
    
    this.arrayholder = json.results;
    };
    

    Next define searchFilterFunction :-

    searchFilterFunction = text => {
    this.setState({
      value: text
    });
    
    
    const newData = this.arrayholder.filter(item => {
      const itemData = item.email.toLowerCase();
    
      const textData = text.toLowerCase();
    
      return itemData.indexOf(textData) > -1;
    });
    
    this.setState({ data: newData });
    };
    

    rendering searchView:-

        <TextInput
          style={{ height: 40, borderColor: "gray", borderWidth: 1 }}
          onChangeText={text => this.searchFilterFunction(text)}
        />
    

    Don't forget to import TextInput from "react-native";

    0 讨论(0)
  • 2020-12-28 08:50

    Do filter by applying

    let filterData= data.filter((item) => {
      return item.name.toLowerCase().match(text)
    })
    if (!text || text === '') {
      this.setState({
        datasource: initial
      })
    } else if (!Array.isArray(filterData) && !filterData.length) {
      // set no data flag to true so as to render flatlist conditionally
      this.setState({
        noData: true
      })
    } else if (Array.isArray(filterData)) {
      this.setState({
        noData: false,`enter code here`
        dataSource: filterData
      })`enter code here`
    }
    
    0 讨论(0)
  • 2020-12-28 08:51

    FYI : data is the subtext to be searched, this is a basic search implemented as the data to be searched is looked into every list item of an array which is a copy of the actual array/array of objects and finally its state is set whether match found or not between 0 to (actualArray.length-1) and the temporary arrayData is rendered if there is at least one match else actualArray is rendered

    implementSearch(data) {
        temp = [];
        var count = 0;
        var searchData = data.toUpperCase();
        var arr = this.state.personDetail;
        for (var i = 0; i < arr.length; i++) {
          var actualData = arr[i].name.toUpperCase();
          if (actualData.includes(searchData)) {
            temp.push(arr[i]);
            count++;
          }
        }
        this.setState({
          tempArray: temp,
          matches: count,
          searchValue: data
        });
      }

    Hope this helps

    0 讨论(0)
提交回复
热议问题