Build a Shopping Cart with React and TypeScript - Tutorial

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hello and welcome to this little tutorial here on free code camp i'm thomas weber farq i'm a developer from sweden and i've created a few videos for free code camp now i love free code camp they have a lot of great stuff so that's why it's so fun creating videos for them i just want to say also that i have my own youtube channel where i publish weekly videos so search for vapenfarc or check out the link down below here and i also have a site where i have my premium courses if you want to get more in-depth knowledge of stuff i do a lot of stuff on react and gatsby for example so visit my site if you like my teaching style and want to support me so let's get started hey hey what's up in this video we're gonna create a cool little maybe not that cool but a little web shop with a cart so it's going to look something like this because i found this fake store api where we can get some data to create this little store so that's what i'm using here and you can add stuff to the cart as you can see and it adds them up here and then we have the cart button here and we have these nice little buttons where we can change the amount and it will show the total and of course is this if this was a real shop you would have a button here to go to the payment and stuff like that but i won't do that and i'm going to use material ui i'm going to use react query and typescript and style components for this one so it's going to be a lot of learning in this video i think go back to your terminal and inside somewhere where you want to have the application i have mine in a folder that's called react shopping cart so we're going to create our project mpx create dash react dash app and then we name our project i think it's going to be named react shopping dash cart yeah then we use the dash dash template and typescript this is how you set up a typescript application with create dragged app and we press enter it will take some time so i'm going to skip this okay that went well we have our application and make sure to navigate inside of the folder cd react dash shopping dash cart clear the console and then we're going to install our dependencies so first we're going to use material ui so there are a couple of things that we need from that library i'm going to install the core and also the icons because i have an icon up here you can see in the store that i use for this one so mpm i at material dash ui forward slash core that's the core library and then we need icons so at material dash ui forward slash icons so that's everything we need for the material ui and then we're going to install react query so mpm i react dash query so i'm going to clear the console where one more thing to install and that's the style components and you may think well why are you using style components when you're using material ui and that is because i don't really like the way that i style stuff in material ui i think there's a lot of great stuff in the library itself but the styling is in my opinion not good so that's why i use style components i will get much cleaner code instead of using their internal way of styling things so that's why but it's highly opinionated of course so if you want to use the internal stuff instead you can do that but i won't show it in this tutorial so i'm going to install mpmi styled dash components and as we're in typescript land now we also need to install the types so we have add types forward slash style dash components all right we can open up our code like this and i'm going to do some cleanup first we don't need app.css we don't need app.test we don't need the index.css not the logo and not the report web vitals and the setup tests so delete those ones and inside of the index.tsx we can remove some stuff remove the report web vitals remove the index we can also remove this one here and actually we can't use the strict mode as we're going to use the drawer in material ui or we can use it but we will get a warning so i'm going to remove strict mode they haven't fixed that yet i hopefully hopefully they're going to fix it soon it will throw a warning in the console so for now i just remove it and inside the app.tsx file we can also do some cleanup you can see that this one is grayed out and that's because we don't need to import react when we're using react 17 and above as we use now so we remove that then we remove the logo and we also remove this one and here we can just remove everything that has to do with a header and we can say start i like to have an arrow function so i'm going to convert this one to an arrow function you can do whatever you want something like this save it and i'm going to do one more thing before we start up the application to see that it works so we have something to start from and that's inside of the index.tsx file we're going to set up react query so i'm also going to bump this one up maybe like this so we import query client and something that's called query client provider from react-query right then we're going to wrap this app with the query client provider and it takes in a prop that's called client and this client is going to be something that we create here so we have a const we can call it client and we create a new query client and we call it like this and this will make sure that we have a client in this const so we can provide this client to the client client to the query client provider oh long names here and i'll move the app inside of this one and this will make sure that we can use react query in our application so i save the file and then i go back to my console and i'm going to type in mpemstart yeah i already have my other application running on port 3000 so this one is going to be on port 3001 instead so i'm gonna open up that here localhost and i'm gonna move it here so this one is the application we're working on and we also have the finished application there so it seems to be working just going to check the console great so that's the setup we're going to move on and create the different items for the shop itself and then lastly we're going to create the cart and items for the cart all right we're going to be inside of the app.tsx file and first we're going to start with some imports or it's actually quite a lot of imports we need for this one so first we're going to import use date from react then we're going to import use query from react query and then we have some components so i marked them with components and i'm going to import some stuff from the material ui that we're not going to need yet but i'm going to import them now so that we have them later so first i'm going to import a component that's called drawer from at material ui forward slash core forward slash drawer capital d all right then i'm going to import something that's called a linear progress from at material ui forward slash core forward slash linear progress then we have the grid so import grid from at material ui forward slash core forward slash grid and we're gonna have the icon for the shopping cart import add shopping cart icon from at material dash ui forward slash icons forward slash add shopping cart yeah add shopping cart and then we have a badge so import badge from at material ui forward slash core badge so that's everything in this component that we need from the material ui library we're also going to import some other stuff here later for example the cart and the item so that's what we're going to do later and we're also going to have some styling for this one so i'm going to mark this one with styles and for now i'm just going to scaffold out the style component and i like to keep them in a separate file so i'm going to create a new file that i called app.styles.ts and in this one i'm going to import styled from style components and i just scaffold out the component that i call wrapper so i have to export it as i want to import it in my app export const wrapper equals style.div save it and go back to the app.tsx and now we can import it import wrapper from dot forward slash app.styles and that's our import for now and as i told you i'm gonna use an api that's called fake store api i haven't heard of it before i just googled some stuff because i needed a fake store api for this application so that's what i'm going to use so we have to create a fetching function for it so go back to the code outside of the app itself i'm going to create this fetching function because we don't need to recreate it on each render so const get products equals and this is an async function as we're going to fetch from an api i'm going to wait and have parentheses and i wait again so this weight inside of the parenthesis is going to be for the api call itself and this the weight is going to be when we convert it to json because converting to json is also async so a weight fetch i have a string with a url https for column forward slash forward slash fake store api dot com forward slash products like this and here at the end after the last parenthesis i have dot json and convert it into json so that's why i have the double weights we're also going to type this one the data that we get back from the api has a structure of it and as this is typescript we want to type that structure so this structure that i'm going to type now i can mark it with types is from the api and we're going to see this structure when we get the data back so i'm going to export this type because i'm going to use it in other components also i call it car item type and i specify my type so the id is going to be a number the category is going to be a string the description is going to be a string the image is going to be a string the price is going to be a number the title is going to be a string so this is all the properties that we get back from the api but i want to add my own property and that's the amount because we need to keep track of the amount in our cart so i add the amount and i type this as a number so that's the types so now we can type the return type of this get products function so colon and this is a promise as we're using async and weight and the promise is what's called a generic in typescript so we can provide it with the type that we want so promise and then we have angle brackets and inside angle brackets we specified the type that we created up here cart item type so there you have it that's the correct type for the get products function all right i think we're ready to go to actually fetch some data so inside our app we're going to use react query to fetch our data so i create a const either structure out the data the boolean that's called is loading and the error equal and i call the use query hook and this one we can also type the return type of the data that we get back because this use query is also generic so we have angle brackets and we type it as the same type card item type and this is an array and actually this one should also be an array up here i missed this one because the data that we get back is an array with all the card items so we specify this as an array also all right so that's the type for the use query then we have the query key and it's a string we can name it to whatever we want i name it products and then this is getting quite long here we have our fetching function here so we have the query key a comma and then we provide it with a function get products like this do some order formatting we'll place it on its own row and this should be get products that's the function that we created up here and now we can actually console.log out some data to see that we get something console.log data save the file go back to the application reload it you can see that we have the data here and here's the structure that i typed in my type the category description id image price title and you can see that it missed that amount prop that i added myself but otherwise it looks exactly the same when i specified i typed i first looked at the data and then i know the type so i could create that type for it all right so we know that we have some data we're just gonna scaffold out some stuff here before we create our jsx we're gonna have a few functions inside of this one we're gonna have a function that's called get total items and for now i just create an empty arrow function we're going to return null for this one and we're going to have one that's called handle add to cart and i also specify it as an empty error function and the last one is going to be handle remove from cart and i return now and of course we're going to return back to these functions later all right and before we return the data the actual data with the products we can check if is loading and if we load in something we can return from the material ui library we have something that's called a linear progress we also have a circular progress if you want to have that that one is a little bit more tricky to get centered in the screen so this one is going to be displayed at the top and i'm going to show you that in a second and also if we have an error we can return something return a div that says something went wrong something like this save it go back to the application and we reload it you can see this progress bar here when we load the data so i think it actually looks kind of nice to have it up here at the top like this otherwise you could have a circular progress in the middle here or something and that's of course the linear progress that we imported up here before from the material ui core so we have some data and we need to to create our grid with the products but first we actually want to create a component for the grid itself because if we look here we have these nice little cards it's going to be a separate react component so we can create that one first so inside our src folder we're gonna create a new folder that we call item capital i and inside this one we're gonna have two files we're gonna have the item itself so item.tsx and we're also going to have a file that's called item.styles.ts and that's because i want to have my styles outside of the component itself so inside items.styles we're going to import styled from style components and for now i'm gonna export const i call it wrapper again and it's gonna be a style div and we have double back ticks like this so we're going to fill this in with styles later but first i want to create a component itself so go inside of the item.tsx file and up here we're going to import the button from at material ui forward slash core button then we're going to import those types that we created in this app component up here so that's why i export them here so that we can reduce them in other components so i marked this one with types and i import card item types type without an s from dot forward slash app and then we have the styles import wrapper from not forward slash item dot styles right that's every input we need to do and we're in typescript so we have to type some props for this one type props because it's going to take in two props we have the item itself and that's why we imported this one here this item prop is going to be of the type card item type and then we're going to have the handle add to cart that's going to be the function in the app here this one handle add to cart and we could actually change this one a little bit now this handle add the cart is going to take in an item i call it clicked item and it's going to be able to type cart item type like this so you can see the type here if we hover over handle add to cart we have the type here it will only accept this type so that's why we also have to type this correctly in the prop in the item.tsx so this type is going to be clicked item and it's going to be of the type cart item type and it's going to return nothing so it's going to return void so this is the correct type that one and then we can create our component const item it's going to be a colon and it's going to be a react dot fc that's the type for the react functional component and this is a generic so we have the angle brackets and we give it the props so this is how you specify and type the props in a typescript react component all right then we have an equal sign parenthesis with the structure of the props the item and the handle add to cart and then we have an error function and we can make an implicit return because we're only going to return jsx in this one so first we have the wrapper like this i'm going to have the image so imd the source is going to be from the item dot image we can set an alt on this one and we set it to the item.title and these are the properties from the data in the item that we get back from the api of course then we have a div i'm going to have an h3 tag with the item dot title and as we're in jsx i have to use curly brackets to grab these values then we have a p tag i have a new pair of curly brackets and i'm going to grab the item.description then we have another h3 tag for this one and first i'm going to have a dollar sign because the price is going to be in dollars and then i have a pair of curly brackets and i grab the item.price like this and then we need to export default item and yeah of course we need to have the button also for adding to the cart so down below here where after the after the div we have the button we're going to have an on click on this one we have an inline arrow function and we call the handle add to cart and we give it the item and i need to have an inline arrow function here because we need to send in this little prop here to this one also so that's why we can't just do it like this because this will trigger it right away so that's why i use an inline function you can also create a function up in the component if you want to do that but in this case i think it's neat to have this little inline arrow function it will be fine so the button we close it and it's going to say add to cart so there you have it this would be this component we're going to style it but first i want to see if our data works so i'm going to go back to the app.tsx up here i'm going to import my component import item from dot forward slash item and forward slash again an item then i go down here and in our jsx in our return statement here i'm going to create parentheses and first we're going to have a wrapper like this and inside a wrapper we can map through our data and see if this works so first we're going to have a grid so i use the grid component from material ui this is the container so i mark it with a container prop and i'm going to set the spacing to 3 and then we're going to have a grid item inside of this one and this is the item that we first have to map through our data and create the grid item for each item in the data so i have curly brackets i have the data i use a question mark because it's going to complain otherwise if it's undefined so if you use a question mark it will just return undefined if it can't find the data dot map we map through the data then we have the item and we know that this item is going to be a card item type card item type i don't think actually that we need to specify this because it is already specified it already knows that this data will be of the type card item type or undefined so i try to not set it at all yeah it seems to be working so we we map through the item and i'm gonna make an implicit return because we're returning jsx only so i have parentheses and then i have a grid item again from the material ui i marked this as an item not the container that i did there i set the key to the item.id because we're mapping through stuff in react and we need to have a key and then you can set how this is grid is going to be structured on different viewports so the extra small is going to be set to 12. small medium is going to be set to 4. this is quite similar to the bootstrap if you have used bootstrap before so we have the grid and then inside the grid i'm going to use my item component that that i just created and we give it the item prop we give it the item and then we have the handle add to cart it's going to be the function handle add to cart and then i self close this one do i dare to save it go back to my application yeah you can see that we have our items here but it looks like crap and that's because i haven't styled it yet so that's what we're going to do go back to the application and inside the items.style in the items folder we're gonna style this little sucker okay so we have the wrapper so first we're gonna display it as a flex not full screen edit why did it say like that yeah that's because this one disappeared display flex i'm going to justify the content to space between i'm going to set the flex direction to column the width is going to be 100 percent the border is going to be one pixel solid and light blue the border radius is going to be 20 pixels maybe and the height is going to be 100 and then we're going to style the button so we can specify it inside of the wrapper here that's so great with style components you can nest stuff like this i'm going to set the border radius to 0 0 20 pixels and 20 pixels and i'm going to explain that why later then we have our image so we style the imd the max height is going to be 250 pixels the object fit is gonna be cover and the border dash radius is gonna be 20 pixels 20 pixels zero zero and the last one we're gonna style is the div and we can check it out here we have a div here inside also so we're going to style this once so back to the item styles the div the font family is going to be ariel not font font family font family ariel i set the padding to one rem and i set the height to 100 percent and hopefully when we save this and go back to our application you can see that it looks a lot better now and this if you see here when i click the button you can see that i style the corners otherwise this one here will go over the corner of the card itself so that's why i set the border radius on the bottom and i think it looks pretty nice and you can see that it restructured itself now on small viewports so you can tweak this yeah maybe a little bit better if you want to do that i think you get the id here on how stuff can look so that's the items and we're going to continue on creating the cart next so we have this nice little icon here to show and hide the court and we're going to add some stuff to the court and do some calculations and stuff like that the first thing we're going to do is to scaffold out some stuff in the app.tsx file and up here at the beginning of the app component i want to create a few states that we need for our cart it's a const cart open set cart open or you can call it cart is open or something if you want to do that because this is going to be a boolean that telling us if the card is open or closed equal use state and we set it to false initially then we need a state with actual items that we have in our cart so const card items items with an s set cart items equal use state and this one is going to be an array and we have to type this one i want to set it to an empty array initially so i create an empty array and then i specify the type s cart item type like this and this will create the correct type if we hover over here you can see that this is the card item type it's an array of card item type so that's the states that we're going to need for this one and then we can scroll down here just at the beginning of the wrapper inside of the wrapper we're going to create our drawer and that's a component from the material ui drawer it takes a prop that's called anchor and we want it to be anchored to the right of the screen open that's going to equal the state that we created cart open state up here that we just created so it's going to flip between true and false shouldn't be a coma there and then we have a prop on close so we have an inline arrow function set cart open and we set the value to false then we close it like this and inside of drawer we're gonna have our cart we haven't created that component yet so we can just type in cart goes here like this then we need our open and close button for the cart and for this one i actually want to style this button a little bit so i'm going to show you a different way of styling the button last time for the item i styled the button like this but you can also style a button by providing it to the style component itself so inside our app.styles file we're going to create a new style component and for this one the wrapper we can actually just set the margin to 40 pixels for that one that's the only style that we're going to need i just give it some morgan so it won't go to the edges of the screen and then we create a new component export const i call it style button equal style and then we can provide this function instead of doing backticks and creator styles we can have a parenthesis and provide it with a component that we want to style so i'm going to import something that's called an icon button from material ui so from at material dash ui forward slash core forward slash icon button and then i can provide this icon button to the style component like this and then we have the regular backticks for styles and we can type in our style just as we always do with the style components position is going to be fixed the set index is going to be 100 we want it to be placed over the other content we set it to right 20 pixels and top 20 pixels and as usual you can tweak these values if you want to do that so we save the file go back to our app component and we can create our button so just below the drawer now first we have to import it of course so up here where we have the styles wrapper we're also going to import the styled button like this then we move down here just below the drawer we can use the style button and this is now a button element or an icon button from the material ui so we can use the same props as usual we can use it just as a regular button from the material ui so an on click handler an inline arrow function set card open and we set it to true when we click this button and this button is also going to have something that's called a batch if we look at the finished application i have this red little badge here that shows how many items there is in the cart and we're already importing this as we did before so we can use this badge now from material ui so badge the badge content and we have created a function for this but it's empty now but it's the get total items and we give it the card items then we set the color to error and that will make it red and then inside of here we have our add shopping cart icon that we imported from material ui also you can see here that typescript complains because we haven't specified that this function has a parameter so we can't send in an argument to it expected zero arguments but got one so we can adjust this one so go up here to the function this one is going to take in the items that's all the items so we have the type of cart item type and an array and this will make this arrow go away hopefully like this sometimes it's a little bit slow actually before it kicks in save the file make sure that it works and we have our button here you can see and it opens the cart and we can close the cart by clicking outside of the cart you can of course add a bottom there if you want that also i think this is sweet actually i like this sidebar from material ui and no we don't have any items here so this one will show this badge when we have the items so we can actually create this get total items function now we remove this null and i'm just going to put it on the other row you can have these curly brackets if you want to have that and create a return statement but i'm going to do an implicit return here as this is an arrow function so it's going to be a one-liner so from the items that's the items that we send into this function we're going to reduce and first we have the accumulator that one is going to be a number it's going to return the total number of the items in the cart and then we have the items the items is already specified up here so it will know that this one is of the type card items type right then from the accumulator we add the item dot amount and we initialize it with zero shouldn't say items it should say item without an s so this will iterate through all the items in the cart and it will use the property amount and add up the amount and that will give us the total amount that's in the cart and the accumulator we give it an initial value of zero so that will add up so 30 starts with zero then it adds the amount for each item but it won't show us anything yet of course because we don't have anything and we can't actually put something in the cart so we're going to see this in action later okay so we have the drawer and we have the button for the card i think it's time to create the card itself so inside the src folder we're going to create a new folder that's called cart and inside of that folder we have a file that's called cart.tsx and we also have a file for the styles just as before card.styles.ts we can start in the style file we import styled from style components like this then we create our component we're going to have a wrapper again so export const wrapper equals a style and this one isn't a div i think it's more appropriate to have it as a side because it's kind of a sidebar a style on a side element double back ticks and then i have the css and this is not much so we can actually do it already now i set the font family to arial i set the width to 500 pixels for my sidebar i set the padding to 20 pixels and this should be it i think save the file go back to the cart dot tsx file and we can start by importing some stuff as we always do and also we're actually going to have a cart item so i think we can create that one also and just scaffold it out so we can use it in our cart so inside src folder create a new folder cart item and just as before we have two files cart item dot tsx and new file cart item dot styles dot ts and we start in the styles file import style from style components we export the const that we call wrapper for this one also and it's going to equal style.div double back ticks and then we have our css and i think yeah no we can wait with the css i'm just going to leave this empty for now so save the file and we go back to the card item and first we're going to import a button from at material dash ui forward slash core button then we needed types so import card item type from dot dot forward slash app and then we have the styles import wrapper from dot forward slash car item styles and then we scaffold out this component const car item is going to be a react.fc a functional component equal and for now we leave it empty like this we can just create a div that says card item and we export default card item and save the file so we're going to come back to this later of course and create that component but for now we go back to our cart and we can import this cart item from dot dot forward slash cart item and cart item then we have our styles import wrapper from dot forward slash cart dot styles and we have our types import card item type from dot dot forward slash app you can see that i also comment here everything you don't have to do this actually in a small application like this but it's a habit i have when i work on larger applications that i i like the common stuff here on the imports because if you have 20 or 30 imports so you quickly can see what you're importing but you can of course remove them like this if you don't want to have them because we only do three imports here right and this one is going to have some props type props we have the card items and by now we know that these are going to be the card item type and it's an array because this is the cart so it's going to receive an array with all the items that's in the cart then we're going to have add to cart that's the function that we created in app we know that this one has the type parentheses clicked item that's the parameter for that function and that one is going to be a car item type and it's going to return void it returns nothing and then we have remove from cart this one is only going to take in the id and it's going to be of the number type and it return nothing because when we remove something we don't actually need to add any elements because we already have all the items in this array that we're going to remove from so that's why we only need the id for that one okay so that's the props so we can create our component const cart it's a react dot fc a functional component we have the angle brackets and we give it the props because this is a typescript generic so that's why we can send it in like this and then we have the props so every parenthesis with the structure out the card items the add to cart and remove from cart and we have an arrow function and this one is going to make an explicit return so we have curly brackets and we have the return statement like this so first we return the wrapper that's the style component we created then we have an age to tag your shopping cart or whatever you want to type in and then we can also type in some text if we don't have any items in the cart so i have curly brackets and i check if cart items dot length equals zero then i have a question mark it's a turner operator i display a p tag no items in cart and otherwise we display null we display nothing so this will display this text if we don't have any items in the cart and then we can map through our items card items dot map we have the item we don't have to specify the type because it will know that it's of this type you can see here card items is of the card item type so we don't have to specify it here like this and i make an implicit return on this one and i'm going to return the cart item and for now i just do like this we're going to come back to this one very important to export default cart otherwise it won't work so we're going to come back to this one and give it the correct props but for now i'm going to go to the app dot tsx file and we're going to import cart from dot forward slash cart forward slash cart like this we go down in our jsx instead of cart goes here we're gonna use our card component and you see that it complains because it wants the props so we have to specify the props also for the cart so we have the cart items it's going to be the cart items then we have add to cart it's going to be the handle add to cart i can actually move them down to their own row and then we have remove from cart it's going to be the handle remove from cart save the file and we go back and see what we got so far you can see that we have our shopping cart here no items in cart because we don't have any items in the cart all right so we go back to the cart we know that it's working and this cart item here we're going to provide it with the correct props first as we're mapping through these items we need to set a key and the key is going to be the item.id then we have the item then we have the add to cart function add to cart and we have remove from cart and remove from cart and now you can see the complaints because we haven't created this item component yet so that's what we're going to do next because now it complains and it breaks the application but keep calm we will fix this soon so we are sending in the props to the card item and we can build our card item component so go back to the cart item file not the styles right now the file here and we import everything that we need here and we can create the props for this one so type props equal we have the item it's going to be of the cart item type this is a single item so we don't have an array here and then we have to add to cart it's going to be the clicked item and cart item type and it's going to return void it returns nothing and then we have remove from cart this one is going to be an id with a number and it's going to return nothing so void and we give it these props inside of angle brackets just here we did before so now you can see cart won't complain anymore because we have the correct props typed for us so that's sweet and our application should be working again yeah it is right back to the code we can still make an implicit return but we're going to have parenthesis here and we're going to have the wrapper and first inside of the wrapper we're gonna have a div oh what happened yeah okay like this then i have an h3 tag and there i'm gonna display the item.title insider curly brackets of course because we're grabbing these items now and we haven't destructed out the props i need to do that also it's up here i just structure out the item the add to cart and remove from cart and this item of course i can show you in the finished one is this item here that i create now so i have the so the h3 tag is going to have this title and then we have these buttons to add and remove stuff here so that's the one that we create now all right that's the title then we have another div and for this one i'm going to create a class name it's going to be information this one is going to hold a p tag with price i have a dollar sign and then i have curly brackets don't mistake this for a template literal because this is just a dollar sign that i print out it has nothing to do with these curly brackets here i'm going to grab the item.price for this one and then we have another p tag we're going to calculate the total for each item so the total is going to be yet again we have a dollar sign in front of our price that we're going to show and i have a pair of parentheses and i take the item dot amount times the item dot price and then i need to remove some decimals so i'm going to have dot 2 fixed and a 2 that's going to give us 2 decimals all right so that's going to be the total that we can see if i go back to the application [Music] the finished one going to be these ones here that we created now and now we have to create the buttons and the total amount here so i create another div with a class name of buttons i create a material ui button the size is going to be small i'm going to disable elevation so i don't have any drop shadow on it the variant is going to be contained as i want it to display with a background in the button and then i have the on click handler it's going to be an inline arrow function and i'm going to call the remove from cart and i'm going to provide it with the item dot id now we close the button and inside the button i'm just going to type out the minus sign right then in the middle we're gonna have a p tag curly bracket item dot amount and curly bracket and then we can actually copy this button here paste it in below the size is going to be the same disable elevation and contain is going to be the same the on click is going to be add to cart instead and this one takes in the complete item not only the id so i'm going to remove id and give it the item and this one is going to have a plus sign instead so that's the balance and then we need to have the image also and the image is going to go below the divs here last before the ending wrapper tag so i have imd src equal the item.image and i set an alt to the item.title on this one we can self-close it like this and this should be the item for the cart save the file just go back to check that everything works it does but we can't see any items because we don't have any way to actually add it to the cart so that's what we're going to do next we're going to create the function for adding and removing stuff in the cart and we're also going to display the total amount in the cart we move back to the app.tsx file the main component for the application so to say and we need to create our functions for adding stuff to the cart and also removing stuff from the cart we already scaffold out this handle at the cart so we remove this null create curly brackets and inside we're gonna do some stuff when we click this button we're going to set cart items and this is the setter for the state and we can always get the previous state from this one so prev you don't have to call it prev but i like to call it prev as it stands for previous in my mind at least so we have prayer and then we have curly brackets i'm going to make an explicit return on this one and first is the item already in cart already added in the cart because we have to take into consideration here when you click add if the cart is empty we need to add that item to the cart if it already exists in the cart we should only add on the amount on that item so we should modify the item that exists in the cart so we can check if this one is in the cart and remove the sidebar i create a const is item or is item in cart maybe to be extra specific here from the previous state i'm gonna find i have the item and i check if the item dot id equal to the clicked item dot id so i check if the item that i clicked on exist in the cart by by comparing these two ids i loop through the stuff it's going to return true or false if it finds it in this array right then if is item in cart if we have this item in the cart we need to do some stuff so if we have the item in the cart we need to update the amount on that specific item and we can do that by mapping through the items so return prev.map we have the item an arrow function and we can make an implicit return on this one we have the item dot id if that one equals the clicked item dot id i create a turner operator it's going to be on multiple rows here but i have the question mark then if it finds the item we're going to update that amount so i return an object with curly brackets i spread out the old item and then i have the amount property i'm going to update this property item.amount plus one if we find an item otherwise we have a colon and we're just going to return the item as it is we don't do anything we only update the amount on the item that we actually clicked on so this is if we have an item in the cart otherwise we can mark it as first time the item is added we're going to return and we have the array we spread out the previous state inside of the array and we add this new item so we spread out the clicked item inside of curly brackets we're creating an object here and we set the amount to one so this is hopefully going to add this item to the cart so i'm going to go through it again here the first thing i do is i call the setter for the card items if we use a function for the setter we will get access to the previous state so i checked in the previous state if this item already exists because if it exists we need to update it instead of adding it to this array and if it exists i'm going to loop through all the items until i find the item that i clicked on and i'm going to add one to the amount for that one otherwise if this is the first time that we click on this item to the cart the first time we put it in the cart i return an array with all the previous stuff in the cart i spread it out here and then i add this item to the array here where i spread out the clicked item but i set the amount to one so we can see if it works save the file go back to the application reload it just to be sure i click add to cart and you can see that it adds it up here and this actually looks awesome already but it doesn't look awesome here it's quite big we haven't styled this once yet so that's what we're going to do next we're going to style this cart item so that's what we're going to do now go back to the code and inside the cart item dot styles we have this wrapper first we're going to display it as a flex we justify the content to space dash between we set the font family to ariel border dash bottom is going to be one pixel solid light blue we set the padding dash bottom to 20 pixels we can actually see how it looks like go back to the application yeah we have some styling here right then we're going to style the div we set that one to flex 1 and then we have the class that we call information and also the class that's called button so we style these ones in one go we display them as a flex and justify content space dash between and then we're going to style the imd the image max dash width is going to be 80 pixels for this one and we set the object fit to cover and the margin dash left is going to be 40 pixels save it go back to the application and you can see that yeah it still doesn't look right we have to fix this it's some stuff with this one here the buttons information i'm gonna go to the cart item no it's the bonus class name buttons yeah buttons with an s change this class and add an s it should say buttons and i'll go back and you can see that it looks great now i think but we can only add items and you can see this is what's so great about reactos we can reuse stuff we have created this component and we use the same function for adding stuff and it just instantly works because it's the same function that we use here so the thing we have to do now is to create our function for removing items in the cart so go back to the code and inside app.tsx we have our function that's called handle remove from cart and this one is going to have a parameter that's called id and this one is going to be a number we remove null create curly brackets and yet again we're going to set cart items we have the previous state an arrow function we can make an implicit return and for this one i'm going to use reduce so i have the prev dot reduce parenthesis and another pair of parentheses i have the accumulator and i have the item arrow function and i make an explicit return on this one i think it's more readable we also need to specify the initial value for the reduce otherwise typescript will complain for us so we have a coma we have an empty array and we're going to specify this as cart item type and an array and then it won't complain for us later and the first thing we have to do in this reduce is to check if if the item dot id equals to the id if we're on that item in the array that we clicked on we're going to do something so we have curly bracket and we have another if statement because we want to check if the item amount is 1 then we're going to remove this item from the array when we click the minus sign because we go from one to zero and it's no longer in the cart so if item dot amount equals to one we're going to return the accumulator we remove this item from the array so we only return our accumulator and do nothing otherwise we're going to return an array we spread out the accumulator the previous array we create a new object where we spread out the item we have the amount and the amount is going to be subtracted by one so from the item dot amount we have minus one so if we're on the item that we clicked on we first check if the amount is one then we remove it from the array otherwise we remove one from the amount and if we're not on the item that we clicked on we have the else statement here we're going to return an array we spread out the accumulator and we return the item as it is we don't do anything with item and i have some stuff here that is not correct [Music] why is it so i guess it is yeah this one here should of course remove the coma and it should go inside of here instead like this so the reduce starts here and then we have a coma and then you have the array and we specify it as a card item type like this so i'm going to go through it again just to explain so we set the card items we have the previous state i call the reduce on the previous state we have an accumulator that starts with an empty array that we specify as the card item type an array of card item type then i check if the item id is equal to the id here that gets sent in as an argument to this one we know that this is the item that we clicked on and if the item amount equals to 1 i return the accumulator so i skip this item and this will delete it from the array otherwise i return a new array where i spread out the accumulator and i have a new object where i spread out the item and i subtract one from the item amount so we remove one from the amount otherwise we return the item as it is so we have the accumulator and the item in this array right save the file we can go back to our application and see if it works and it does and you can see that it calculates this beautifully when we remove stuff here so i'm pretty happy with this we only have one more thing to do and that is to display the total amount in the cart so go back to the code and inside the cart that's why we also made an explicit return here because we're going to create this function here so up here at the top of the cart component we're going to create a new function const calculate total equal it's going to take in the items that is going to be of the card item type and array we have an error function i make an implicit return so i move down to the row below and the items dot reduce yet again i'm going to use the reduce method we have the accumulator it's going to be a number and we have the item the item we don't need to specify because it already knows that this is for the cart item type so we have an arrow function and accumulator and to the accumulator i'm going to add the item dot amount times item.price and then i have a comma and specify the accumulator to be zero initially so we have the calculate total function and if we move down here just below the card items we create an h2 tag total colon and then we have the dollar sign again just to display it in front of the price current brackets we call the calculate total we give it the card items and this is fine but i want to remove some decimals on this one also so i have dot 2 fixed and i give it a 2 because i want 2 decimals save the file go back to the application and you can see the total amount and there you have it we have a fully working cart at least some of it we can't actually buy something but yeah you know what i mean so i think this actually is a good practice because you can use this in the real world so to say because this is not actually far from a lot of stuff you probably will do if you work on a real world application
Info
Channel: freeCodeCamp.org
Views: 103,655
Rating: 4.954051 out of 5
Keywords:
Id: sfmL6bGbiN8
Channel Id: undefined
Length: 66min 44sec (4004 seconds)
Published: Thu Jan 21 2021
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.