5.5 Filter Cards
When you have a lot of cards in your deck, you might want to filter them by searching. In this lesson, we’ll add a search feature to our app.
1.Introduction2 lessons, 04:39
2.Get Started With Redux6 lessons, 41:43
3.Create React Components8 lessons, 50:18
4.Application Structure9 lessons, 56:09
5.Implement the App9 lessons, 1:31:34
6.Conclusion1 lesson, 01:32
5.5 Filter Cards
In a Flashcard application like ours, it's possible the decks will eventually get pretty large. I've created a words deck here and I filled it in with a bunch of words. It's not really that many but it's enough to make us wish that we could filter the deck in some way. What we'regonna do in this lesson is add a search box in our toolbar here that will allow us to filter through these words based on whatever we type into that search box. This may sound like a bit of a challenge, but I think you'll find that with redox, it's gonna be pretty simple. We're going to begin in our actions.js file by creating a filter action. So let's go ahead and create a filter card's action. And we'll expect to receive some kind of query as the parameter to filter cards. And the object that we'll return will have a type of filter cards and the data will be that query. Now we're gonna create a whole new reducer for this. Let's just put this right at the top. We'll export const and we'll call this card filter. And of course this reducer will take a state and an action. And then we're going to have our usual switch statement here. So we'll switch on action.type. And the case, of course, is going to be the filter card's action. And this will be really, really basic. If a filter card's action happens then action.data is the filter. So card filter has a property in our state should be what ever the query is ACTION.DATA. Otherwise we need a default case and the default case will just return whatever the current state is or an empty string. So if we're currently filtering and another action happens, that's fine we'll just keep our current filter. Otherwise if there is no current filter, we'll just use an empty string. Now, we need to head over to the toolbar, which is where we're going to add our search box. Now, let's start up here in our imports statements. Right now we have one action that we're importing, which is showAddDeck. Let's also import the filterCards action. Of course, usually inside of a component like this each action we import usually has a corresponding function inside of map dispatch to props and this is no different. Let's add onFilter function here. And this function is going to take a query as a parameter and we're going to dispatch the filter card's function. And we're going to pass a query in as a parameter. So now inside the toolbar, we take onFilter as one of the properties of our single Propst parameter. And now let's use that by adding an input box to our deck tools here. So we have our deck tools object and after these two links, let's add an input box. This input box is going to have a couple of parameters. Whenever it changes, so onChange, let's just inline a function here because it's gonna be so simple. We'll take the event as a parameter of course and we'll call onFilter. And we're gonna pass it event.target which, of course, is this input box .value. So whatever is currently typed into our search box will be our value there. Let's give this a class name of search and let's also give this a type of search. And finally let's add a placeholder value and we can just say Search Deck. Okay, there is our input. So, right now we have all the components in place to actually change our state. And we could actually see this in action if we head back to the producer and here inside card filter. Let's go ahead and just console.log the state at the very beginning of this function. Now if we come back to our page, you can see we have a couple of undefineds and an empty string already being logged. And if I go to the search box here and I start typing, you can see that as I type, we have whatever the current filter is being printed out to the command line here. So we can see that as we type each letter, we create a filter. However that filter is not yet being used anywhere. So how can we actually apply that filter? Well I think you know that the place to do this is with invisible cards. In the visible cards component, we have our mapStateToProps where we decide what cards will be displayed in our list. Now currently we're doing that based on the deckId which is fine. However we need to filter by both deckId and whatever the current filter is. Now to do our filtering we're going to install a package for us. We're gonna do npm install -- save fuzzysearch. This is just a handy little function that will take some text and a filter and it will return true if the filter is found within the text or false if it is not. Let's head back to our visible cards here, and let's go ahead and import fuzzysearch from fuzzysearch. Now, underneath here, let's create a matches function. This is gonna take the filter text and a card. And in here we'll just do fuzzysearch based on the filter and card.front or, and let me duplicate this, and we'll say card.back. So basically our matches function here takes the filter and the card object. And we'll do fuzzysearch on the card.front or the card.back. And this way if either of these return true then the function will return true and we know that the card will be included in the results shown. So now down here in mapStateToProps, first where we get our cards here we also need to get our card filter property from our state. And then down here inside of our cardstock filter call, we can say we'll return a card if c.deckID === deckID. And if it matches the card filter, excellent. So now we can head back to the browser and let me minimize our console here so that we can see more of our cards here. And now I'm gonna start typing. So if I type an m, we're immediately filtered to only six different cards. If I filter again, filter to three. I can type again and we're only filtered to one. Excellent, and we can go ahead and filter these cards however we want. Now the neat thing about this is that the filter will hold even as we add new cards. So if I filter to z, we have no cards. However, if I add the word zebra, then you can see that it will show up as the one card that we have. All right. So now we can filter cards. And as kind of a small bonus because we gave this input text box a type of search, our browser gives it this little clear button here. So I can click that to clear the box and we're back to all of our cards. All right. So now we have all of the features of our application in place except for the one main feature that we want, which is studying our deck of cards. So, we'll tackle that in the next lesson.