Transcript for:

in this course we are going to learn to build apps for multiple platforms like Android iOS web and desktop from a single code base using the flutter framework this course is specifically designed for non-programmers now if you're someone who has previous coding experience in another language don't worry since this course is designed for everyone even those with coding experience you can follow along at an accelerated pace so I'll recommend you to watch the videos at 1.5 x speed for topics you're already familiar with like variables functions classes and so on this course solely focuses on flutter app development and does not cover any database related topics we'll create three apps in this course first one is a simple currency converter app to get started second is the weather app where all the weather data is being fetched from the web and the last one is a shopping app by building these three apps we learn various aspects of flutter such as widgets layouts responsive layouts State Management Etc additionally I'll provide you with a brief overview of the inner workings of flutter like understanding how flutter handles surrendering State Management and more behind-the-scenes stuff I've covered database related topics in separate tutorials which you can easily follow along after watching this tutorial before we dive into flutter specific Concepts I want to make sure you have a solid foundation and Dot thus in this course our initial Focus will be on learning dot without involving flutter at all once we have a third understanding of Dart we will proceed to build the three apps mentioned before one last note for non-programmers learning a new language can sometimes bring up questions or confusion that's completely normal if you encounter any difficulties or have questions about the concepts or syntax we cover in the tutorial don't hesitate to ask you can leave your questions in the comment section below we also have a Discord server with over 2500 members including myself ready to assist you every step of the way link to the Discord server is mentioned in the description below so that wraps up our introduction now let's understand what dot is and how is it different from other programming languages dot is an open source language developed by Google it shares similarities with other popular programming languages like JavaScript and Java if you're already familiar with these languages learning dot will be a breeze but now the question is why would you use dot instead of JavaScript or Java the primary reason many people use it is because they want to learn flutter flutter uses Dot and allows you to build apps for iOS Android web and desktop with a single code base this doesn't mean dot is only used to build user interfaces it can also be used to build back-end your own server or anything else you prefer so before diving into code there's a thing I want to mention really quick dot comes with two compilation processes by compilation I mean the process of translating the source code the code we type into machine code so compilation is basically converting from Human readable format to format which the computer can understand so the two compilation processes are just in time jit and aot short for ahead of time compilation during development Dart uses the jit compiler which allows for fast iteration and immediate feedback it means you can make changes to your code and see the results without waiting for a link the compilation however when it's time to deploy a dart app you can use the aot compiler the aot compiler compiles your dot code into optimized native machine code this results in Faster execution and improved performance making your applications really efficient so to write Dart code we need something known as an SDK SDK stands for software development kit now what is this software development kit let's break it down software development kit a kit for software development and it's somehow related to dot right so let's take an analogy to understand this better suppose you're building a model car when constructing this model a whole kit of items as needed including the kit pieces the tools needed to put them together assembly instructions and so on similarly ndot or any other programming language when you want to try to run it on your own machine you need something as an SDK so that you can write your code test it out and run your code as well right now your system doesn't have any information about dot when you give it a set of tools it knows that yeah this is how I need to process dot code and if you give me this instruction in the command line this is how I will do it so those are the set of tools we require there are three primary ways of installing dot SDK first one is by installing the flutter SDK frata SDK contains the dot SDK so using it we can create flutter apps where we can write dot code or we can create dot packages or dot projects that will allow us to write dot code second option is to go to dot dot Dev and install the dot SDK when we installed the dot SDK from here we won't be able to create flutter apps and run them but we'll be able to test out a DOT code and the third option is using dot pad Dart pad is a bit different from these two solutions dot pad is a way to write dot code inside the browser itself so you don't have to go through the hassle of installing the SDK or anything you can directly start writing your Dart code over here and that's exactly the approach you're going to take the reason we are not installing the flutter SDK or the dot SDK is because there might be some installation processes where you might get stuck and the point of this tutorial is not about installing anything it's just about practicing to write dot code when we get to the flutter section we are definitely going to install flutter SDK so that we can have local development and with that we'll get the dot SDK so we are going to locally install flutter and Dot in the flutter section but for now let's start writing a code in dot pad and let's dive into dot so first thing we are going to do is remove all of the code that we see here and we are just going to have an empty thing right here don't remove this part because this thing right here is very important this is what is known as a function and we're going to know more about it as we go forward in the tutorial but for now you can consider this thing as the entry point to your dot applications and dart programs but if you see right now this thing right here is empty and if I try to run it nothing is spit out in the console or in the documentation or anywhere everything Remains the Same what I want to happen is something should be spread out in the console so that it gives me some sense of encouragement to keep coding so I want to see some output in the console how can I do that so to do that we have some special keyword keyword are basically special words that carry special meaning in dot or any other programming language in general so if you have print and if you type it like this you'll be able to print out something in the console but here we get an error let's say it's one positional argument expected by print but zero found what does this line even mean you'll get to know more about it when we move forward and by the end of this tutorial you'll be able to understand almost all the frequent error messages I can just try experimenting something right in the print I'm just going to pass in what I want to see in the console I want to see Hello World to be seen in the console so if I do this and you know then try to run but even before running it gives me an error it says undefined name hello try correcting the name to one that is defined or defining the name and here it says too many positional arguments one expected but two found now this error message is similar to the last one if you notice when we had nothing typed out here we got one expected zero found but now we have two found just keep this in mind so when we move forward in the tutorial you'll be able to analyze these error messages and the reason we are getting all of these errors is basically because we want to wrap all of this text that we have in single inverted or double inverted commas so if you do that and click on run you'll be able to see something in the console earlier it didn't work because it thought it is something known as variable and we have not defined any sort of variable here and to print something that is a text in dot all we need to do is wrap it with a double inverted or a single inverted comma both of them work the same way and we can also pass in numbers instead of this text message and while in text we needed to have the double inverted or single inverted comma when spitting out some number we don't have to do that we can just have three written over here and run it and we'll be able to see it in the console but even if you do this and try to run it it doesn't matter it prints it up so either of them work but both of these things are not similar or same they are quite different from each other to show you these two things are different from each other what I'm going to do is use operators to explain them now I hope you know operators and if you don't know well they are basically addition subtraction multiplication division all of that so I'm going to use operators to make you understand that these two things are different so we are going to have 3 plus 2 over here which we can do it in the print statement and it doesn't throw any error and the result we should be expecting is 5 and that's what we get 5. and we can keep doing this we can have 3 plus 2 minus 2 into so this is the sign for into in programming you have to add an asterisk to do into if you use x obviously it thinks it is some sort of variable so you have to have into 2 divided by 4 and if I do this much and run it we get 4. now if I just remove this from here and instead have 3 plus 2 like this we get an error the error says the argument type int can't be assigned to the parameter type string now what does this error mean I'm not going to explain it to you right now but you will understand it very soon and I'm sorry for doing this but you'll understand as we move ahead the point I'm trying to make here is not to make you understand error messages now I just want to tell you that these two things are different and if I just convert this to in a string as well and add a plus over here and then try to run it we should be expecting 5 but we get 32. why is that the case well that's because dot considered this a text this a text and this plus operator here thought if either of them are string or both of them are string I should be adding them by added here I mean concatenated now let's experiment a little bit what if we have got a minus sign over and as you can see we get an error minus multiplication division anything of that sort is not allowed you can only put in a plus because it thinks it's concatenating but it does through a warning because that's not the way to do it there is another way to do the same thing but we'll explore it as we move along interestingly if we put multiplication here we get an error saying the argument type string can't be assigned to the parameter type end and it only highlights this part so what if I convert this into number and this into a normal text and then try to run it as you see we get 33 that's because it prints three two times so it's basically multiplying the text and adding it together so if you have 22 and then try to run it you'll get 3 22 times written over here you can count it for yourself now I just want to show you something related to numbers that we have done previously if we have 5 divided by 4 plus 2 minus 4 and let's add a multiplication as well and then try to run it you get minus 4.75 and if you try to calculate on your own this will be the answer and you're calculating this using bod mass and that's exactly what dot follows dot follows operator precedence that means things like multiplication division take precedence over things like addition subtraction also if we have bracket over here that's going to take precedence over division or multiplication so if you try to run it you get the same thing because 4 into 2 takes precedence over minus if I have to show you a simple example just to clear it off we have 75 divided by 5 plus 2 and then try to run it we get 17 because 75 divided by 5 is 15 plus 217 but if we put bracket over here in 5 plus 2 what will we get will we get 17 no we should be getting 75 divided by 7 which is 10.742 so now that you know about these two things what if I want to make my notes aware I've learned something new that dot follows bodmas or any other programming language mostly follows bodmas I just want to make a note over dot follows bodmas I just want to write this here but if I try to write this here we get an error so do I have to enclose this in a string no that's not a good idea because this thinks this is a text which is different from what I want I want to make notes for me I don't want to make some text that is understood by the DART program I want to create something that is understood by me as a programmer so to do that we have something known as comments and comments are of different types as well these comments allow me to make notes for me so that I can understand my code better even if I look after you know 10 years and the different type of comments I was talking about is first this one the single line comment what if my node extends more than two lines you know more than one line sorry so if I have another one which says dot is cool right now I can do this you know put single line comments to make it multi-line but what's a cleaner solution for us so that I don't have to put this two forward slashes again and again so for that we have multi-line comment with this I can just have a syntax like this syntax basically refers to the script in a programming language if that makes sense so this is a script of English language this is a script of dot all right so I have this comment which says this is the start of the comment but I have not ended it so it doesn't know where to end so it covers everything a rest of the line in the DART program so to end it what I have to do is put a status forward slash again and now it knows that this thing right here is my comment and this is the scope of it that means this is the part where I can create my notes and if you want you can go ahead and create your notes here as well you can create as many comments as you want but if you're extending more than one line it's obviously recommended to use multi-line comment a third type of comment exists as well which is called a documentation comment this might not be useful to you right now but when you start creating your flutter apps you'll be able to use and make sense of these documentation comments now if documentation comment doesn't make sense to you don't worry about it you'll understand as we develop our own app and flutter and when we have several files to scan through so now that we've completed all of this let's remove it and dive into variables what are variables I'm just going to ask you what do you think variables are variables by looking at the word it just means things that can vary right and that's exactly what variables are variables are just ways to store the data and later on change it now you might ask when would I need to manipulate or change some data let's take an example to understand this further suppose you know we have a print statement and here we are just asking for the user input and the user input gives us 19. I'm not really asking for a user input here I'm just faking the value but in a real life scenario we are going to ask the user what is the first value going to be what is the second value going to be and based on that we are going to carry out multiplication addition subtraction all right okay so this is my first value after that I'm going to ask for the second value also and that is going to be input from the user as well let's say the user entered five now I want to make some calculations based on this so I'm just going to have print 19 into 5 print 19 plus 5 and print 19 minus 5. all right so I'm taking the first value and the second value and multiplying adding and subtracting if I run I get 19 first value that we printed second values that we printed 19 into 5 is 95 19 plus 5 is 24 and 19 minus 5 is 14. so we get the correct values now what's the problem here well the first problem is we are just faking the value by ourselves right but in a real life scenario we don't know what the user will enter will the user enter 19 20 25 we don't know we have to assign a variable to this which will contain this value and we can use it later on and let's say we are not taking the user input only we are taking the values on our own all right so no user input is involved we are basically telling this is 19 this is Phi and we have to do multiplication addition subtraction based on these two values but later on someone else comes in and says the first value shouldn't be 19 it's very easy calculation let's make it something more difficult let's make it let's say 302 and this should be 51. now now I'll have to go through this entire program change everything everywhere so after 302 into 51 302 plus 51 302 minus 51 and suppose we have like hundreds of print statements will I do that in every single print statement or every single line that's not an effective solution right I'll have to do so much work just to change one value and if the value changes again and again that will be a big problem and that's why variables were introduced so to create a variable this is the Syntax for it this is how it looks in dot every programming language has something differently done in dot this is how you can do it so we have to first mention a data type then we have to mention a variable name then I'll assign using the equal to and then I want to pass in some value and finally a semicolon semicolon is used for the print as well it's going to be used here as well it's used for probably almost every single line that you have there are some exceptions like you know this thing right here this doesn't have any semicolon it has a curly bracket but we are going to discuss more about this curly bracket and why it exists the advantage of having the semicolon actually is if you just want to put everything in one line so you have multiple print statements in one line and that will work as well okay so if you just do this and run we get the say we cut the right output so you can have all of them in a single line thanks to the semicolon it's kind of like a full stop in your English language all right so coming back to this if you want to come back to anything you just need to press Ctrl Z if you're on Windows and if you're on Mac command Z and you'll be back here it is the undo option and if you want to redo you can have command shift Z and it will redo all the stuff for you so now that we have all of this out of the way let's create variable for first value and second value and use those variables so first we need to understand here what is a data type so there are multiple types of data right it can either be a number it can be a text it can be something else what do we want well I want my data to be a whole number a natural number a negative number a positive number that doesn't matter but it should not be a decimal number that's my restriction I need to know if my number is going to have a decimal or not if it's going to have decimal then we have a data type assigned to it called double but if we don't have a decimal we're going to have something known as int both of them double and end allow you to have negative numbers positive numbers but the difference lies in the decimal point so with int you can store proper numbers not any fraction or anything but with double you can store decimal fractions Etc so we are going to use int because I don't want there to be any decimals and then I'm going to have variable name which is first value now you might ask why do we need variable name variable name is needed so that we can distinguish two variables from each other for example I am Revan and there's some other person called Norman we're given two different names so that we can uniquely identify each other that's the case with variable we are giving this the variable name of first value then you are going to create a second variable and that is going to be called second value okay and then I'm going to add is equal to set it to a value my value is 302 and there we go we have first value variable created and if we tap over this in our documentation part we see int first value local variable now we are going to have second variable and that is V and second value which is equal to 51. now I can remove all of this I'll take this first value and instead of print I'm going to print first value over here I'll take the second value I'll print second value and now you see warnings are going the warnings appeared first because we are not used this variable but we had created it now it is very smart to know that we haven't used this second value anywhere in our function all right so that's why it says yeah you have not used it it's better to remove it but we have to use it so I'm just going to use it over here let's remove the comment then I'll take this first value replace it with 302 then the second value replace it with 51 and I'm going to continue doing this over here so our first value 2 000 years later now my entire code is dependent on variables and if I try to run it I get the same output I print first value okay so it checked yeah this is first Value First value is already been created so let's take first value from here let's take its value and print it then we have second value the same happened over here let's find for a variable second value yeah it exists so we are going to take this 51 and print it over here then we have first value we already know the first value that is 302 into 51 so it multiplied them then first Value Plus second value so it had 30 hundred and two plus fifty one so the same thing happened but now instead of hard coding it by hard coding I mean manually typing 300 and 251 every single place I'm going to replace everything with variable and I did it the benefit of this now is if I have 310 year and if I decide to change this to 102 and then try to run it I will get completely different results the benefit is I don't have to keep changing every single thing here I just needed to change one thing or second thing the values and all of them automatically change their values now let's try to do the same thing with double now so if I use double here and let's say we use double here and then I have 310.50 and 102.5 22 just to demonstrate to you that I wasn't lying if you have interviewer it will throw you a compile time error that means while you're coding while you're writing in your code editor it will tell you with the red warning or red arrow that yeah this is wrong and if you try to run it it will give you an error so we have double now we got rid of the red warning and you see I get 310.5 instead of 0.50 I get 0.5 data smart then we have 102.22 and all of these which you can calculate on your own now other than numbers we have other data types as well another data type is string so you know how in your print statements you used to write let's remove all of this so that we don't have any confusion we have understood why we need variables now if I use string aware you know we get an error because this is a type of double and I've used string now what exactly is a string you know how in your print statements you had written hello world like this and then when you try to print it it printed hello world now this thing right here this text is a string so if you take this paste it over here you see the error goes away now there's just a warning that you've not used this value of course we can just use it over here and then run it and we get hello word so string is used for text for words for characters you can use string so you can even store a single character in a string and the string like in the print statement we saw can have single inverted or double inverted comma and that's going to work just fine there are two more data types that I want to show you right now of course there are going to be more but as of now I'm going to show you two more later on in the tutorial we'll cover more another type is Bool like this this booleo stands for Boolean all right in other programming languages like Java you define it like this Boolean first value is equal to false or true you know either of them either it's going to be false or true and as you can understand Boolean value only tells you if you're going to have a true value or a first or a false value so you cannot have string numbers or anything you can either have true which is a keyword in dot or it can be false again this is a keyword of course if you use this within a string it loses its value but as of now like this it has a special meaning and when you try to run it you'll see false printed out over here now you might ask why would I need a Boolean value why would I need just a true or false there are many cases where you might need Boolean for example we're going to have is adult so we just want to know whether the child is adult or not and this is a naming convention all right let's make this small so this is a naming convention whenever you have a Boolean most people prefer to have is before it so you know you know that this is a Boolean value and you don't have is not adult or nothing no sort of negation is there it's either is adult or is child and that's much better to read it's just a convention obviously you can name variable names whatever you want but yeah they cannot be repeating themselves so you can have Boolean s child which is false and then you can print s child and run it so with this variable now you get access to you know getting to know is this a child or is this an adult If the child is false that means it is an adult and the last type that I want to show you is very interesting and that is dynamic and you see when I have Dynamic I can put Boolean value I can put in string value I can remove all of this I can have 10 10.5 I can have anything I want so I can just name this some value and then use this sum value over here this is going to be dynamic that means it can take any value it can take integer it can take string it can take Boolean whatever you want and then run it and it will tell you that yeah it's 10.5 it's doing stuff correctly but it's generally not recommended to use Dynamic by yourself there are certain cases where you cannot avoid Dynamic but it's recommended that you use values like end Bool or string or whatever don't use dynamic because when you use int string or whatever you're basically telling the system that yeah this is this value and it is easier for the system to know that this is an integer value when you have Dynamic you have Dynamic value you don't have any clue what it is going to be so it can be a bit tough for example when you have interior and you put dot you get a lot of things that you can use all right so these are the things that I'm going to cover later on but for now you can just see that when I have integer here and if I do some value dot is even that will let me know if it is even or odd and as you can see it is prefixed with is if it is prefixed with is we can get a clue that this is going to be a Boolean value so it's going to give me a Boolean value and tell me if it is odd or not and then when I try to run it I get false here there we go and if I have is even it will give me true and there are lots and lots of things is finite is infinite is negative absolute like this the syntax is a bit different but I'll let you know as we move along by the syntax is like this why it's not like this etc etc of course you can use it but it wouldn't work so if I just try to run it like this you see we get something like this which doesn't even make sense to us we can just do this and run it and we get 10. abzero stands for absolute value of this absolute value of 10 is in need 10 and there are loads of other things now if I just convert this to a string and then put this inside of string as well and then I do string some value dot you see we get a whole bunch of new properties these are called properties I get smt whether my string is empty or not you know smt is not empty length what is the length of my string so if I just do this I get 2 over here okay because that's my length of the string if I add something like this it should increase and it definitely does then we have more things like compared to contains ends with index of last index of I'm going to explain all of this stuff later on when we dive into functions Getters and all of that so it will make much more sense but for now my point to tell you all of this is whenever you used end of string it gives you capabilities like this but when you try to do dynamic and then you try to do some value dot you see you only get all of this hash code then runtime type so if I have runtime type and then I try to run it I get string over here so you see the difference at compile time the value is dynamic that means when we are writing in a code editor it knows that this is dynamic it can contain any value but at runtime you know when the code has been executed or when the code is executing you get string because at run time it knows yeah this is a string now just to demonstrate one last problem with Dynamic if I have some value plus 3 over here we know this is not possible because this is a string this is an integer and when we try to do it earlier it didn't work and now if I try to do it it gives me an error over here it doesn't give me a compile time error it doesn't give me red lines over here if I use string like this it does but with Dynamic it doesn't because at compile time the value is not known at run time the value is known and when it is known it says no this is error how can you even run this code that's why it's generally recommended to use the type as it is one last thing I want to tell you while we are on this is the variable naming convention this is not the convention to name a variable generally naming convention is used which is camel case so you have sum and when you feel like it's a next word right some value is consisting of two words right sum and value so you want sum and values V should be bigger okay so this is a convention obviously you can go ahead and make this some value but just for better readability it is recommended to use camel casing now you can take this put it over here and there we have it so if you don't trust me now you can see when I put some value dot is empty it's assisting of two words is and empty is not empties consisting of three words is not empty so the first case is small second is capitalized and third is capitalized so except first everything is going to be capitalized that's how the naming convention is so now that you've understood all of this let's remove it and use integer here let's call this first value like this which is equal to 20 and I said in my definition of variable that variables are things that can store some value and when needed it can even change the value so if I want to change first value how can I do it well do I have to do in first value is equal to 30 like this no you cannot do this you see we get an error the name first value is already defined if you already have some value defined you cannot create a variable again but yeah you can create a variable like this first value like this and first value like this is different because dot is case sensitive even if you have double aware you cannot be naming them like this the variable name should not be same it can be like this but it's generally recommended to have a different name altogether if you're creating a new variable because it can create a lot of confusion as your program grows go grows bigger for example if you have one variable that says first value is 20 and then you have another one which is similar to this but V is small then you have 22 then you have a third variable where let's say e is capitalized it can be a lot tougher to read and when you want to print something and do your operations you're like which one should I use it can be confusing right so it generally recommended to make your names as descriptive as possible and to be quite different from each other but yeah please don't name your variables like f v whatever just name it something that makes sense right first value 20 now I want to change the value I can just do first value is equal to 100 all right now I have changed the variable now if I just try to print stuff so this is first value then I'll print first value again and we should be seeing two different values now I have 20 then I should have 100 and we get that so you create a variable you print it then you re-assign it and don't put it into where because that's like assigning a variable again you're reassigning so you don't have to pass that in and then you have printed now what if I want to increase the value I don't want to set it to a definitive value for example if I change it to 25 I want 75 to increase if I have 20 I want 75 to increase all right I don't want it to be 100 only so I can just have first value equal to First Value Plus 75 and then we run it and we get 20 and 95 so if I change the value to 25 here I should be seeing 100 and that's exactly what I want so this is how you can use operators to give value to a variable right you can even multiply you can divide whatever you want so let's minus it for now and run it and you'll see the result now shorthand Syntax for this is just removing all of this and you can do minus equals 75 and then when you try to run it you should be seeing the same result why does that happen this is a shorthand Syntax for what we just typed this stands for first value is equal to First value minus 75. but yeah if you want to do first value which is equal to 75 minus first value this wouldn't work and you cannot do equal to minus 75 because that just means first value is minus 75 yeah if you try to run it you see we get 25 and minus 75 because it's like this so you're reassigning it to say minus 75. but you can do this minus is equal to 75 and that will make sure that this happens and now if you do want to do plus you can do that if you want to do multiplication you can do that if you want to do divide you can do that so let's try to do this and there we go so this is how you can reassign variables and use operators to give new values to variables now let's remove all of this and get into Strings so we have string first value which is equal to let's say hello what and let's make this variable name more descriptive this is a greeting and now if I try to print greeting I will be seeing hello world we now have that much confidence now I want to reassign it so I can just have greeting equal to hello world without a comma then I print greeting again and then when I try to run it we see Hello World with a comma and hello world without a comma that's good now you can obviously add to greeting as well so you have greeting Plus yo like this and then try to run it and you get Hello World hello world yo but now where you see an error we've seen before use interpolation to compose strings and values we get this error because this plus operator should generally be not used with strings what you should be using is string interpolation and how does string interpolation work well I can just remove all of this and we have this right so we have reassigned it to you but now here I'm going to pass in dollar curly bracket greeting and then when I try to run it we get the same output so with this we have added the variable hello world over here like the value hello world has added using this syntax and you that means dollar and after that Curly braces have a special meaning in strings so if you whenever you use Dollar in a string it isn't just a normal dollar it carries a special meaning so you have to use dollar curly bracket greeting but even if you see now unnecessary braces and a string interpolation and that warning is quite descriptive when I have greeting like this I don't have to put curly bracket I can just do dollar greeting like this and the error goes away the warning goes away and now if I try to run it I'll get the same output now you might ask why did I put curly bracket earlier if I already knew that's not allowed because I wanted to show you when we have to use curly bracket curly is to be used suppose when we have something like this all right so I want the length of this string so I want 12 U to be present over here and that's when I will use curly bracket I cannot do something like this because this way it thinks dollar greeting is a variable all right so we'll have Hello World then it will print out dot length and then it will print out to you so it considers dot length as a normal string dollar greeting as a variable and it isn't what I want I want 12 view to be present because that's the length of hello world so that's why whenever you have something like this you put curly bracket over here and when you have curly bracket and when you run it you get 12 yo so in this case we don't get any warning but yeah if you have a single word you have to use it like this if you have something that adds up to it it will consider it a normal string you can see the highlighting also gives you some clues about it so you can just have like this and run it and there we go we get the nice output so this was string interpolation and a new way to concatenate strings now you might ask what if I just want a normal string with a dollar there so if I'm having an e-commerce site and I have dollar 12 to be written how can I write that right I mean dollar is my currency well to avoid that you can just put a backslash and with a backslash it will consider dollar as a normal dollar sign it will lose its special importance and then when you try to run it you get dollar 12s perfect so just put a backslash to remove its importance now there are a few more cool things I want to show you so if you have hello world like this and I want to print world on a new line how can I do that if I do this will that work no you can see we are getting an error because all of this needs to be in a single line to make it multi-line what we can do is put three things like this three single inverted commas and even here we are going to have three single inverted comma and now it knows that this is a multi-line string and this is generally used for bigger values right I mean if you have like a very very long text you might want this so if you have three strings like this and then you can have multi-line strings so you can do like this and run it and you get hello and hello world like this perfect but what if you don't want to do something like this you want everything to be in a single line but you want to go to a next line so for that we have special thing n Dot so let's put it in a single line again if you just put it like this you know it will work as well but this is generally used for multi-line comments or multi-line strings sorry so let's put it in a single inverted comma and here to make world go on a new line what I can do is slash n and then when I run it we get hello world on a new line but you might see Hello is overwritten over here then there's a space and then word that's there because we have left a space over here if we remove the space and then do it we will get hello and world right below it and you see we get that so slash n basically stands for new line if we just put n over here it will just think it's a normal value but when you put slash it adds a special importance of air which says yeah leave a new line and then when you run it you get hello world like this great and one last thing that I want to show you is if you have a string written over here and if you try to later on change its value to 10 that's not allowed because Dutch type system is very powerful what is this type system well just knowing that this value is a string so if this is a string it cannot be reassigned to an integer value a double value a Boolean value anything if it's a string it needs to be a string you cannot change it later on and that is type system because those are data types right you can consider it like data type system but for short we just say type system and the type system is so strong that it knew yeah this is a string you cannot assign it to an integer why would you do so if you use dynamic and if you have a string over here you can reassign it to an integer and it will all be good all right so if you just try to do this run it it will work well for you you get hello world and 10. there's no runtime error there's no compile time error nothing at all because Dynamic is basically saying give me whatever value you want I'll take both of them but yeah at runtime it knows both of its value so if you just have greeting dot runtime type first it should print out a string then it should print it out an integer and that's exactly what it did so I hope you understood Dynamic and string integer Etc now let's get rid of all of them and I'll show you a new way to create two variables now you might ask what is this new way now let me tell it to you so another way of creating the variables is like this first you'll have to mention either where or final or cons followed by the variable name equal to and then the value so this part right here is the same but instead of int string whatever data type we had we can just type in VAR final or const not all three of them either one of them and we'll get to know what's the difference between all these three but let's first type something out so we are going to have where some value is equal to 10 all right so it gets to know that one line is completed then you're going to have print some value and then we are going to run it and we see 10 over here now you might say this can't be the exact same thing as integer over here because you know we are using a different keyword here we are using where and it might be similar to dynamic because you haven't mentioned a type right but that's not the case if you go where in the documentation you'll see int some value and if we just see the nice autocomplete features that we get we get those things just like we have in integer because it has correctly identified that this is an integer now you might think this wire only stands for integer you're fooling Us by saying that is is for all types but no that's not the case if I convert it to string it will automatically get to know that this is a string why is that the case it's again because of Dot's powerful type system you need to know that every variable must have a type so even if you put Dynamic the variables type is dynamic if you put a string it is of the type string if if you put enter where it is of the type end but if you put VAR it correctly identifies the right hand side and gives the value of the right hand side to this variable and again if you go ahead and try to change it to let's say an integer it will throw an error this is not Dynamic this is of the type string and it's got to know that so although every variable must have a type the Syntax for specifying types is optional whenever you use wire final or const this happens because darts type system or the type inference system can automatically know the types of variables based on what you've written over here now let's put in final as well so we have final some value which is equal to n and const some value which is equal to 10. all right let's make all of them strings so that we know all of them are the same thing but now you might see obviously we get an error the name sum value is already defined I told you all variables cannot have the same so you need to go ahead let's Place some value two some value 3 over here and let's call this some value one okay yes you can add numbers to your variables okay but you cannot add these numbers to the start of these variables keep that in mind okay so if you have one sum value that wouldn't work you need to call it some value 3 or some value 1 or some value 2. so now that we have this let's print everything out so we have some value 2 some value 3 and we print it and we should be seeing 10 right because well it's all the same and note that yeah everything here some value 2 is also string some value 3 is also string so the type inference works for all these three things but the difference comes in when we have to reassign the values all right so we have printed this now let's put some space away up so we are just going to print you know kind of a divider and then we are going to have print or let's reassign it first so we'll have some value 1 which is equal to 1001 now okay then we'll have some value 2 which is equal to ten thousand one and some value 3 which is equal to ten thousand one as well okay now let's try to print all of these values again so I'm just going to copy them and paste it but there we go we got an error why is there the arrow well let's see the final variable sum value 2 can only be set once constant variables can't be assigned a value so this is the difference between where final or const all right where basically stands for variable that means the value can vary final stands for this is like the final value the ultimate value and const stands for constant value that this is constant so obviously based on the context that we have here based on these keywords we get to know that these can't be reassigned so once their value is set they can't be changed but variable can be changed so this is the difference between variable final and const so you can do this and then run it again so the value will now print 10 10 10 10 then it will print out ten thousand one ten ten and that's what happens over here so hopefully you've understood this but now you might ask if final unconscious both can't be reassigned what's the difference between these two variable is understood and by the way I forgot to mention this but this is what is called mutability and immutability mutability means that the value can be changed after it's set and immutability means the value cannot be changed after it's set so variable your where or VAR or whatever you call it is mutable and these two things are immutable so now that we have this let's remove variable out of the scene and let's compare only final and const because you might be confused in that both of them look similar both both of these values cannot be changed later on but there has to be some purpose that's why these two keywords were created separately otherwise it could just be final or it could just be const right so to understand this difference what I'm going to do is completely remove the strings from here and gives a value of date time dot now now you might not have seen this before or if you're already familiar with dart and you're just watching to revise you might have seen this we generally use this more often in flutter apps because you want to get the current time or current date that's where it helps it gives you the exact time right now so this using this thing you can get it but obviously you're not familiar with the syntax we understand more about this when we go into classes functions and all of those stuff but as of now you can just blindly copy that this thing just gives us the current date time all right so it's the correct date with the time but now if I set it to both of these things the constant one gives me an error but the final one doesn't give me a compile time error why is that the case that's because date time dot now retrieves the current date and time at runtime so its value cannot be known until the program is executed and that's the difference between final and const final is a runtime constant and const is a compile time constant now this might be confusing because there are a lot of words juggling around so let me clear it up so what I want you to do right now is just think about it logically date time dot now can it give me the variable value such that I know it before the code is executed that doesn't make sense right if I give a 10 like this over here it knows that the value is 10 at compile time but when I give date time dot now that is not really a constant 10 is a constant date time dot now cannot be because it gives me the current date and time and current date and time is always changing so it cannot be a constant it is a variable so the value is known only after we press run but in case of const const is a compile time constant and you're assigning the value of a runtime variable that doesn't go hand in hand right that's why it gives you an error constant values can be 10 you know strings sort of these things but it cannot be runtime variables it can only be compile time constants so I hope that was clear now if you just try to change its value obviously it won't change so you'll have some value 2 is equal to date time dot now let's say again and if you see we get error the final variable can only be set once now if I try to run it and the output is 2023 516 so this is the date when I'm recording this is a Time if you want to match your letters and obviously it goes into much more detail and if I again run it this part will your change right because time is not fixed that's why this is a runtime value not a compile time value so this was the new way I wanted to show you but obviously it's not like you can eliminate integer it's against the syntax you can pass final let's say date time over here we'll get into the syntax more but basically you can pass date time over here and you can pass string over here both of these things will work it's not like they won't work but if Dart can automatically handle it for you why would you want to type it right I mean if dot is already doing all of this why should I do it so this is the convention that people generally follow now you might say if this is the case if I can use variable final constant all of those things why did you show us this string approach string some value is equal to thousand why did you show me this way isn't it adding more confusion well first of all I wanted to show you more about types I could I wanted to show you about reassigning the variables and I wanted to show you about type safety meaning you cannot assign string to an integer you cannot assign integer to a Boolean Etc but other reason for doing that was just having final const where doesn't really mean you can eliminate using these data types all the time there are certain cases when you can't avoid using them and you'll have to avoid using variable final or const let me show you some situations like that and that introduces us to A New Concept which is nullable variables or optional variables so let's remove it from here let's put the heading optional variables over here now what are these optional variables optional variables basically say that your variables can have two values not at one time but it just says it can have either one value or other value so what are these values well first value is string or integer or Boolean whatever you've mentioned like this and it can have a null variable or null value what is this null value well null value is basically null nothing it doesn't have any value so suppose you want don't want to give any value to a string when you initially set it but later on based on some condition or something you want to change the value that time null is used because if you just pass in an empty string that's not a solution because this is not null this is not like it doesn't have any value that's not the case here you're saying that it has a value of an empty string but when you use null you say that this doesn't have any value let's take an example of end if we have end sum which is equal to let's say 0 you're not saying that sum doesn't have any value sum has a value of 0 to not have any value you set it to null so when you pass in null which is a specially defined word it's a keyword you get an error over here a value of type null can't be assigned to a variable of Type n now if you were using dot SDK 2.0.0 or below you would be able to use it because these optional variables these nullable variables were introduced n dot two but with DOT 2 and above including you know dot 3 you have to do something else within tier after the end you have to mention this question mark to show that this is an optional variable that means it can have null values the same with string if you pass in stuff like this it will get to know that you can have null values assigned over here so we can have null we cannot use final for this so you cannot have final some value is equal to null like this because that's not allowed you see we get an error so you can just have some value 2 which is equal to null and you'll say this is fine right but that's the problem if I just hover over this and let's remove all of this so that I can see the documentation you see aha variable is now Dynamic I I said that time using Dynamic is the least preferred way you should always try to avoid Dynamic and if I just type it null I lose everything related to types that dot has to offer so that's why I don't prefer using final sum value 2 is equal to null or variable some final value is equal to null or constant which is equal to null okay and that's why I prefer using these string with a question mark and with a question mark because if I come over here let's remove this if I have this over here we have string question mark sum value so I still get the nice features the string thing has to offer so if I just try to print some value dot I still have access to all of these things but with final I wouldn't have them so I hope that was clear but now let's see why we are getting this warning we are getting this warning because it says redundant initialization to null what does this even mean well it basically means that you don't have to explicitly set it to null because even if you don't set anything over here a variables automatically get to know that the value is null so if I just print some value over here and then I run it I get null and then if I reassign it and I have some value equal to 354 hello world then I print the sum value again we should be getting null 354 hello world right and that's what we get and again you can set this value to null again so you have some value is equal to null print it and then you have some value like this okay so dot basically has support for nullable variables or optional variables and this is called sound null safety now you might ask what is this null sound safety where's the safety coming from well that's because if I just try to find the length wire because this is where I have the value and then when I try to run it so this works fine but if I come over here and here I type dot length it gives me an error why is that the case well the property length can't be unconditionally accessed because the receiver can be null the error messages might be driving you crazy but stay around this is basically telling that the dart compiler knows that the value is null it knows because you are in this void main thing right here this thing is called functions we are going to take a look at that very very soon then you'll understand what I'm talking about and it will make sense but as of now just think that this this thing this function right here is giving Dart the additional context and telling that that this value is set to null and if the value is set to null dot knows about this null value so it's telling that you can't unconditionally access the receiver because it can be null So to avoid this error what you need to do is put this which basically tells that this variable that you we have is not null but that isn't the case right we have reassigned it to null and if we try to run it we don't get any compile time error but we will have a runtime error we get null and 15 printed out that's correct but here we get uncaught type error cannot read properties of null so this thing I told you is a property and it's saying that it cannot read properties of a variable because you are telling that this is not a null but in fact it is null so it's your logical error so we cannot use this method what else can we use well we have another thing we can use question mark now and if we use question mark we are basically telling that if it is null then just print out null but if it is not null then use dot link and when you run this you get null 15 and null so if I just set it so to some value let's say hi you see we are getting this error the receiver can't be null so the null aware operator question mark is unnecessary it has got to know that this sum value is not null anymore so you don't have to use this question mark just like you had over here you can just use dot link and then when you try to run it you get null 15 too now you might again have many questions about this why is this null operator there when dot compiler already knows that this is null it should do manage all of these things by itself right to make this example better what I can do is just shift this out of the main function all right so we have this thing right here and now you might see some changes when I shift the string variable outside of the main function we get an error here and this error is basically when what we had when we assigned it to null when this string some value variable was inside of this function why is that the case this is the case because these functions have the special ability to give context to the dot compiler this function was basically getting to know all the values some value could take and would know that yeah this is now null this is now null you cannot use this but now that is in the case because some values declared outside so it doesn't know much about the context so it since it doesn't know it's throwing an arrow and this is why we have null aware operators now you have to manage everything on your own so now you'll have to do this by yourself you'll have some value dot link I can use this or I can use this both of these things are fine in this case because some value already has a value so if you try to run it we get null to none so that's fine you can also use question mark that would be no problem that would just make sure that if by chance you change this to null it is handled by its own so you have but again if you're building your application you don't want to show null to the user right you're a programmer you know what null means but your user doesn't know null so if the value is null what I want to do is show zero all right so I can achieve this by just having question mark question mark which basically says if some value dot length is null then I want 0 to be written I don't want null to be printed out and the same thing can be done here as well and then if I run it I get null so take the 0 and the same thing over some values dot length value is actually null so put one over here and if I put hello world like this it should be printing out the length of this hello world right here 11 and that's exactly what it does if I put exclamation mark over here and that's not the case why do we get this warning we get this warning because here you've mentioned that some value cannot be null all right and that is why you are able to access the linked property on it but then you're saying that if some value dot length is null then take zero that's a bit of a confusion from your side right your first saying this value is not null so give me the length but if it is null then give me 0. so you can think of it in an English sense as well question mark is basically asking if this null is this null and exclamation mark is forcing dominance all right that yeah this is null and this thing right here is basically a short form for something known as a ternary operator we're going to look at this right away now that we've completed the entire variables section we can move ahead to control flow which includes if statement switch statements and there itself we are going to learn about ternary operator so let's get started first with if statements and this if statements doesn't contain just if statement it will be if else if and else so what are these if statements and why do I need them well let's consider we have an INT age of 30 and I want to check if the user or the age is adult or not that means I want to check if the age is greater than or equal to 18 right only then is the user adult how can I do that with the help of if statements you've already said it in English what you want to do you want to check if so the Syntax for it is if then you put parent thesis then you have age is greater than or equal to 18 now this is something new but hang with me then print adult otherwise we are just going to print child okay so let's try to run it and we see child written away because the age is 13 if I put 21 year I should be seeing adult and that's the case now what is this entire thing let me explain it to you first we've mentioned the variable name that we want to check so we want to check if age is greater than equal to 18. so this is the greater than operator that means you know you've already learned it in math I assume age is greater than 18 or age is equal to 18. that's what this greater than equal to operator means so if you just try to put in 18 over here and then run it you should be seeing adult but if you just remove this is equal to then you should be seeing child all right so we have the if condition here and we had to specify this using the curly bracket exactly what we have in functions and these brackets serve a special meaning over here basically saying that if this is the case then this code needs to run else you can run this code so else and if are special keywords here you don't have to mention else and again mention a condition however if you want to check something else as well see here you want to check for something else let's say else if this is where you have something else so this is how you check something else okay and here you'll have to mention the condition again and here you basically want to check if age is greater than equal to 21 if that's the case I want to print adult to 1 okay and then when I try to run it you should be expecting adult 21 right but we only get adult why is that the case doesn't this else if work that's not the case let me go through this code we have age 18 then we are checking if age is greater than equal to 18 so if age is greater than equal to 18 you print adult and then you ignore all of these conditions you don't even check it because if condition passed so you don't have to check the else and else if conditions so to fix this issue what we can do is just use H greater than equal to 21 as a separate if condition if we have that we see adult and child both showing up at the same time because here age is greater than equal to 18 and there's no else condition which is fine then it moved to if condition and then it said if age is greater than equal to 21 that's not the case so I'll run to the else condition and in the else condition I see print child so I get child printed out here but still my problem isn't fixed what I want to do is print out only one thing so that means I'll have to put all of this in one condition only so the condition will have to be modified like this if age is greater than equal to 21 then print adult 21 else and then I'm going to copy this else if age is greater than equal to 18 so we print adult else we print child now if I try to run it I should see adult that's true but if I put 21 over here and then I try to run it I see adult 21. what happened here was you said if age is greater than equal to 21 yeah age is greater than equal to 21 so you print adult 21 ignore all the else if else conditions and then it worked but if you put 12 over here what happens is age is greater than equal to 21 no that's not true it is false so you put LG for where age is greater than equal to 18 no that's not the case so we'll go to else block and well else obviously doesn't have any condition so you just print child and if I run it I should be seeing child over here and this else condition is totally you know optional even the else if condition now notice how I said this is false this is because if conditions over here need to give be given an expression of Boolean you might remember Boolean from our variables so we have Boolean you need to put in Boolean conditions over here because that's what if conditions are at its core it's either true or false if this is the thing then it's true or false if the user's age is above 21 then it's true otherwise it is false that's how if conditions work you need to pass in a Boolean value over here so you might think what if I just go ahead and create a variable Boolean is adult is equal to false then I use this is adult over here can I do that yeah for sure you can do that but it gives you errors or Warnings because of the Dead code it's dead code because our compiler already knows that the value is false then why are you having this if condition so obviously we'll just put it out of the main function so that a compiler doesn't have any knowledge about it and there we go so if other if is it adult it's false now that means I should be going to these conditions now let's run it and see what we get and we get child why is adult is false so we will just shift it to else if then else if says age is greater than 18 it is actually 12 so no we cannot do this let's pass it to else and else will print the child so we get child over here so I hope this was interesting for you I just wanted to put that here now let's get rid of the variables and there are more things I want to show you and if statements you saw H could be compared using age is greater than equal to 18 there are more operators like this there's less than equal to 18 so that's the same thing you know greater than equal to the opposite of that will be less than 18 make sure to remove that is equal to if age is greater than equal to 18 it might contain 18 so the opposite of that shouldn't contain 18 so yeah if age is less than equal to 18 then I want to print something let's say haha otherwise we are going to have naha all right so let's try to run it and we get haha because age is less than equal to 18 because H is 80. other operators here are is equal to is equal to basically telling if age is 18 then do this now this is different from age is equal to 18 with age is equal to 18 you are basically telling that age is 18 and you cannot put expressions like this over here they need to be true or false when you put age is equal to 18 it's reassignment it's not a Boolean thing even in the error it says conditions must have a static type of Bool so this needs to be H is equal equal to 18 and because of that you should be printing haha and that's the case opposite of this is is not equal to so if age is not equal to 18 then print haha otherwise and we should be seeing naha now so I hope you understood the difference between assignment and relational operators those are two different type of operators assignment is is equal to this is assignment and this is relational because it compares two things but this just assigns the value to the variable now what if I have another variable which is actually a Boolean value which says Boolean is allowed and that is equal to false and obviously we are just going to put it out of the function otherwise we will get the dead code warnings whatever I am showing you is a fake value obviously this isn't happening in your real life applications I'm just putting it out of the function trying to simulate the bigger apps so it's allowed basically tells me if I'm allowed or not so as of now it's saying Falls away so I can just add a condition over here the condition will be if age is not 18 and if I'm not allowed then I want to print haha otherwise I want to print naha Salas if age is not 18 and the user is not allowed then we will print haha so you can have two Ampersand signs which basically suggests that this condition and this condition both should be true so that we can print haha so if I try to run it we get nah and that's the case because age is not 18 that's false so it probably doesn't even look at this it just says H is not 18 so we will go to the else block but what if a just actually not 18 it is 20. then what will we get well age is not equal to 18 that's true and is allowed is not there and we have put exclamation mark over here what is this exclamation mark you might ask it's basically reversing the condition we are just saying that if is allowed is not true that means it is false so if we run it we get ha ha because both of these conditions are true now if you're confused about this part right here let me fix it for you this basically means is allowed is not equal to true that's what not is allowed means okay but if you put is allowed is equally equal to true and then try to run it you get na because it's allowed is false and you said that 8 should not be 18 and is allowed should be true then only we will print her you can even follow this approach over here so if you have is allowed just reassigning it we will have no is equal to not is allowed that basically means whatever value is allowed has will be reversed so you can even do this but obviously you cannot do this over here you'll have to do all of that stuff in a function over here so we can just put it in a function if we try to run it we should be getting haha now because age is not 18 and is allowed is true thanks to this statement that we put in and that's exactly what I did this was a shorthand syntax we used a Boolean variable over here if instead I just put age over here that won't work because age is an integer not a Boolean not what an if condition wants what if condition wants is a Boolean value so I can use a Boolean value over here just like this but if I have an integer I'll have to put these relational operators or something other than the and operator we also have the or operator so you just have to put these two symbols and you can find that on your keyboard if you press shift and the button above your enter button when you use just a single one it's probably called a bit wise operator if I'm not wrong but with this this is called an or operator in and conditions both the conditions needed to be true in or condition either of the condition need to be true so if age is not 18 or is allowed is not there or is allowed is true then we will print haha so let me remove this that means the value is false that means this condition right here is false but age is not 18 that's true then what will we get we should be seeing haha and that's what happens and it's not restricted to only two conditions you can put as many as you want to here so you can put and and again put some condition and after the condition is done again you can put or or but obviously you'll have to Nest them correctly according to your logic other thing that you can do is have a nested if condition so if age is not 18 if this part right here is true then you can have if condition again which says if is allowed is there if is allowed is there then you can print lolol else you can print haha and then we can run it and we will be seeing haha because age is not 18 that's true but is allowed as false so we come over here and we print haha and one last thing I would like to answer which I started this session with what is the purpose of these brackets these curly brackets that we see in if conditions in functions well that's because of something known as scope all of these if conditions and all have some scope within them by scope what do I mean well if I have a variable described inside of the if condition let's say string for some value which is equal to hey and then I have print some value yeah this works but if I just take this print some value and put it over here it doesn't recognize this variable it says undefined name some value because this variable is not defined this variable is only accessible Behind These two curly brackets not even inside of this else condition so to use this value you'll have to Define it outside of the if condition so that you can use it everywhere so you'll have to Define it in the function scope not inside of this if condition that's what the bracket signifies it's not just integer you can compare you can also compare string so we have a lot of string some value which is equal to High then we will have some value is not equal to but obviously you cannot compare integer because it throws a warning neither type of the operands of is equal to is a subtype of the other this basically means some value is a string 18 is an integer you cannot compare both of them they are very different from each other so here you can have if some value is not equal to high then we are going to print wow otherwise we will print naha just the standard one and we get wow because it's not high it's high and then when we run it we get nowhere that's cool so you can have is not equal to working with strings as well other things that we can do over here is by using if some value dot is empty that means if some value is equally equal to this this is what is empty stands for so if we run this we get Na and if we have Dot is empty and then when we run it we should be getting naha as well because that's the same thing and then if we use if is not empty which is the opposite of is empty there are other values that you can use here so some value Dot starts with so you need to mention like what does it start with so if it starts with H then you can have that or you can have dot ends with and then you can see if it ends with Quest exclamation mark so this was about if condition ternary operator this is basically like if statements but instead of if statements being so big you can just write it in a single sentence what do I mean by that let's say we have string value which is equal to well I just want this thing to be here so what I'll do is some value dot starts with h all right so if some value dot starts with H then we'll put a question mark here which basically says if it starts with H if the condition is true what do I want to return well I just want to say that then the value is wow otherwise so far otherwise you put colon and then you have naha and then you can go ahead and print the value so then if we run it you get wow which is this our idea and wow again so what have we done here well we have put the Boolean condition now if I just stopped at this this wouldn't be a string value it would actually be a Boolean value right starts with returns a Boolean and that's why we could use it in the if condition but I don't want to store string uh Boolean sorry I want to store string so to store a string I put a condition over here and the condition is started by a question mark so you say does this start with h if that's the case if the condition is true then I want vow to be the value of string otherwise I want naha to be the value of this string and then after we have assigned the value we just print out the value now variables are just a way to store data you can just eliminate the this variable copy this print it and that would work exactly the same way and it starts with you don't have to type in just the initial characters you can pass in much more so if it starts with ha then you can run it and we should be seeing naha now and that's exactly what we get so this was ternary the third type of control flow is switch statement this is the Syntax for switch we have switch then you pass need to pass in a variable whose value needs to be checked so we'll pass in some value then we are going to have a curly bracket which specifies the scope again then we have a keyword called case and in the case you type in the value so some value will be high if that's the case I want to print so I'll have hello and that's it let's try to run it so if I run it I should be seeing wow wow but the third one is not printing and the reason for that is some value is high with an exclamation mark and here the case is not there of correct exclamation marks so I can put it over here and then run it and then hello what is this weird kind of syntax well we are just passing in the switch with the value that needs to be checked and these are the values that you know some value can have so the first case is high with an exclamation mark and if some value is equal to high with an exclamation mark you print hello since this was the case you got hello so to handle the else condition what you can have is default if this is the case or something else is the case okay so you have caves high with an exclamation two exclamation marks away yeah or if you have a third case which says hi with three exclamation mark but none of the values are matched by some value then we will have print U okay so let's try to run it and we get wow wow and yo so I hope you understood some value is basically matching with the cases over here if you're from other programming languages you're familiar with this but what you're not familiar with is you don't need to put Breakaway up so if you're from Java or something you know that after every case condition you need to put a breakaway that's a rule in Java but you don't have to do that in dot especially after Dot 3 the break thing was removed from here you only have to write this break if you know this thing right here is empty so if this is empty and you don't want to execute anything you put break over here so break is required when the case is empty over here but if it is not empty then you don't need to put break what I mean by this is if I remove this High let's remove this hi let's remove this high and actually let's put our first case matching as the value of some value and now if you try to run it you get wow wow which is Wawa and U which is the default one why did the default one run when the first case matched because we didn't put break what if I put print over here I say hi you can just run it so we have wow wow and hi but that's quite strange right I mean the first case matched my value but I'm getting the print statement of my third case which doesn't even match my value that's why I said when you have empty cases you need to put break so if you have break and then when you run it you will not see high yo anymore you only get wow wow from the two conditions appear there is some limitations with switch for example just like we had int age is equal to 18 then I could check if age is greater than equal to 18 I cannot do that with switch so switch statement is basically there so that I can check for equality however there are more things you can do in switch statements now after the release of dot 3.0.0 switch statements were enhanced more like they were upgraded so what now I can do is int age is equal to 20 okay suppose the age is equal to 18 and then I want to if the case is high then I want to print yep and here we can see yep will work what I want to do here is not just check if the case is high I also want to check if age is greater than 20 so to do that I can do something over here what I can do is add when over here so here I can just add relational operators or relational things just like we had in if statements so I can just add when age is greater than or equal to 20 that means some values case should be high and if that's the case then we will check if age is greater than equal to 20 and if both of these things are true then we will print yep so if I try to run it I get yep written over here but what if I just reverse the condition ages less than 20 I get you because that's the default one since it did not match this condition it executed this default part obviously it also ran through these two things but they weren't matching it was matching with this one so this was a new thing that was introduced in switches in dot 3.0.0 which you can do so this was all about if conditions ternary operators and switch statements so here's a challenge or exercise for you you need to develop a program to calculate the shipping cost based on the destination Zone and the weight of the package and these two things are provided to you usually these two things are provided by the user input but since we cannot do that in dot pad let's assume these two things to be a certain value all right and based on this you need to calculate the shipping cost so if the destination zone is XYZ the shipping cost is dollar five per kilogram if the destination zone is ABC the shipping cost is dollar seven per kilogram and if the destination zone is pqr then the shipping cost is dollar 10 per kilogram and at the destination zone is neither of these three things then you need to display an error message saying the destination zone is incorrect so what are the given things to you well the destination Zone and the weight of the package so let's say we have two variables destination Zone let's say the destination zone is pqr and you're also provided the weight of the package and weight of the package can be let's say double because weight can be in decimals so we have double weight in kgs equal to let's say six all right so we have a package that is six kilograms so now you need to follow these conditions and print the stuff out pause the video and try to do it on your own if you're able to do it then you've successfully mastered if conditions and you know how to go about it congratulations if you were able to complete it now let's code along so what do I have to do let's understand the question first I need to check if the destination zone is XYZ or ABC or pqr so that means I can either use a switch condition or an if condition so I can just go ahead with if if I'm unsure about anything then I can just take if destination zone is equally equal to pqr yeah if that's the case then what will the shipping cost be it is ten dollars per kilogram and I have six kgs of parcel so that means I'll have to multiply 6 with 10. so that just means I'll do print rate in kgs into 10 right and then maybe I want to type something else so what I can do is you know string interpolation so I'll just add dollar wheat and kgs into 10 like this also a string over here then I'll have shipping cost as weight in kgs into 10 right now I'll just put in my lzif condition and now if destination zone is equal to let's say x y z so we just put x y z over here then we are going to go ahead and print shipping cost weight in kgs into 5 because we have five dollar per kilogram here and finally we have another one not finally we have another one which is destination zone is equally equal to ABC and if that's the case then I want to print shipping cost weight in kgs into seven and if it's none of them then I just want to go ahead and print else invalid destination Zone all right so I think we're done with the program at also very small program but it solidifies the concept of if conditions now we can run it and if we see we get shipping cost as 60 6 into 10 because it's pqr what if I change this to ABC and this to 4.5 and then I run out I get 31.5 because 4.5 into 7 and if it's some invalid destination Zone like NYC and then when I run it invalid destination so great now we can write this exact same thing in switch as well because we are using equality so you can just have switch destination Zone then I will just go ahead and put in some cases so I will ask case pqr then I can print this exact thing then I can have another case x y z then print this same thing here and finally the last case which is ABC so we'll copy this paste it over here and print this and you are forgetting the default one so let's put that in and there we go now we can comment this thing out just because you know I just want to ignore it temporarily and if we see we have invalid destination Zone correct and if I put ABC we should be seeing 31.5 again great now there are a few changes we can still make in the switch and the if conditions and what is that if you see we have shipping cost written over here three times and if I want to change the shipping cost written over here in my UI let's say I want to call this billing cost so I'll have to go ahead and change it everywhere now this is not very acceptable to me you know I have to put in extra efforts to so to resolve this what I can do is just have double cost which is equal to let's say 0 initially then I can take this cost and put it over here cell of cost is equal to weight and kgs into 10 then I can copy this put it over here as well so I'll have kg weight and kgs into five then I'll put cost is equal to weight in kgs into 7. now I can just copy the Sprint function and remove everything else then I'll have statement printed out over here billing cost weight in kgs into seven not that we'll just print out cost right because that's what we have assigned over here and whenever I want to change the UI I can just go ahead and change it in one place and it will affect everywhere so if I run this I'll see billing cost now this was a slight Improvement but you know I just don't have to go through every if condition there I can just change it in one place and that works well but now the problem comes in when we have an invalid destination Zone if we have pqra I will get invalid destination Zone and shipping cost both why because it matched through all of these cases then went to ill's condition and in the ills it printed out invalid destination Zone so it printed out this and it also print out the shipping cost which is a normal statement so what I need to do is make a way so that after this else condition gets executed this print statement doesn't get executed and nothing else after it gets executed so for that I'll just have return over here this is a keyword that we'll learn more about in the functions section but for now you can just consider that when you return like this you are returning well nothing from this function so it just says Hey the function has terminated at this point it has been completely executed and there's nothing to run forward so when we run it only this gets printed and nothing else after this will get printed and there we go so after this return this program ends over here and doesn't execute anything else so if you were able to do it on your own congratulations if not try to rectify your errors and build your logic this is a good time to do so now let's get done with it and dive into the concept of Loops so what are these Loops when when would I want to use Loops well you would want to use Loop in condition like this let's say you want to print something let's say hello world and you want to print it six times for some reason so you'll just type go ahead and print the six times and then run it so there we go we get Hello World written six times now what if I want to write it 10 times I'm just going to copy this and write it four more times and then run it and there I go so we have 10 hello worlds written now what I want to do is just go ahead and and index all of this so I have Hello World one hello world 2 hello world 3 10 years later so I had to do a lot of tasks to get all of this running and as a programmer I'm always trying to reduce my task because I'm lazy so what I want to do here is introduce you to the concept of loops and the first type of loop which is for Loop there are multiple types of Loops so in this for Loop what I need to do is write a 4 and then a curly bracket so just like we had in a function you know an if condition as well we need to have first if so instead of fifth I have four after that parenthesis and then a block and you know why we have a bracket away a curly bracket so signify that whatever comes in your needs to run that many times first you need to initialize so you need to create a variable and initialize over here after that you want to pass in a condition and after that you need to pass in some sort of increment or decrement for the variable you've created now all of this is quite abstract right so let me comment it out so to comment it what I just did was select all the code pressed command slash and there we go all of this code is now commented so I don't have to go through and you know just add multi-line comment over here that can be erased by just you know selecting a bunch of code and doing command slash anyways now let's follow this pattern that we have so I'm going to have first initialization so I'm going to have 4 int I which is equal to 0 generally in your initialization part you have int I written so you've created a variable here now why did we have a variable so that we could put a condition and what is the condition well the condition is generally based on the variable that we've created so I'm going to put here a condition I is less than 10 so I'm starting I from 0 so over here you could have 1 but then you would want to make this condition I is less than equal to 10 why because I wanted such that this hello world gets repeated 10 times so this is my condition and I just want to increment it so here I've created a variable now I'm using that variable over here I which will be less than equal to 10 since it starts from 1 I have to put less than equal to 10 so it will be 1 2 3 4 5 6 7 8 9 10. if I started from 0 and did till I is less than equal to 10 I would print it 11 times this Loop will run only if this condition is true after the condition is false it will not run but it will just get out of this for Loop now we can take the Sprint and paste it over here and let's remove rest of the things and run this and here we get we get hello world one written 10 times why did this happen let's go through this again we have created a variable entire is equal to one then we have put a condition I is less than equal to 10 and then we have incremented that I plus plus basically stands for incrementing so I plus plus is basically equal to I equal to I plus 1 and I minus minus is equal to I is equal to I minus 1. this is what it stands for okay so here I've just done this this is a shorthand syntax you can also do stuff like I plus equals to 2 which basically means I you know I plus equals to 2 means I is equal to I plus 2 so you can guess how many times this hello world one gets printed and it gets printed only five times because initially it starts from 1 and it matched the condition 1 is less than equal to 10 I plus equals to 2 so now the value of I is 3 hello world 1 gets printed then we have the value of I as3 so it will neglect this condition so this is just the primary initialization part all right this will only run for the first time when the for Loop begins to run after that it loses its value then we directly have I is less than equal to 10 so 3 is less than equal to 10. so that's true the condition is true so it prints it out again and then we have I plus equal to 2. which means 3 plus 2 5 then 5 is less than 10 5 plus 2 7 then 7 is less than 10 7 plus 2 9 and after that 9 is still less than 10 so it will have I plus equals to 2 which will be 11 but now 11 is not less than equal to 10 it is greater than 10 that's why it will not print this and then it will terminate this Loop meaning it will get out of this Loop and won't run this loop again so that's how we get Hello World written five times so let's jump back and print hello world 10 times so now instead of showing one year I'm just going to show I and we already know how to do that we've seen that using string interpolation and there we go we have all of this written but generally most of the for Loops starts from zero and they go till less than 10 I plus plus and then if we run it we get Hello World zero one two three five six seven eight nine but how I want it is one two three four five six seven eight nine ten the way I had earlier so what I can do over here is have dollar I plus 1 written wire so whatever is the value of I I'll just increment it by one and display it over here then I'll run it and there we go we have Hello World exactly the way we wanted it why does this I start from 0 because most of the calculations or most of the things that we have in programming start from zero for example if you want to extract some part of a string you have a built-in method for it so let me show it to you we have string High which is equal to hello world and then if you want to get some part of this string let's say I just want to get hello from here what I can do is hide Dot substring and substring basically asks you to enter a few things here you have to enter the starting point and an ending point if you just click over here in the documentation you'll see string substring you have to pass a starting value and an ending value and this means you know in a square bracket it means you have to optionally enter it you'll get to know more when you learn about functions but as of now just understand what I'm saying with this method you need to mention a starting point if I mention a starting point as one like a normal person would and you know I wanted till your so I'll just say one two three four five so I'll just pass in five and then you know print it out so let me run it we get Lo written 10 times obviously because we are in a for Loop right but we get Lo written instead of hello why is that the case that's the case because the numbering in strings or substring starts from zero just like anything else in programming as I said only length was an exception because length gave you the real length like a normal number it didn't start from zero it started from one but other things start from 0 and that's why it's recommended to have I started from 0 as well because if you're using High Dot substring in a for Loop that's probably because you want to do I comma 5 or let's say 11 so we have hello world because I was 0 then I incremented that's why I was 1 so we have 1 to 11 so we have Hello World low World low world over world and so on if you used one year instead that would cause a problem it would just start from Hello World right so I hope that was clear and this is why we start from zero where generally not always but generally and here you can have any kind of assignment that you want you can even have multiplication division but make sure you don't do anything wrong because if you do something wrong like I minus minus over here that can cause big problems so if I run it hello world hello world one and we get uncaught error range error because initially it starts from zero so it print hello world exactly then hello world one but then its value became -1 and you cannot pass in -1 to a substring you know I'll just remove these things and then run it maybe it fixes the problem but you see after I run it there's nothing printed out in the console if you can see anything my computer is now Frozen and you can see page unresponsive it is unresponsive because we got stuck in an infinite Loop why did we get stuck in a finite Loop let me explain and then I'll exit the page and come back the reason for that is entire is equal to 0 I is less than 10 I minus minus so it ran the first time hello world zero that's cool hello world one actually that's nice after that it became I is equal to -1 if it became minus 1 that means minus 1 is less than 10 after that it became minus 2 is less than 10 minus 3 is less than 10 so it's an infinite Loop the condition is always true so it's going to print every single time causing our app to lag and you know my PC to crash so let me close the app I'll run this again and fix the condition over here so make sure you don't run into Infinite Loops like this great so suppose we have some value over here let's call hello okay and then what I want to do is Loop through every single character in this string and after I've looped through every character I just want to print it you know so to do that what I can do is for enter is equal to 0 just like the previous approach and then I is less than value dot length I know this value dot length will give me the length of the string and then I'll increment the value of the variable I cool I can do this because value dot length will give me a number here also we had a number don't wrote learn whatever I'm typing here just understand the fundamentals so obviously now I want to extract one character from it so to do it let's see if value has any method for it so I can just have character there's nothing like that so if we don't have any method for it what we can do is print it like this value then a square bracket and then you'll have I mentioned over here now if I run it let me just remove the previous for Loop let's run it again and we have hello written over here we have hello written on every new line because print is getting called again and again we are getting h e l l o hello if I want just this L I can just have 3 return and I'll get L written five times and there we go so I hope you have a good understanding of for Loop the foreign Loop that I've written over here in the comment is basically another type of for Loop that I wanted to discuss but the example can be a bit more tricky and for that we'll have to learn something known as I trebles less then it will make much more sense to you using it with string is not very much intuitive as of now so we are going to cover this in the list section all right now let's try to do something similar in another type of loop which is the while loop now while loop is similar to for Loop but instead of having all of this what while loop has is while and here just a condition so this is similar to the If part right you have if then you pass in a condition and the block with while you also have a condition but it will run as long as the condition is true so let's get started I'm just going to comment this out just so we have reference because we are going to rewrite this for Loop in terms of the while loop now coming to the while loop we don't have to pass in any kind of you know initialization we do have to put in condition but no value assignment is also needed what can we do there so we have int I equal to 0 all right so I've created this variable outside of the while loop then I'll have I is less than value dot length so we have a condition written over here then I'll print value at I and then if I try to run it you can see our dot pad is again stuck because we have stuck in an infinite Loop we'll have to exit the page we'll have to run this again and understand why this infinite Loop happened in the first place so let's go over the code we have value written over here and I is equal to 0 while I is less than value dot length that means 0 is less than 5 we are printing value at I so that means I'm printing value at 0 then this is true again some printing value at 0 this is to again value at 0 this is to again value at 0. now your understanding why we are stuck in an infinite tube it's because we have not modified the variable we are using for the condition either the value dot length has to decrease or I has to increase so to increase I what we can do is just have I plus plus or I is equal to I plus 1 if we have that and then we run I hope things are neater and indeed they are now we get hello written over here so the initialization is done over here the condition is put away a and I is equal to I plus 1 is done over here but obviously this int I can be used anywhere in our code so example if I have this and I try to print I over here that's not possible because I scope over here is limited it's just limited within this thing right here but since I've created I is equal to 0 in this function not in the while loop because it's not allowed I can just print I over here and it's fine I can print i o air and that's fine there's a third type of Loop and that is the do while loop so right now the problem with these Loops or the benefit of this Loop is it is entry control Loop meaning if you want to enter this Loop you have to pass the condition but what if I want to run the loop at least once and after that I will check the condition and based on the condition I'll write the code how does that work that's what you know our entry control exit control Loop means these two are entry control just think of it like security guards in your building all right they will let you enter only if you have a valid pass or something this is what for Loop and while loop does if you have a valid condition met you can enter but with do while loop you don't have to have any conditions met you can do that after you've run it once so this is the Syntax for it we have do so you can do whatever you want over here and while so this should run while this condition is true and a condition is I is less than value dot length let's comment this while let's comment this for Loop and let's shift our eye down so that we have a clear understanding of what's going on so if you have I is equal to 0 do what do I want to do well I want to print value at I all right and I'll do that while I is less than value dot length and I'll put a semicolon here this is a Syntax for it and then when we run it and we are again stuck in an in finite Loop why is why are we stuck in an infinite loop again we have not put any incrementing decrementing conditions over here so let's exit the page run it again so now you have an understanding you will use I plus plus over here in the for Loop but in one Loop you'll have to do it over here and the do loop as well you'll have to do it over here let's say we incrementing it over here and we get hello printed out over here but you might say What's the difference right I mean that's fine but let's do something else what if I have I is less than I or while I is not equal to I this is just always a false condition because I will always equal I if that makes sense right so what we should be seeing here is H being printed out zero times you know it there should nothing be printed because the condition is false obviously so if we try to run it we get H printed out anyways well that's because do while is an exit control Loop meaning the condition is checked only after the do Loop has run so what's happened is the dart compiler saying do print value at I then increment the value of I and obviously then if you have while I is not equal to I while I is not equal to I I will always be equal to I because I is I right so it just prints out H one single time and then the condition is false it never runs again but if we do the same thing in for Loop it will never run because it is an entry control Loop so this was a big difference between do while loop and while loop follow so I hope you're clear with this now there are a few more treatments by few I mean two so there is two things that I want to show you break and continue let's say we have to ignore this e all right I just want hllo to be printed or let's just ignore all three of them ell so we have ho printed out all right so what can we do here well we'll have to do something in the for Loop only because that's when we get the characters right so we know we have to do something over here but what do we have to do well we only need to check if I is equal equal to 1 because if I is 1 that means we are going to access value at 1 which is e remember that H is 0 is 1 so if I is 1 or I is 2 or I is 3 then I don't want to print anything I just want to skip it that's where continue comes into play so let's just have it and then run it and also let's comment out while loop over here let's run it again we have who printed out why did that work well what happened here was we put our F condition here and checked if I is 1 or I is 2 or I is 3. so in our first case none of these conditions matched that's why it printed out H then I was 1 so I checked is 1 that means it needed to continue with continue you basically get out of this for Loop and run the for loop again skipping the current condition so if I have to show you what happened over here well when I is equal to 1 came continue basically said a let's rerun this entire thing from the for Loop but with the incremented value we're going to skip rest of the things that are mentioned down below we are directly going to start from here again with the incremented condition so then I is equal to 2 came in and again this condition was met so we again run continue that means we again skipped rest of the things down below and we again started from for Loop but with I equal to 3 then we add I is equal to 3 condition also met so we again continue and then we started it over here then we add I is equal to 4 4 is less than 5 I is less than value dot length right 4 is less than 5 none of these conditions were met that's why print value at I was value at 4 and value at 4 GA was O and that's why we printed out o so we add H and O printed out so this is a case where it continue might come into your play or might come for your rescue obviously you could con you could tweak your conditions a little bit and without using continue you can make that happen it's a task for you actually if you're familiar with for loops and if conditions by now and you follow through this video I'm sure you'll be able to do it right now so give it a try and let me know in the comment section anyways I'm gonna move ahead and talk to you about break What If instead of I have I is equal to 1 I is equal to I is equal to 3 continue I have break written over here and then if I run it I get H printed out what's the matter with this well what happened here was I is equal to 0 none of these conditions are met so we add value at I which is value at 0 which is H then one came along I is equal to one condition was made break was called with break you exit out of the loop to the next code only so I'll continue to queue from year to year and you know skipped rest of the things over here what break does was throw you out of the for Loop so that you can execute next pieces of code it doesn't throw you out of this function all right many people get confused here it's not throwing you out of a function it is just throwing you out of the loop you used a 10 so it's throwing you out here and you might know this break right this break was the thing I talked about in switch cases as well in Dot 3 switch break is not required for non-empty conditions after you've mastered Loops we're going to get into the fun stuff and the fun stuff starts with functions we've talked a lot about functions without even covering functions right now we are going to dive deep into it so let's get started so before creating a function let's understand what functions are and why do we even need functions well what functions are you can see it right over here there are blocks of code well just that they are just blocks of code that you know contain your code why do we need functions well it's easier to have functions than write your entire code in just one function so imagine me writing my entire program in just one function do you think that's good idea because there will be like hundreds of things I want to do doing all of them in of just one function which is the main function can be a lot of headache I'll have to write Ten thousands or hundred thousands line of code in just one function so it's better to have multiple functions so that they have their tasks ready for example I can have one function to figure out my name one function to calculate my age one function to you know identify my gender one function to display them etc etc so it's good to have multiple functions so that they can all do their task and if there are more Engineers working on in your team you always want to segregate the tasks right you don't want everyone to just work on a single function that's right functions are very important and this is how functions look so we can deduce a type from here what is the type of the function or how do the functions look syntactically this is how they look so I'm going to put a multi-line comment here and first thing that we have here is void so first thing we are going to have is a data type so this data type can be integer string Boolean whatever data types we've learned till now it can be either of them then we have the function name so I'm just going to call this FN for function name then we have these parent thesis and then we have the curly bracket this is a simple function definition all right so let's create another function we have void Main let's create another one so we'll create void now you might ask what is this void void is basically saying that this function does not return anything so it has a data type return data type and that is void but void basically means that yeah this function is not going to return anything it is different from null null means that you're returning a null all right void means that you're not even returning null you're not returning a string you're not returning a null you're not returning anything at all and I'm going to say print name and this is my function all right and here I can just have print Revan all right because that's my name now if I run this application nothing shows up in the console and rightly so because I told you the trigger point of this application is Main and it will trigger only when this is void main so it first has to notice something known as void main if it notices that it's going to run our app and there's nothing inside our main function so what I basically want to do is take this function and call it over here so I can take this so I did something and it's giving me an error basically they're asking me to put a semicolon I can put the semicolon and then run it and as you can see nothing works why is that the case it should work right I mean that's how I can call the function not exactly because if you try to print this print name it gives you something known as closure print name this is basically giving you the address of print name it's not exactly calling print name it knows that yeah something known as print name exists and it doesn't know because we have not called the function to call a function this is what we do and we'll have to remove print from here and our errors will go away we needed to remove print from here because you can see this expression has a type of void such value can't be used when print name is called like this it returns void so if you're trying to print void and void is basically telling that it doesn't return anything so what exactly are we printing doesn't make sense right that's why we are going to remove this print from here and then run our app or on our program sorry and as you can see it prints Revan so this is the Syntax for calling a function and this is how you declare a function now let's try to do something different now we know how to call the functions let's return string from here all right I'm not going to print it I'm just going to return a string now I've been saying that this returns nothing this return string what do I mean by returning well it basically means that this function is going to well throw a value which is of the data type string that's what I'm trying to do so how can I return a string well it's very simple just called return which is a keyword in Dot so you called return and then you pass in a string and there we go we have returned a string as simple as that and the same thing goes for integer if you want to return something you return 0 1 12 and same for double Boolean whatever we've learned till now so let's return a string here let's return my name everyone r and then if I try to run it nothing in the console well that's because I've not printed anything I've just returned a value returning a value doesn't mean I'm printing anything returning a value means Whenever I Call this function I get access to the value returned from this function I know it doesn't make sense to you right now so stay with me if you come over this you see string print name what I can do is just print print name like this because it's returning a string you know and I'm calling it I can print this right and it will give me access to a string and that's exactly what we get as simple as that now we can return an integer let's return 12 run it and it will work there we go other things people usually do is whenever they get a value from it they store it in a variable how do you store it in a variable just like any other thing right if you are getting an integer what you can do is end let's say name it's not really a name but since we have name this function print name let's call it name but yeah please be descriptive I'm not descriptive here but you need to be and then you can set as equal to why did we do that and why does it work well that's because whenever we call Print name it returns 12 to us so we're basically assigning it to 12 right but it's disguised in the form of function you can think of it this way now you cannot do string name is equal to print name because a function knows that it's going to return an integer if you return a dynamic from your it it is fine okay but again you will get runtime error and I've obviously said it to you don't return Dynamic and when I say this I mean this runtime errors that we continuously get because of the type checking that is disabled in dot also if you just do this this is also a valid syntax but this print name is basically Dynamic print name you can see it over here you always want to return a data type for your functions make sure to do that all the time okay if you don't it's going to return Dynamic and might cause problems because it disables type checking it's very important that's why I'm repeating it many times all right so we have integer or you can have final or you can have variable but you cannot have constant aware if you have constant it will give you an error because constant variables must be initialized with a constant value functions are not constant values so you can use final meaning the name variable is not going to change again or variable which means it can change again now that we've understood the basics of functions let's see what other things we have first thing I want to show you is from this function if I want to return two data types you might be thinking how to return two data types right can I return something like int comma string like this will it work not really this is not a valid syntax and you cannot do this so what can I do you might ask well dot 3 added the support for something known as records in other languages it is also known as Tuple so you can use that what you need to do is wrap this with a parenthesis then you need to have end comma let's say I want to return string and here we are again going to have 12 comma let's say the one so this is a valid syntax before Dot 3 this was not allowed but with Dot 3 this is enabled and I can do this and now if I run it's not going to print 12 anymore it's going to print 12 and driven so we are able to return two data types from a single function we can also return two or more data types so if you want Boolean if you want string again you can do that but obviously make sure you match it okay since this is an integer you need to pass in teacher over here since this is a string you need a pass string since this is a Boolean you have to pass Boolean if you try to pass string over here and say let's say Hi and then if you pass false it is not valid because of the error you can understand it from here in string string Bool can't be returned from the function print name because it has a return data type of in-string bull string so this needs to be reversed and there we go so I hope you understood now you might ask what if I want to get one value from it I just want to get ravan name value from it and other things I might figure out later on so to do that what you can do is name Dot and you see here you get access to dollar one dollar two dollar three dollar four these things are known as ghettos we are going to take a look at that when we get into classes which is the next topic after functions so these Getters are helping us now dollar one stands for the integer value which is the first thing string is the second Boolean is the third string again is fourth so I want dollar two because I want Revan from here and then I can run it and we see we get driven and yeah you are able to get the type surveyor so dollar two is giving us the string type okay our dollar two is knowing that this is a string let's confirm it and how do we confirm it you can just call Dot runtime type on it and then run it and you'll be able to see string over here not just runtime type even the compile time type of dollar 2 is string you can trust me on that so this thing was called as records now another thing that goes hand in hand with records is patterns so instead of doing name dot dollar to what you can do is just destructure it right away so if you're from JavaScript this might seem familiar so you'll have to match everything over here since the first thing that is being returned is integer I'm going to call it age then name then let's say is adult and finally greeting now I can take this name and you can see no longer I can call Dollar two on it that's because it's no longer a record it's actually giving me a string value if I come over here you'll see that string over here if we can just get rid of this Arrow so to get rid of these arrows let's quickly print all of these things out so we'll have print is adult and then print greeting then let's run it here you'll see Ramon 12 Falls High and your string name so it's correctly able to get the data type and it's correctly able to get the value which is cool so you've de-structured all of this in one line This is how you can do it but obviously you need to match everything over here if you don't match it like this you see you're getting an error so you need to match it and carefully name your variables right over here because it can be confusing when you're returning more than two because you know it's kind of tricky but there's a neat solution to that we'll get to it after I've discussed more about functions all right so now let's get back to our normal function we'll get to records again but just after some time when we get basics of function clear we have known how to return values from your how to return certain data types we know how to return more than two values in a variable now you can also return string with a question mark so that it's nullable variables that are returned and then obviously you can return null okay but you have to return null or you don't have to do anything at all over here but yeah it throws a warning but it will compile okay but yeah it's definitely recommended to return null but don't do this okay if you just do return it will give you an error because when you have string question mark it is asking you to return a null or a string you cannot return nothing so that's how it's done another thing is if I try to print after return statement you'll see we get a warning over here saying dead code why is this a dead code if I just move this above let's copy this function and put it over here and run it you'll see we get hello and then null it's not saying dead code anymore why is that the case this is the case because return Works in this manner you remember break and continue it's kind of similar to that but not exactly same return basically ends the function after returning a value all right and even if you have something like void and you cannot return anything you can just call return like this and it will work because you're not returning anything you're not returning a value you're not returning null you're not returning anything but you're basically telling that this function is over just end this function right away just terminate this function no more code has to be executed after this and if we have string question mark So nullable strings we can just have hi you can return string from your and it won't go to the next thing so that's what return does it doesn't let you execute things after it you have to do everything before it functions can do much more and they are quite customizable so what are the things functions can do well first of all if you want to give some parameter over here by parameter I mean if you're having some value in your main function all right so if you have your name over here okay suppose it was a user input and your accepted user input from the main function now you want to give this name to the print name so that it can print it out and printing it is basically let's say void okay that would make more sense you can obviously return the name that is over here but let's not take that route let's remove all of these things so it's just a void function meaning it won't return anything and it's calling print name but now what I want to do is print the name that I got in the main function in the print name so now I want to pass this name to this print name so to do that I can just pass it over here so I'll have string name written over here this thing right here is arguments so this is argument of a function and now you're saying that yeah I'm ready to accept name whenever I call it and here we get an error the error is quite familiar we saw this in the start when we were just starting out and printing something right so when we had print like this you know I try to print hello world like this if you remember we've come very far with it undefined name hello now you know what this means basically means that you don't have any variable hello defined you don't have any variable World defined too many positional arguments one expected but two found let's understand this error message now so let's remove the Sprint function and to resolve this it's basically telling me just pass in some name here and it should be a string so I can just pass and drive on like this or I can pass ranavat or whatever okay so I just need to pass in a string and it can be an empty string as well but I cannot pass a null because this is not string nullable name it is just string name so I need to pass in name like this so I can pass in this name and well I'll just want to print this name that I got over here so I can just have name and then if I run it I should be seeing rivon R and that's exactly what I see now why did I have to mention string name over here well if you don't pass string over here it won't give you an error but just like in the function if you don't pass in the type of a function it will assume that it's Dynamic here if you don't pass in anything it will assume that it's Dynamic so I'm just going to have string over here and then I'll print the name now why did we have to give a variable name over here just so that I could use it in this function below as simple as that yes I cannot use it outside of this function Block it's limited to the scope just like over here we had this name limited right I could use this name just over here I cannot use this name in this function that's not allowed but yeah one thing we can do is put this string name outside of this function and then I can remove this name from here because it doesn't require any argument and it works but this thing right here is called as a global variable and many people don't like Global variables if we put this thing right over here it's called a local variable meaning function can access it right only one function where it's defined can access it it's local it's not anything Global you can consider it like your government all right you'll have local governments you'll have your Nationwide government if I put string name is equal to revanar this is kind of like a global government or your national government and this is like your local government many people are not in four of this you might ask why just you know imagine it in the form of a bigger code base this is very small so you might think yeah I know name is being changed but think of it like hundreds and thousands of functions and if you have a global variable like this which is accessible in any file in any function you can change it anywhere it is a lot of chaos because at some point you lose track of this variable name and then you'll ask yourself do I want to rename this variable by mistake you might rename this variable it might cause a big bug in your app and you won't be able to figure it out because the code base is so big so you cannot go you know blame it on code base you need to find an efficient solution for it and one of the efficient solution is you know just keeping this local variable I agree sometimes Global variables are necessary they are important but most of the times people try to avoid it so coming back to this function we have string name like this now I can change the value over here all right and then print it but the value changed over here doesn't mean the value of this name is changed I hope that makes sense basically let me try to print name I'll show you the difference now you see I get Revan Naman driver well first I've defined a variable name then I print name which is this function and then passed in a name and I've accepted the name from here now I'm setting this name that I got from the parameter here to Revan Naman and then printing the name again so then I'm able to print name which is rivan Naman the currently changed value and then I'm printing name which is this thing right here you're not taking this name passing it over here and then changing the name that was mentioned over here you are just changing the name present over here you can edit it but it doesn't affect this original variable right here so I hope this was clear this was a very important property many people don't know about n Dot so let's remove it and let's remove this thing as well cool now that we have understood this you know I just wanted to tell that you can have multiple arguments here just like we have in records you can have more than one you can have zero one two three in records you need to have at least two that's why you're returning a record right if you wanted to return a single value why would you use a record you could just go ahead and return a string but with function you can have 0 you can have one you can have two and as many as you want but what if you know I have more than three more than two it can be a bit difficult right I need to constantly match it like print name this is int age I need to pass in 12. now this is greeting so I need to properly make sure that I pass in hello and I can get confused in this especially when I have two strings over here if I have two string I can mess up name and hello and it won't even complain right so if I just have name hello switched over here it doesn't complain because the conditions are being met you have you want a string over here we got a string you want an end you got an N we got a string you got a string perfect so it works but it doesn't know we have messed up things and again this results in a bug in your program so to fix it there's a good thing created in dot which is named arguments this thing right here was called as positional arguments whenever we did print hello world it said too many positional arguments one expected but two form basically print is a function as well so these are positional arguments and you gave it two instead of the one that it requires so I can remove this but again it gives an error because it thinks that this variable is not defined actually I just want to pass in a string what I need to do is convert this positional argument why is it called positional because it depends on the position right I need to match everything carefully but now I can do something known as named arguments with named arguments I'll pass in the name and according to that I can pass in the value that's safe why do I what do I mean by that let's say you know I put the console over here just shift it a little bit now I'm just going to remove everything from here just so that we have a fresh start then I'm going to put a curly bracket over here now this might be a bit of a syntax change for you because you've always seen these curly brackets be used over here and a function but we're using it over here and this is the Syntax for required arguments what we need to do away is pass in you know string name and age string greeting just like we had before all right these are just positional arguments where the curly bracket around it but you get an error it's telling you that the parameter name can't have a value of null because of its type but the implicit default value is null try adding either an explicit normal default value or the required modifier by this it's basically telling that you know you've told that you want these named arguments but you've not told that are they necessary or not can the user not pass them and it's fine or not we need to mention that so to mention that we have the required arguments you need to pass and required in earlier Dart versions you had to pass in at the rate required but that's not required anymore nice panda so you see the error got fixed over here what this required is telling that this name thing is compulsory if you don't enter it it will be a problem so please enter it the same thing with age if I pass required aware it says pass in the age it's required and the same thing for greeting now if I do this much all the errors go away now the errors are there over here so to fix them let's get rid of them so you pass a name like this age like this and greeting like this and you see the errors got resolved why does this work well it works because we've converted this to a named argument by named argument I mean I meant this you see before passing in anything I don't have to match positions I just need to pass match the names that are mentioned over here and this is quite easy right I'm I don't constantly have to make sure that this is greeting so this has to match this isn't this has to match this is name this has to match no I can just pass an age over here pass in 12 I'm good I'm greeting I can pass hello like this name I can pass name like this and yeah this works now if I try to run it let's come over here and you see we get ravana R printed out correctly so this is the thing about named arguments you don't have to match the positions anymore you just have to match the name that's written right over here there is just a less scope of error you know you've minimized the errors now if you have more than you know two or three arguments I would recommend you to use named arguments otherwise positional is fine it will work now what if you don't want all of these fields to be required right I just force them to be required but what if they are not required for example this age if the user doesn't passage I don't care how can I make sure that happens if I just do this it gives me an error So to avoid that what you can do is make this integer nullable value all right so even if the user doesn't enter a value it will be fine it will work and if the user enters then it's fine user can enter integer value or a nullable value both are fine so if I just remove this you see the function doesn't give any error because it assumes that age is not passed age is null I also want to print out age and then run it and I get nulled over here and if I pass H like this it will work it will print out 40. so this was about you know named arguments and positional arguments I hope you got a difference between them now we can get rid of this age entirely now what I want to show you is how you can use positional and name arguments both together in this function argument or function parameter whatever you want to call it just to get the names right this thing right here is called arguments and whatever we enter here is called parameters now coming back to positional plus named what you can do is just our string not string I think it was int age so let's have end age like this and there we go you see that's a magic you can have positional as well as named arguments together now if I mention some other thing Boolean is adult it gives an error this error is there because you cannot have anything after required arguments all right you need to have them before the required arguments so you can have Boolean is adult over here and it won't complain but yeah it gives an error here because you need to pass in positional arguments so you need to pass in 12 like this you don't have to pass an h12 like this it will throw an error what you want to do is 12 like this Falls like this and rest everything is fine now if I run it there we go we have 12s now that you've understood this let's remove all of these arguments I'm just going to remove this as well now let's remove this let's call this function let's say print stuff now it's not print name anymore and here we are coming back to records I want to return a record we know how to return a record in string then we are going to have a return 12 comma rewind and here I'm just going to final or variable whatever you want to call it or you can also have something like end comma string stuff equal to print stuff so you can do this as well this works or you can just have you know final like this and then get age and name and then you know print the stuff out age print name and then run it so yeah this works but again just similar to the positional arguments this can be a scope of error and I told you I'll come back to this because of this particular reason you know I'll have to match this again and again so it's quite cumbersome error prone so there's a solution to this as well just like we had for named arguments we can have named records like this or named values like this but yeah it gives an error do I have to pass and required now no if you're passing in a record you're returning a record it has to be required that's why you're returning it right and if it's not then you can just have int question mark which means nullables you're returning a null value but I'm not doing anything of that sort it's giving me an error because I have to name the variables so I'm just going to pass int age string name then I'm going to return h12 name Revan like this and that resolves the error but here you can see it gives me an error it gives me an error because it's giving me some stuff and here by the stuff I want to do dot but now it doesn't give me dollar one dollar two dollar three anymore since this is named it's giving me stuff dot age stuff dot name so I don't have to wonder oh dollar one is this dollar two is this I can just use stuff.name stuff.age and my you know solution becomes much more easier to read let's get into the interesting stuff we have learned almost everything we need to know about functions and things that are generally used but there's no what if I tell you that you can return a function from a function so to return a function so you can just have function and you see we are getting an error we are getting an error because we are returning a string in fact we should be returning a function and then I just print out the stuff here okay so let's see how it turns out let's go over this code we've got this but let's go over the code for this we have final stuff is equal to print stuff and print stuff here returning a function and we are printing you so we have returned a function now all I want to do is call this function so I'll just do stuff because at the end of the day I'm returning a function if it's giving me a closure then I have not called it I need to call this function so I'll run and I get yo that's cool then I get null and then I get closure mean closure why do I get closure main closure closure main closure we get is because we have still not called this function right here to call this Anonymous function we need to do this we need to call this as well right you can just consider it like a variable like the stuff variable is this exact thing right and to call it we have passed into para parenthesis I am able to run it and I get yo null yo null that's great now if you're wondering why we get this null thing right here we can just remove print from here let's just call stuff let's just call this Anonymous function as it is let's remove the surrounding prints from them run it and we get yoyo so the null are gone by this we have shortened it we don't have to pass in you know curly brackets like this you can just have is equal to followed by a greater than operator which creates a fat arrow and this is called a fat Arrow function or simply an arrow function Arrow functions are used when you have just one statement to be executed or to be returned if you want you can also print over here so you'll have high but then you'll have to change this to void because you're not returning a string you're having white and we can do this because print essentially returns void you can see this print is a type of void you know it has a return data type avoid that's why that's why we can return it like this and it will execute the code so now we are done with functions now we are going to dive into classes where we are going to use functions variables if conditions for loops and everything will come together in this class so let's get started with classes now what exactly is a class and how do we define IT classes are like blueprints or templates for creating objects now you might ask what does that mean now let's take an analogy to understand it better let's imagine we are running a bakery all right so in a bakery we have a variety of baked goods such as cakes cookies bread Etc each type of baked good has its own distinct characteristics and functionality right now classes are similar to these Bakery items you use a class to create objects that share similar properties and behaviors for example you would have a class called cake that defines the properties and methods specific to cakes the properties of a cake class might include attributes such as flavor size frosting type the methods of the cake class might include actions like baking decorating and slicing using this class blueprint you can create multiple cake objects each cake object created from the class will have its own unique set of values for the properties for example a cake might have a chocolate flavor a medium size and let's say a vanilla frosting similarly you could have another class called cookie that defines the properties and methods specific to cookies the cookie class might have properties such as shape flavor size and methods or actions like baking Cooling and packaging by defining different classes you can create multiple objects with their own specific attributes and behaviors each object belongs to its respective class just as each big good belongs to its specific category so classes are like the blueprints for creating objects similar to how different types of baked goods have their own unique characteristics and recipes so I hope that definition and that analogy was clear if it's not I'll give you an example in the code itself and you'll understand it better so I'm gonna go ahead create a class that's how you create a class and I've done this outside of this function all right so to define a class we have class written then we need to give a name to the class and the naming convention for a class is different from that of a function of a variable name for a function or variable name we followed camel case right camel case looked like this in classes we use path skill casing meaning we are going to write it like this let me type it Pascal case so everything here is Big all right so yeah I'm just going to go ahead and create a class let's say cookie and then obviously we are going to have this curly bracket this curly bracket is specifying the scope of this class whatever we Define in this class is going to be within this class it cannot be used outside in this main function I hope you're clear till there so yeah we have created a class now but what does our class do as I said cookie might have different properties now what are these properties we've actually learned about these properties before these properties are basically variables or methods methods are also known as functions all right so classes can contain variables so that they Define different properties on a cookie then it might include functions so that we can change the behavior of the cookie or we can put in some actions like baking cooling packaging so how do we Define a variable here exactly how you would do in a function so here you can have a variable let's call it string shape which is equal to let's say Circle so this is a shape and this is also a property of this cookie class because this cookie class is known by this variable you know you can access the shape property and get a definition of how this cookie might be so if you do cookie.shape you'll get access to you know that it's a circle now we can introduce more variables you can create as many as you like so we can go ahead and create let's say int or double if you want to be precise double size is equal to 15.2 let's say this is in centimeter all right you cannot put go go ahead and put centimeter like this so I've put a comment here saying that this is in centimeter or inches or whatever I would go ahead with centimeter and then let's say I just want these two variables now I want some function now what will my function do well it's just going to let you know about some actions in my cookie making procedure so it's just going to have void baking and then I'm going to create my function and this function in a class is known as a method so I can just name it like this you can call this function but to be more precise you call this a method when it's inside a class and now I can just go ahead and print baking has started all right now I can create another method as well and this method can be another function so it can be Boolean let's say is Cooling and then we have this and then we are just going to return false so the cooling process has not started yet obviously right now this is a false variable but later on we are going to modify this a little bit all right so now you have a clear view of what this class is this class contains a bunch of properties that are unique to this cookie class because if I create another thing you know if I just Define all of these publicly in a main function there can be other things that use these values I don't want that I don't want you know a cake to have all of these properties because cake might have something else I wouldn't want something like a bread to have these things or what a cake has because all of them have different properties and different methods of creating them that's why we have created a class and have all properties inside of it now how do I use this cookie class for functions we could call the function like this if I had a function let's call Main again you know if I have a function I can call it like this but how do I call the cookie class it's quite similar to how you would call a function all you need to do is Cookie just the name stack name and then you go ahead and call it and there we go we have instantiated this is called instantiating so we have instantiated a class and then when I run it what should I expect should I expect baking should I expect a schooling value or should I expect all of these values well nothing really comes well if the other case well first of all we are not printing anything why should we get access to anything right so let's go ahead and print cookie now you might say yeah you're printing it over here so we are printing something not really these methods will only get called when you actually you know go ahead and type cookie dot baking or cookie dot is cooling let's run it and we get instance of cookie printed out what is this thing well this thing is basically saying that we have a variable or we have like an object of cookie created that's what it says and what do you mean by object you might ask well cookie object can differ as well right I mean a cookie can have a different shape it can have a different size that's why this is called an instance of cookie it is an object made on the same properties that a cookie has now you might ask how can I access all of these values I just want to print them out well to do that you can just do cookie dot so you need to call this okay if you don't do this you'll have cookie Dot and you won't get any Auto suggestion but if you have cookie like this so you have instantiated or created a cookie instance then you have access to this and then you can call Dot and then you see we have access to shape size something known as hash code we know runtime type baking is cooling to string no such method let's call to string because we know what to string means it will just convert it to a string right so let's run it and we again get instance of cookie class basically it's just saying that whatever you have in cookie class I'm just going to convert that to a string so whatever it gives me I'm just going to convert that to a string so it was basically returning you know let's say instance of cookie like this and let's say the string wasn't there so it just converted it to a string and returned it to us but in the console we see this as a string format only there's no difference let's call Cookie dot shape if I do that and run IC circular that's cool right now I can just have size and then when I run it I get 15.2 now you might say I want to print out centimeter as well how can I do it well we already know how to do it we'll convert this into a string format we'll put braces over your curly bracket then dollar this is string interpolation I told you whenever we have more than one thing you know accessing the property over here or something we have to put a curly bracket over here so and let's leave a space between them otherwise it will be stuck together as you can see 15.2 centimeter I'm just leaving a space here so we have 15.2 centimeter like this now I can go ahead remove all of this and what I want to do is call cookie.baking but I'm not going to do that in the print function because I'm smart I know print has already called here so why should I call Print again so I can just have cookie dot peaking and then we run it and we have baking a starter we can also have cookie let's save it away a cookie dot is Cooling and then when I run it should I be seeing false over here not exactly because you're not printing it so we have to print it and this is just like a normal function all right if you have called this cooling it is going to return a Boolean value so I'll have to store it in a Boolean value let's say is Cooling or let's make it more descriptive is Cookie Cooling and then I will print is Cookie cooling I've named it this way because there's a chance I'm going to create a cake class and use it here as well if I'm having a k class I'll have two is cooling because baking a cake also requires cooling I hope so at least and then when I run it I get false all right so my variable name is quite descriptive something to learn from it but now you might see that I'm using cookie with parenthesis over here cookie with parenthesis over here as a smart programmer I do not want to create these classes instance again and again so here I'm creating one instance then again I'm creating another instance I don't want to do that so what I'm going to do is just create one instance which I will use again and again and how can I do that well I'm going to treat it like a variable all right so I'm going to store the instance of this cookie class in a variable and then I'm going to use that instance every single place so I'm just going to have cookie cookie which is equal to cookie and then I can replace this cookie with DOT baking cookie dot is Cooling and then run it and we see the same output but the difference is the cookie class is not being created again and again now I don't want you to trust me on this and by the way this is the Syntax for creating a variable right you mentioned the type of the variable so now the type is now cookie earlier we were using end Double all of that but I've introduced user something new which is Cookie so you can create your own class and mention it as a type over here and then you can use it or you can just have final cookie equal to cookie and let dot do its job and it's able to create cookie over here that's great there will be no visible difference in the output now there's a few things more we can do actually I'm just going to remove all of this and now what I can do is let's say I've created a cookie class but I don't like how this shape is over here I want it to be rectangle and I want to increase the size how can I do that well I'm just going to use this cookie class and uh cookie instance let me make that correction cookie instance all right or a cookie object this is what is known as an object and this thing right here is a class and as I said classes help us create blueprint of an object and using that object we can call Properties or actions or methods on it so I hope the definition makes sense now now what I want to do is change the shape so I can have cookie dot shape which is equal to let's say rectangle I can do that and I can go ahead print cookie.shape over here I can go ahead and print cookie dot shape over here let's run it and we should first see Circle then rectangle and that's exactly what we see sweet now you might say hey this is a final variable right if this is a final variable How can I change the value of cookie.shape the reason for that is this cookie object is final the cookie dot shape the shape property is not final right I've not defined it like final string shape or final double size if I do that I won't be able to change it over here but I've CH I've put final as cookie that means I can go ahead and change the shape and the size property on it so if you just go ahead and create cookie class again because cookie can only be given to cookie you can see the final variable cookie can only be set once so now that we have understood this I just want to take any this example and tweak it a little bit what if I do cookie.shape like this then I go ahead and do cookie dot shape is equal to rectangle and then I have cookie.shape I'm just going to remove this all right what do you think we will get let's run it and see we are only getting Circle we should be getting Circle and rectangle right we have changed this but that's because I've told it to you before the reason for that is we are creating cookie class or the instance of the cookie class here then I'm having dot shape so I'm creating a new object okay and then I'm calling the dot shape property on it that means this cookie class gets created all right and then we are accessing the shape property on it which is circle then here we are creating a brand new cookie object if you don't understand this let me draw it out let's say I have this thing right here and this is a cookie class I've created an instance of the cookie class and I've named it let's say cookie one because I've not really put it in a variable but let's assume I've put it in a variable all right so this is final cookie one is equal to cookie so I've created this over here so all the properties are being run again so that means the shape is created size is created all the functions are created over here then I've gone ahead and created another cookie class and this is a brand new cookie class because I've initialized this cookie class again and then you know when I create the cookie class I'm just going to have let's say cookie 2 over here so I've created size shape and all the other functions and methods on it then what I've done is Cookie dot shape is equal to rectangle that means this shape thing I've just replace this value with another value so I can go ahead and remove this and now this is a rectangle all right so I'm just going to denote it by R and then I'm creating a third cookie class and here I again have to create size shape and then all of the actions like methods and all of that so we have done that and then I'm just printing it so these two are just being print but this value was changed but was never printed and that's because this cookie dot shape cannot be you know used again until we store this in a variable only if we store this cookie instance in a variable can we know that yeah we have changed the shape now we want to use this cookie too because that's what it is this is cookie two right so I just want to print out the shape of this cookie too since you have not stored this cookie to variable anywhere we cannot use it because every time we call this it creates a new object and rightly so why would it not create because I might have to edit out the shape I might have to edit out the size and I will have to create different things for it and that's why it's important to store instances of classes in variables and use them correctly also it's better to store them in a variable because sometimes as you can see we don't want to create the cookie class again and again I just wanted to use the cook same cookie class but also in some cases you know class creation can take a lot of memory in your app not a lot of because it has to go ahead and create like these strings these doubles all of these methods it has to newly create it and that requires memory because all of these things where do they get stored they get stored in the memory of the program you're running so when I'm running it all of these things are getting stored in the memory of the program and I don't want to increase the memory right do you like any app that is you know big in size not exactly right so we are trying to reduce that but since this is an example of a program we don't want to increase the size of the program and it might also take more time than expected or more time than normal to create all of these classes instance again and again because I'll have to create this first then I'll have to create this again then I'll have to create this again so I have to create three objects that takes more time than creating just one object right that's why so I hope you understood this concept of classes let me just go ahead and create the final cookie instance Sala final cookie which is equal to cookie great now to edit out some values I have to do cookie dot shape which is equal to let's say a rectangle and then I have to edit the size I'll do cookie dot size is equal to 16.2 that's fine right but the problem I have right now is whenever I have to create an instance of the cookie class and you know if I want a rectangle I'll have to continuously pass in yeah final cookie is equal to cookie cookie dot shape is rectangle cookie dot size is this much now I have a modified cookie with me I don't want that I just want to go ahead and give the values initially only so to do that we have something known as Constructors what are these Constructors these Constructors are things that run when you create an instance of this cookie class right so as soon as I call this thing these parentheses The Constructor of this class will run and that's what I want to do all right so I'll just have cookie the Constructor is named after the class of the name itself then it has this parenthesis and these blocks so it's kind of like function but it's different from function in different ways in terms of syntax yeah it looks similar to a function but here you don't have to mention any return data type because it's a Constructor right why would you want to return anything from here function names can be anything but Constructor names have to be after the name of the class if you create cookie 2 over here it will give me an error you can see it thinks the variable cook name cookie to a center lower camel case identifier it saves this because it's considering this other function so if we just you know get a chance to see this documentation you'll see Dynamic cookie too it's thinking that this is a function it's not a Constructor but actually we want a Constructor so it has to be right after the name of this class and then we have a block similar to the function so whatever variables we create whatever the scope is is limited over here and what I want to do over here is basically ask for the values of the shape and size so to do that what I can do is just Define string shape over here double size over here then I can get rid of the these things and then I can have this dot shape this dot size asked where and now you'll see we are done and it's giving us this error because this function block is not necessary until you add something over here so I'm going to add your print cookie class cookie Constructor called and now the error goes away that means if I don't mention this block it's fine I can just have this and this is a Constructor as well but if I want to go ahead and print something as soon as you know cookie is called or if I want to you know start baking as well so I can just start baking like this I can call the function right here I don't have to go ahead and call Cookie dot baking like this over here what you can do is just call baking why because we are in this class if you are in this class you don't need to call Cookie you don't need to create an instance of the cookie class you can just go ahead and use baking over here you can just go ahead call is cooling over here you can just go ahead and use shape and size you see we get an error over here earlier we didn't get that and if you see the error two positional arguments expected by cookie.new but zero found so that's quite to break down in this error message well you already know what two positional arguments expected means that means it requires two things to be passed in over here and this error message is similar to what we get in functions so basically it's asking us to give string shape and double size we can get that from the cons context so that's fine but what is this cookie dot new basically whenever we create instance of the class it was recommended to use new cookie like this if you have learned Java you already know that this new class or this new keyword helps us to create and allocate memory in Java but that is not required in Dart you can put in but it gives you a warning because that's not required anymore now we have the cookie instance created like this now I can go ahead and mention the size and shape so if I have 20 comma hello will that work not really because I've messed up the positional arguments what I want to do is go ahead and have hello 20 like this all right so the shape is hello and size is 20 and then if I try to print cookie dot shape print cookie dot size and then run it you see we get a bunch of things that are called first cookie Constructor was called why is that the case well we created an instance of the cookie class all right so this Constructor was called when this Constructor was called it verified that yeah the shape and size are given correctly then we have the curly bracket which was run so it printed out cookie Constructor calls so the first thing cookie Constructor was called then it ran the baking function so baking has started was called then we add hello printed out which is cookie.shape and cookie dot size hello 20. now you might be confused about this thing right here what is this this so let's go ahead and print this right if you're confused just print it out it should give you certain value right and you see we get instance of the cookie class so with this we get access to the class we are in it gives us access to this class and that's why it is called this so I can go ahead and call this dot baking as well now you might say why didn't I do this dot baking over here and I didn't do that because it would give me this unnecessary disqualifier if you're in the function why would you want to call this dot baking right when you can just call baking now a valid question would be why do we have to put this dot shape and this dot size over here why can I not do shape and size over here and when we try to do this you see non-nullable instance field shape must be initialized since we have not given a value to these things it's telling us yeah at least give it some value and then pass it or have it in the Constructor right and then when we run it we get cookie Constructor called baking has started null null that doesn't seem to work does it well that's because it has gone ahead and created new shape and new size variables all right and since you have not put in any variable data type over here it is considering that this is dynamic so if I just do string shape and end size it will not throw me any error it works fine and then when I try to run it it still gives me null but the difference is now the shape has string shape and this size is in size basically when you have these two variables created like this these are Dynamic they're not referring to this thing that you have aware it is automatically creating a new thing now you might say let's just discard all of them let's have string shape and size over here but then you'll see we get an error the getter shape isn't defined for the type cookie at the getter size is undefined for the type cookie it's giving us these errors because these shape and size variables do not exist publicly Constructor is similar to a function in a function you know if you put anything over here they are accessible only inside the block you're using it so I can use go ahead and you know print out shape aware and let's run it and it will print out hello to me you see I get hell over here but I cannot use the shape variable anywhere else so if I try to print shape over here I cannot do that because shape is not defined and that's why I had created so that's why I had created public variables over here so we could access shape and size property on it and then I did this dot shape meaning we are going to ask the shape from this thing right here when we instantiate the cookie class and whatever value we get we're just going to store it in the shape variable that we have in this cookie class that's why this dot shape so we are accessing the cookie class and its shape this dot size and these are nullable variables so you can just go ahead and pass null over here and that is fine but if you have string shape you cannot pass in null over here I want to take this opportunity and expand on the concept of Constructors further there are different types of Constructor this type of Constructor is the normal type of Constructor you've already seen we can also have this done and it will work the same thing but if you want to run any function or anything as soon as the cookie class is created you obviously want to do this because you can't do this like you know just having baking over here that's not allowed you know it just says the name baking is already defined it's thinking you want to define a new function or a variable so we cannot do this so that's why it is said to have it in this curly bracket so that it knows yeah you need to run something run it over here also you can specify some value over here let's say cookie so you can have cookie over here but obviously when Hello gets you know returned over here it will occupy the value of the shape So to avoid this what you can do is just create string shape again then you'll have end size again then we are going to create the Constructor or block and over here we are just going to set this dot shape is equal to shape this dot size is equal to size so this is what we have done earlier but as you can see we are getting warning saying try using an initial formal initial link formal this dot size to initialize the field so this is the big hand Syntax for what we just did you know this dot shape is basically this dot shape is equal to shape this dot size is equal to size all right but I want to introduce a new thing over here I can just do print shape not print shape this dot shape and then when I run it we get an error and the error is there basically saying a value of Type n can't be assigned to a variable variable of type double so I need to take double aware so that I can pass it in that's nice now I can run it and here I get cookie hello 20 so what just happened over here well first we have string shape is equal to cookie then we have created two new variables these variables are different from these variables that we have created these are parameterized variables all right so here what I've done is string shape and double size new variables then I've printed this dot shape that means I've tried to print cookie over here then I've set this dot shape equal to shape that means I've reinitialized both of these fields for which it is giving me a warning but I had to do this because I wanted to print this dot shape if I did this dot shape and this dot size I wouldn't get access to cookie right I wanted to print out cookie and that's why I initialized it this way so this is one of the use cases for having a Constructor like this great now I can come back to my original thing as you can see I can reassign the properties I can reassign it outside of the class as well so if I have cookie.shape I can change it over here as well let's say rectangle I can change it over here as well what if I don't want to allow any changes at all so after this was set I want to restrict it from changing ever again why do I want to do that because I just want to keep all the fields of cookie in one place so if I want to change the shape I can do this from a method that I create over here if I want to change the size I can do it over here if I want to change anything else I'll have to do everything from the class itself but I cannot change it outside of the class that makes my class more secure right so to do that we already know how can how we can do that we can have final string like this final double like this and you know I'm just going to say let's remove this because if I have this is equal to cookie it will just question me that this was Final then how come you're changing it so I'm just going to go ahead and have this final string double final double size and then we are good to go now you might again question me if you're having final over here we are having final over here so we have created the variable why isn't giving why this isn't giving us an error like you know null check operator should be used or like I should use optional variables over here that's not the case because we have a Constructor created if we don't have a Constructor created it will definitely throw an error over here now if you try to do cookie dot shape is equal to rectangle we get an error the shape can't be used as a setup because it's fine since it's finite I cannot change its value now you might ask how can I change its value the thing is you cannot change and that's why we had created it like this whatever you pass in over here is going to be treated at this way only also one thing that I forgot to mention earlier you can go ahead and use these variables all right so we can just have your cookie of dollar shape shape so it's just saying your cookie of hello shape and 20 centimeter let me just reframe my English and if I run it obviously nothing happens so what I want to do is as soon as this thing is done I just want beaking to start so we are just telling that yeah if you've given this order the baking has started and there we go we have your cookie which is of the shape hello and size 20 centimeter is baking now obviously just like we had in functions when we have too many variables to be taken it can be quite a problem so to do that a similar or the same thing is used we are just going to wrap all of this with a curly bracket and then it gives us an error basically saying that if these are optional just make them nullable variables but in our case they are not optional so what I'm going to do is require this dot shape required this dot size you can see the consistency over here right just like we had in functions we have in Constructors we have in records as well and now this gives us an error over here the error is basically saying that you need to mention shape like this size like this and the error is result so we can run it and we have your cookie which is of the shape hello and size 20 centimeter is baking nice so these are called as named Constructors the earlier one was known as parameterized Constructor and when we don't have anything you know if we don't have a Constructor at all so let's remove everything we have a default Constructor created and also just to give you some terminology let's get our example back this thing right here even with parameterized Constructors or named Constructor this thing right here is something known as an immutable class why is this an immutable class well we've already talked about mutability and immutability right mutability is when you can change a variable's value immutability is when you can't change a variable's value and here we cannot change the value or properties inside the cookie gloves right we cannot change shape we cannot change size basically this is a const cookie class that means this is a constant we cannot change it once it is given the values or once it is given a set of the values so now that we have a clear understanding of basic terminology let's dive into some stuff that we missed out in classes these are the things that we want to study now private variables Getters Setters static function and static variables let's go over them one by one so the first thing is private variables what are these private variables so there are certain times in your classes when you don't want the variables over here to be visible outside of this class all right so you want them for some stuff inside the class for example for some calculation or something like that then what do we do well for that we have access to private variables let's say we have print cookie dot shape yeah just what we had before so I don't want to be able to access the shape property it is there inside the class but it should not be accessible outside what do I do in that case I can make shape private but there is some limitation in dot you cannot make variables private in class the private variables will be private within a file meaning you won't be able to use cookie.shape or cookie dot height if I made it private outside of the file for example if I have end height which is equal to 0 this is a public variable right to make it private I'm just going to add underscore at the beginning so with this I've made it private unlike other languages dot doesn't have private keyword here it just has underscore aware so that it signifies that it's a private variable however if you have height underscore with let's say this is not a private variable this is just one variable height width which is public but if you just put this at the beginning then only is it private now if I try to do cookie dot underscore height I'll be able to access this why am I able to access this private variable shouldn't be accessible right well that's the problem or that's kind of like a feature in dot private variables are private for a file they're not private for just a class if you use in the same file then cookie dot underscore height will be accessible however if this main function is defined in some other file and class cookies defined in some other file then cookie dot underscore height will not be accessible it will give an error that cookie dot underscore height doesn't exist so I cannot show it to you right now but in flood up we are obviously going to take a look at it so you can trust me on this one and make it clear that private variables are private to a file not to a class so now that we know how to make private variables let's move ahead and understand why we would need private variables in the first place so I need private variables so that I can calculate the size of the cookie right so I'll have end underscore width is equal to 5 let's say my height is 6 or let's say 4 then I have a function here or a method which I'm going to call void calculate size and then I'm just going to set size equal to underscore height into underscore width and that's not allowed right because size is a final variable so what I can do instead is just return an end and then return height underscore height into width that would be fine right because height is an integer when you multiply integer with an integer you will get an integer so calculate size will return 20 from your that's good now this is just for demo purposes you wouldn't want to do this in real life because well calculate size why would you need it if you already have a size over here but this is just for demonstration so these are private variables you can use it inside of methods to perform some calculations and stuff that remains inside your class you don't want it to be accessible outside of your class it's kind of like your Society or building if you are living in a community you want the communities talk to remain inside the community stock you don't want it accessible like outside right that's what private variables do so now that you've understood about private variables and these are public variables let's get into Getters and Setters what are these Getters and Setters ghettos and Setters are basically used to return a value why would I want to return a value well let's go over there first of all let's get syntax out of the way to create a getter we use data type so you can pass in string and a class name if you want to you can have any of that then get and then the name of the variable let's say height as my variable now I will just return it so it's kind of like a function block you can either have this or you can have a fat Arrow function and then you return height all right so this is a get up with get up what I have access to I can just do print cookie dot hi but then why don't we just make this a private variable that's because the heights value might change in this function for example I will have another method let's call it void modify height then I'll have a new height that I get and underscore height is equal to H so I can change the value of the private variables inside but I don't want it to be modifiable outside meaning if I do cookie dot underscore height I'm able to change the value I don't want to be able to change the value from outside I only want the value to be changeable or modifiable from inside and that's why we have private variables over here so if you have cookie dot height is equal to 10 like this it will give us an error saying there isn't a Setter named height in class cookie that means I cannot modify of get a over here and that's why we have created a getter for a private variable meaning it is a read-only value when there's just a getter it is only a read only value so you can just read from it not modify it however if you just remove this private variable and use and also remove this getup because you have this as a public variable you'll be able to change cookie.it equal to 10. and if you try to make it final you won't be able to modify the height over your I hope you are understanding something if not I would recommend you to watch this part of the video because I'm just going to brief through what just happened and if you understood just skip this part basically if you have public variable like end height is equal to 4 then we will be able to change it outside of the class and I don't want it to be changeable or modifiable outside of the class because it might create a lot of confusion in my code and that's why I will put in final year right because I want this to be immutable this solves the problem here but method aware is giving me a problem because this is a final if this is a final I cannot change it over here but I want it to be changeable over here and not modifiable here how can I do that there's no keyword for that so I can just remove this end height I can make this a private variable I put underscore height as equal to H over here but then I won't be able to access cookie dot underscore height outside of the file so for that I've created a getter and the getter is basically saying end get height and then I put out underscore height and then I can just have cookie dot height the way I want it so I cannot modify it but I can print it so it's a read-only value that I get super so this was about Getters and private variables now they're Setter as well which helps you to set a value so I don't have to create a method for this instead what I can do is set set height this is the convention basically if you have a getter with height over here you want to put set height in camel case then have a function like syntax and you'll get in touch aware because you want to set the height and you'll set underscore height equal to H you can't do height as equal to H because this is a getter you cannot change the value of a getter so you'll have to do underscore height is equal to H and then getter will have the modifiable or the updated value of underscore height returned over here now I can just remove this method and I can just have cookie Dot set height I'll pass in let's say 15 over here but now this gives me an error why is there an error because this is not the Syntax for it this is a Syntax for a function and you don't want to have a function over here you want to have a setup so for a Setter you're just going to have cookie dot set height equal to the updated value which is 15 and the error gets resolved I'm going to go ahead and print cookie dot height again and then run it and you see I get 4 and 15. so the set height works I don't have to create a function anymore the getter is used with the setup but this is a Syntax for a set it's kind of similar to a function but you don't have a return data type and you can set the height using assignment so now that we have understood private variables Getters and settles let's get rid of them all of those were kind of linked together but the static variable and static function are not related to each other now I've already told to you that creating an object can be Memory consumption so as you can see over here every time we create an object we have to create something that looks like this in a diagram format you have to initialize all the fields you have to have all the functions with you it can be Memory consuming we have already talked about it but what if I don't want to get the initialization part done all right so I don't want to create an instance of the class at all so I don't want any of this I don't want actually any of this I just want cookie so that I can access some properties on it that will help me save you can say memory in my program so I want to be able to do that so for that we have static function and static variables these static functions and variables are used for certain tasks for example static variable is used when you have a constant let's say so you have a class that contains all the constants so maybe let's get rid of this cookie class and I'm going to create a class called constants and this class serves one purpose give me all the constraints related to my app so for example I would have a string that says greeting whenever the user comes into my app so I say hello how are you so I store it in a separate class why do I store it in a separate class because if I use it and Scatter it throughout my application it might be difficult for me when my client or my employer comes and tells to me that hey I want you to change this greeting that means you'll have to go over certain files go ahead change the text what if all of that information all of that hard-coded stuff is present in just one file that makes it easy for you to organize your code and make the changes easily and it's so easy that even your client can do it or your employer can do it that's why we have created this class all right so I have greeting over here let's say I have another one that says Buy which is you know buy well that's all the constants I have till now and what I'm going to do is first of all let's create instance of the constants which is constants like this then I'm going to print constants dot greeting constants dot by there we go so if I run this it will say hello how are you and bye great that's how it's expected to work but as you can see why do I have to create the instance of a class over here isn't that weird because I don't need access to any of the things that are mentioned where like I don't want the Constructor to be called I don't want anything to be done right what I want to do is directly have constants.greeting constants dot by so that I don't have to create an entire object for this so can I do like constant dot greeting I've already told you that this syntax is not allowed so we cannot do that unless we have something known as static variable with us so what we can do here is call it static string greeting and we get an error over here this says the static greeting can't be accessed through an instance now your wise enough to understand this error this error is basically saying hey you've created an object and now you're trying to get a static variable out of this object but by Static you're telling that this should be accessible to me without creating an object what do you mean so what we can do over here is just have constants dot creating with this I'm able to access this and now if I run it I'll get the same thing but this time constants Constructor will not be called let's print it out over here so we'll have constant parent Constructor called and then run it we have Constructor called because we have created an instance of the class then we have constants.greeting so it's not calling the Constructor again so with static variables The Constructor doesn't get called that means an object is not created and that saves memory and the same thing I want to do for buy as well so I'll have static string by I'll put constants dot by over here let's remove this initialization of class why did I remove the Constructor let's put it back let's run this and we get hello how are you buy the Constructor is not called at all and this is what static does I hope that was clear to you this is what is static now let's get to static functions these are static variables now static function also has a similar type you have static then you define the function as it is yes static and let's say give me some value then you're not having anything over here you're just going to return 10. so now I can't do print constants dot give me some value that's not allowed what I need to do is constants dot give me some value and then run it and there we go we get 10. now you might say this static approach seems very nice shouldn't I use it all the time no why because there are certain cases where you cannot for example when Constructor is called when Constructor is called certain things can be run so that time you want to create an object you cannot live without creating an object or when you have some variable wire so if you have string height which is equal to 10 or sorry end height is equal to 10 and then I try to return height first of all it will give me an error basically saying instance members can't be accessed from a static method that means if I want to be able to access this height value I need to make this static so that I can use it in a static function or you can just create this as a give me some value like this then you can use it so both of these things have to be static or both of them have to be non-static and it makes sense right if you just do this you're basically telling that this height variable is initialized when the Constructor or when the instance of this constants class is created so when you do this int height is equal to 10 is given but then you are mentioning it in static and then saying even if I don't create an object I should be returning this height a value is that possible no because it's a logic fault non-static cannot be used in static now I can just use constants dot creating like this and constants dot give me some value and it will return 10 to me so I hope that was clear now we are just going to get rid of this and of this and we are going to dive into inheritance so we are going to create multiple classes and we are going to learn something about abstract class and then about object oriented programming or as we know it oh cool so let's get started with this so for inheritance first let's get some classes up so I'm going to have a class vehicle and here I'm going to have final or let's have in speed which is equal to 10 then then you're going to have a Boolean value which says is engine working which is equal to false and that's pretty much it and let's just get one function up which just says void accelerate then we just have speed go equal to let's say 10. so we have speed is equal to speed Plus 10. we've already seen this in the if conditions part this basically means speed is equal to speed plus 10. great now I'm just going to create another class which is car and car is a vehicle right now what I want to be able to do is get all of the functions and variables inside of this vehicle why because car is a vehicle it also has a speed it also has a Boolean value which knows like if engine is working it also has an acceleration so what would I do copy paste right and that works but what if in my vehicle I decide to add another variable and that variable is Boolean is light on which is equal to let's say true because it's night time so the light is on so that means I'll again have to copy this I'll again have to paste it and just imagine if there are hundreds of Engineers working in your team and some engineer decides to have vehicles variable added so that's another variable added then there's another variable added and you're just like hey lots of changes happened and then you decide to again go ahead and copy paste it but the problem with copy pasting over here is car also has its unique set right all vehicles have all of this but car also has some properties of its own car let's say has number of Wheels all right all vehicles don't have four wheels but over here or cars have four these are the type of cars you're manufacturing all cars that we have have four but all vehicles that we manufacture does not have number of Wheels as four because it can be a bike right so that means I'll have to create with this variable again if I just go ahead copy this paste it then I'll again have to create a number of Wheels but what if this class is so big that there are so many variables defined inside here if that's the case then it is a problem that means we can't go ahead just copy paste it so we need another solution for this and that's where inheritance comes into play inheritance just says Hey car is a vehicle so whenever you have an is a relation so let me just comment it out because this is the keyword or you can say a keyword in your mind which will help you to know do I want inheritance or not so whenever you have an is a relation it is using inheritance or it should use inheritance I'm not saying always but many a times whenever you have is a relation you want to use an irritance let me give you an example so I'm just going to draw this out let's remove all of the stuff I'm just going to go ahead let's say you have this thing right here and this thing over here is your family all right and in your family the head of the family is let's say your father or mother let's put an Mother where so either your father or your mother or both have or multiple children right so there are going to be three people over here let's put that out so the first one is let's say Naman which is your first sibling then you have another one which is you and a third one which is let's say River so you have Naman inheriting from your mother or father you in editing from your mother or father or Revan inheriting from your mother or father this means your mother or father are parents and these are children right Naman is a child you as a child Revan is a child and that's what we call in inheritance as well in programming this is called as a parent class or base class or super class and these are known as child classes or subclasses we understood why it's called parent class but it's called base class because we are based on these them right that's why the base class and it is also the super class because it is super right and these are sub classes so that is similar to sets you have a superset and you have a subset that's I hope that is clear this is exactly what we have in programming we have inheritance over here car is a vehicle so if we have a new diagram which says you know this thing right over here is vehicle and there can be multiple Vehicles let's say the first vehicle is a car second one is a bike and the third one is a truck now it makes sense right so now we understand what inheritance is but how do we make short inheritances there for that we have a special keyword in Dot which is extends whenever you have extensor wire you extend the functionality of the Class by another class under another class is vehicle so when you have this car is a subclass so you have car over here that is a subclass and vehicle becomes a superclass so car is extending the functionality of a vehicle but nothing changes over here right let me show it to you you can have another one over here let's say end number of Wheels which is equal to four and then you go ahead and print number of wheels and then you try to print it but you cannot print it because print has to be done in a function so let's go ahead and have void print something and then we are just going to print number of Wheels over here sweet now I can run it and I see nothing because we have nothing in the main function so let's go ahead and create a car so we are going to have car car which is equal to car and then we are going to print car dot and now you see the magic over here you have number of Wheels you have is the engine working but we have not defined it anywhere it's because of this extends vehicle if I just remove it and I have car dot you see everything goes away but if you have car extends vehicle then we can have car dot number of Wheels is engine working is light on speed everything that was mentioned over here it has extended the functionality of car by adding properties and methods of vehicle so now we can have is engine working and car number of Wheels great now if I run this I get false which is the value over here correct and number of Wheels which is four great so this was inheritance as simple as it gets Just Two Words via type and we could extend the functionality of an entire class now you can create multiple types of classes over here for example truck so you have truck but the number of Wheels over here is eight or six whatever I'm not very sure but then you try to run it obviously it will just print the same thing because we have not created an instance of truck so let's go ahead and have truck truck which is equal to truck now I'm just going to print truck DOT number of wheels and same thing away a print truck dot is engine working then I'll run it and I get false 4 which is for car then it falls which is for truck and you can keep doing this and that's fine so I hope you got a basic understanding of inheritance with inner returns one more thing is possible now since we have extended the functionality of a car vehicle what we can do over here is have vehicle car equal to car all right so you can do this and it doesn't throw an error over here yeah it throws an error over here but it doesn't throw an error over here that's because car is a subtype of vehicle so you can have it defined like vehicle car is equal to car and this is a valid syntax but it gives an error because the getter number of Wheels isn't defined for the type vehicle since this is of the type vehicle now you can access all the properties on a vehicle but you cannot access the properties of car but what if I want to access the properties of car but I also want vehicle to be here in that case I'm just going to use another keyword over here which is as so you can treat a certain variable as another data type so you can have as car wire let's wrap it in parenthesis so this gets treated as one thing and the error goes away now why is that the case because we are saying treat car as a car class over here if I had treat car as a truck it would not give any error because the vehicle can be a car as well but if you use integer aware it will say number of years is not defined for integer so it needs to be either of the vehicles so that we can get number of wheels and if I use car as a truck DOT number of Wheels what will I get I will get a runtime error because the runtime type of car is car and you're telling it treat car as a truck that doesn't make any sense right that's why you're just going to have Cara's car dot number of Wheels then we'll run it and there we go we get false for eight Falls so I wanted to show you this as keyword you can use this with Dynamic so if you have Dynamics some value which is equal to 10 let's put this Capital then I'm just going to have some value over here and I told that you cannot have properties over here because it is a dynamic but what I can do over here is treat this as an integer and then I get a bunch of properties that I can access so this is a workaround you can do with Dynamic but I wouldn't recommend doing it in this case because you can just put VAR which is variable or final if you don't want it or just integer so that you know you don't have to do all of this work you can just have some value so now that you've understood basic inheritance what I want to tell you is dot doesn't support multiple inheritance that means you cannot extend two things so let's say the car wants to extend another class it cannot extend that so if you have class vehicle 2 and car wants to access that let's say it also has properties like end speed is equal to 2 and all of that stuff I'm just going to copy paste for Simplicity the is engine working as true over here but the light is false and we are accelerating at the speed of let's say 20. now what I want to do is have vehicle EXT car extend vehicle and vehicle too that's not possible and Dot you cannot do car vehicle vehicle 2 like this or you cannot do extends vehicle 2 like this that's not allowed in dot why is that the case because a class and Dot compiler will get confused like what do you mean if you extend two things at the same time vehicle and vehicle two you're telling I want properties of this and properties of this and there is a chance that both of these class expose the same properties then it will just ask you like what property or which classes property should I use should I use this classes property or should I use this class as properties right even if there is one property matching it can cause that confusion and that's why multiple inheritance is not allowed in dot you cannot extend more than one class now that I've mentioned this let's get it out of the way however one thing that is supported is something like this let's put this diagram a little down and let's say the vehicle is extending from something as well all right so if vehicle is extending from something we have something right over here and then we can have some class that vehicle is extending all right we can have a diagram like this but we cannot have car extending vehicle and car extending let's say another thing that we have which we named vehicle two so something like this is allowed but something like this isn't allowed okay you cannot have multiple inheritances like this so you can add inherit from one for one class but you cannot inherit from both of these classes but this thing right here is allowed so that means vehicle and it can extend some class and some class can extend vehicle so that's allowed so I can create class some class over here and then have let's say final Boolean greeting so whenever you have a vehicle it will give you a greeting let's say hello and this should be a string not Boolean great now we can extend some class over here and we can do that with this whenever we create car or truck or whatever let's put final over here so that we have car instance over here so I can have car let's remove some value we have car dot and now you'll see we have greeting over here why do we have greeting because indirectly we are inheriting from some class as well because car is inheriting from vehicle and vehicle is inheriting from some class so car is inheriting from some class so think of it from your family point of view all right if you have your grandfather your father inherits from your grandfather and you inherit from your father so you are inheriting from your grandfather now what if I have some methods over here right and the method is accelerate the same method that was defined above and here I'm having speed plus equals let's say 30. not speed plus equals 10 this some class goes really fast so what do we do in this case well in this case the warning is the member accelerate over eyes on a narrative member but isn't annotated with override but the fix isn't to just remove this function I can just put add the rate override over here if I put either it override I just need to match this function signature with this function signature this is called function signature or function prototype and if that is the case that means speed plus equals 10. now if I just have car dot let's remove everything else it's causing a bit of confusion and we'll have car dot accelerate so we are not able to print it because it's returning a void to us so let's have car dot accelerate and then we are going to print speed so we have accelerator that means we have set speed equal to plus equals to 10 and then since we are using the same object we can have car dot speed with the increased speed so we have 25 over here what just happened so we have car we have a number of vehicle but it extends vehicle so it goes to the vehicle vehicle doesn't have any speed because it is extending some class and some class has a speed of 15. then we are accelerating so speed plus equals to 10 which means 15 plus equals to 10 it doesn't consider this one it considers this one because we have put at the rate override if we don't put it and don't have this function it will not be 25 it will be 45 because it will be plus equals to 30. you can put override and change the function block over here also it doesn't mean that this needs to match with this you can also have int accelerate the name of the function should be same not the return data type or this entire thing only the name of the function needs to be same and then you can return speed and if you do so and try to print car dot accelerate as well it should give you the value now because car dot accelerate has a type of integer now not void so let's run it and we have 25 25 printing over here sweet and if you remove override from here it will give you an error just like we had with void so now if that is clear to you you know we can get rid of this class let's make vehicle the base class only let's remove Accelerate from your okay let's put accelerate but let's put remove override and let's just print car dot number of fields over here so we discuss something known as abstract classes and implementations so let's get into that so what is this implements and Abstract classes first let's understand implements and then it's easy to understand abstract classes so there's a thing called as implements and first we need to understand why we need to use it that will make it much more clearer so we need to use implements when we have something like this as you can see car is extending vehicle truck is extending vehicle but both of them have number of weeps that means it is essentially a vehicle property right if we have bike as well bike is going to have vehicle as well but we have independently defined in all of those classes now if I have bike let's say class Pi that extends vehicle here I can I have all access to all of the things you know I have access to number of Wheels I have access to sorry I have access to is engine working I have access to is light on but it doesn't anywhere tell me that n number of Wheels should be defined because that's what all vehicles need to have so you need to implement this that's the core concept whatever you have you need to implement that variable so to do that we can have implements so instead of this we can have end number of Wheels which is equal to let's say 10 over here and then I'm having n number of years is equal to 4 and number of fields is equal to 8 but still nothing over here tells us that we need to implement it so for that we will change this from extends to implements right and now since we have implements we get an error let's remove it and what is the error saying machine concrete implementations of getter vehicle dot is engine working is light on number of Wheels is engine working and two more what I what does this error message even mean well you don't understand this part right but you do understand this part because you've already learned about Getters and Setters it's basically saying I need to Define is engine working getter is light on number of Wheels is engine working and all of that now you might ask why do I need to have Getters and Setters does that make sense I don't have anything related to Getters or shadows and my code and that's true what you need to do is Implement all of these variables what I mean by Implement is you need to put add the rate override forcing every single one of them that means you need to have Boolean is engine working which is equal to true so that means our error message is modified over here I'll do the same thing for rest of the things I'll have at the rate override then I'll have Boolean is light on which is equal to true then I'll have add the rate override in number of wheels and that is equal to 4. and the error goes away now I have a certain set of warnings over here showing up for truck so I'm going to do the same thing I'm going to implement it I'm going to copy these two things because tuck is kind of having the same thing over here but at the rate override in number of Wheels that's equal to 6. so now we have implemented number of Wheels aware so whenever we implement we need to implement all of the variables all of the functions that are defined in variable for example if I avoid Accel rate here and accelerate is basically saying that I just want to print axial rating that means I will have to override accelerate function as well so I'll have to do add the rate override void accelerate then I'll have to create my own function block which says print accelerating the car I want to make this change now I can use this other rate override over here as well and we'll have accelerate rating the truck and the same thing for bike but I'm just going to remove it two classes are enough to understand this so basically whenever you implement you get a error message saying that you need to implement all of the properties all of the methods that are defined here and they can be the same as this one or they cannot be what if I want to keep it the same as this one well I just go ahead and print accelerating what if another engineer comes in and then just changes you know and says accelerating why equal ha ha and then you lose track of it and then you forget and then your code is functioning abnormally You're Expecting accelerating the vehicle haha which is written over here but you're getting accelerating will I use super aware now you might ask what is this super well it's one thing that was present in extends so whenever you add extends something and you use super it would refer to the parent class the class that you were extending if I do something like super dot it gives me accelerate is engine working is light on number of Wheels so super refers to the instance of the vehicle class that we have and it gives us access to the nice all of these things that are present so will I do super dot accelerate like this when I try to implement it as well not really because super dot accelerate doesn't exist in implements it only is present in extends so if there's extents you can use super Dot and do something but in implements you cannot do that so if your class extends vehicle and then you say super dot accelerate you'll be able to do that or if you want super dot is engine working you'll be able to get the value of it and if you want you'll also be able to change it let's say true you label be able to change it as well so you're able to modify the content of the parent class in the subclass so I hope that was clear to you now let's get back to Super dot accelerate and Implement can I do the same thing in implements not really super dot this thing is not allowed it says the method accelerate is always abstract in the super type so it basically gets this part this thing right here not all of this so since this is abstract we only get access to this much there's no code block so why would you run this function so you cannot do this when you are implementing you always want everything on your own right if you're implementing you're basically telling hey give me all the properties that I want to implement I don't want to create anything on my own just give me a set of instructions that's why we don't have access to Super because we cannot call this function over here so that's the difference I wanted to show you now you can use extends and implements together so you can have extends some class implements some class so does that mean I can extend vehicle and Implement vehicle not really you cannot extend and implement the same class you'll have to use different classes for them so let's bring our other class back or the super class of vehicle but in this case it's not going to be super class and we are going to have all of these defined over here not accelerate accelerate is going to be present over here okay so all the properties are present in other class and vehicle just has the function void accelerate so you can Implement vehicle but you will extend other class that means I have access to all of these properties I don't need to override them but I have to implement whatever vehicle has to give me which is accelerate so if I just have this it will give me an error saying but he could not accelerate needs and this is what concrete implementation means concrete implementation is something that is not abstract and we are going to take a look at abstract in just a minute so now if I extend other class and Implement vehicle I get access to the accelerate function and that means I can print is engine working over here I can print other things as well like is light on and number of wheels and then I have car dot number of Wheels it will work the same way because number of Wheels over here is 10 but then I will have car dot accelerate which will print out all of these things right so you have 10 that means it is printing the number of wheels of a car because that's 10 then Falls to 10 again which is this part right here but now I want number of Wheels to be present and vehicle I can do that and that means I have access to at the rate override for this variable which is end number of vehicles and I can set it to 4. and now when I run it let's see why I cannot run it oh it's number of Wheels not number of vehicles and here you see we get four Falls to four perfect so now that you have understood the implements and how it works let's get into abstract class what is an abstract class after class is quite similar to the class that we see we defined it using abstract which is a keyword class which is the keyword and then you know you name the class so let's call this class vehicle let's remove the extending of other class from here and then we are going to have a class block let's remove all of these things from here we can have car like this because we are going to create a bunch of properties now what is abstract class you're not defining anything so if you have a function you're not going to define a block for it although you can Define it but you can when you implement it you have to redefine it so let's see an example what if I have void or let's say I avoid accelerate so I can have that but as you can see it gives me an error if I remove this it doesn't give me an error over here but when I add this it gives me an error because I need to override accelerate now earlier we couldn't create functions like this right we had to put in stuff like this but in Absa class this is allowed you don't have to put in a function block and all of that stuff you can just put a semicolon and then override let's put over here then we avoid accelerate and then we are going to print accelerating great now temporarily I can just comment this out run it and truck gives an error so we can comment track out we can look into that later then run it again accelerating sweet so abstract class forces a contract over here it says whatever methods functions I Define over here and if you implement it or extend it all right extending is allowed you can extend an abstract class and abstract class extending also means that it gives an error over here earlier when you used normal class you and you extended a normal class it didn't give you an error if you didn't override a function but here if you extend an abstract class it will give you an error because if you extend or Implement an abstract class you have to put at the rate override and Define the function over here it's not there just so that you can call accelerate in your function or in your class so that is the difference between a normal class and an abstract class I hope you're getting the hang of it now we can have some variables defined as well let's get end number of Wheels aware which is equal to 10 and now you see we don't get the override option over here however if I implement it it gives an error if I extend it I can use number of Wheels over here if you see number of Wheels I can use it so I can extend this property so I get access to number of vehicles however if I implement it I have to implement an override number of vehicles that means I have to rewrite this variable with a new value or the same value as before so that is an abstract class now you might ask if abstract classes can be implemented and normal classes could be implemented does that mean normal classes are abstract classes and you're kind of right apps normal classes are abstract classes they are implicitly abstract abstract classes are there just so that it can force some kind of contract on you the contract is saying that you need to Define all of these functions but if you just create a normal class aware that means you have a need to have something like this you can create or construct or instantiate a normal class but that's just not allowed with abstract classes okay so I hope you got the difference between classes and Abstract classes so just to revise classes are implicitly abstract but abstract classes cannot be constructed and Abstract classes can just have a semicolon right after this you don't have to necessarily Define them like we have to do in normal classes so now that we've learned about abstract classes implements and all of that stuff let's get done with it and we are basically done with inheritance so let's remove it and jump into object oriented programming what is this object oriented programming or oop so object oriented programming is what we are basically doing till now object oriented programming is a paradigm based on the concept of objects and we've continuously been working on with objects right if we had something like date time dot now that we have already seen in the previous lectures like we had date which is date time not now now you'll be able to understand the syntax a little bit more right date time is a class dot now is a method defined inside the state time and probably this dot now is a static function right so you're able to break it down and we've continuously been working with classes so when we created classes like cookie cake vehicle car we've continuously been working with classes and creating object because this thing right here is an object it is a date time object because date time is a class now I hope that makes sense to you because we've studied a lot about classes this date time thing is the class that is built into Dart so that we can use it so the dot team has created this date time class so that we don't have any problems getting the current date and time otherwise we would have to implement this on our own and it's not not possible it's not impossible you can do it but why to waste time on all of these things when that team can do that for us so this was object oriented programming on the it was based on the concept of object but there are certain types of oop Concepts all right so the first one is polymorphism the second type is abstraction the third type is inheritance and the fourth type is encapsulation so these are the main four types of object oriented like Concepts in object oriented programming let's go through one by one what is polyphomorphism polymorphism is the ability of an object to take on many forms what do I mean by this when we had a class vehicle and let's change the example a little bit let's get animal over here all right we've been working too much with vehicles so let's avoid sound aware so the animal can make a sound right so we are just going to print here animal making sound now you will have a class CAD that extends animal and yeah we are just going to override this void sound all right we're not going to you know just have this much we're going to override it in reality because we want to have cat making a sound I told you in extends you can have override and that's it now I'm just going to create a new class that will be dog and here we will write dog making sound or we can just say dog barking now in the main function I can just have animal cat is equal to cat then I will just put cat dot sound aware then I can have cat is equal to dog then I will have cat dot sound again now you might say hey this is not possible how can you do it I can do it animal cat is equal to cat so cat is a sub type of animal so I can make a sound because animal has sound defined in it then cat is equal to dog I can reassign this I can reassign this because dog is also a type of animal all right I cannot do something like class is equal to 5 because that is an integer integer cannot be animal but dog can be animal because dog is extending from animal dog is a sub type of animal again to visualize I would recommend you to think about your family tree let's say this is your parent parent let's say parent U is equal to U then you have U dot sound then you have U equal to Revan now so you are Revan now and driven can also have the sound property because your parent can make a sound if your parent can make a sound you can make a sound so I hope that cleared things up so this thing right here is polymorphism we've already seen this why are you showing this again that's what you might say and I agree I'm showing it again so that you know polymorphism is just a fancy word given to this thing right away up polymorphism is the ability of an object to take on many forms this is achieved through inheritance and Method overriding this thing right here is method overriding it allows objects of different classes to be treated as objects of a common superclass what did I just say it allows objects so we have cat of different classes so let's say we have cat away or cat cat is equal to cat then I have dog dog which is equal to dog so let's say we have this and then we have dog dot sound same thing and then if I run it all right so it allows objects of different classes cat and dog to be treated as objects of a common superclass and the common superclass is animal right it they both are treated as objects of animal so that is polymorphism achieved through inheritance and Method overriding the next thing that we have is abstraction abstraction is the process of hiding the internal details and complexity of an object and only exposing the essential features and functionalities what do I mean by this I told a long definition what does that mean it basically means let's say we have an abstract class and that after class is animal and animal says Hey make some sound so you avoid sound let's get rid of this animal now and then you have cat extending animal override so all of this is fine you can also have Implement here that's fine and abstraction is basically just us doing animal just like we did before in polymorphism what I did was what animal cat is equal to cat that's exactly what abstraction is animal and ml is equal to let's say cat and then I can have print or let's not print animal Dot sound and then you can create another object which is animal which is equal to dog and then you can have animal two dot sound and that will give you card making sound dog making sound card making sound dog making sound so yeah we are just putting out relevant information we are hiding all the complexity inside by exposing only the essential features for example we have got rid of this abstract class from here for example what we have done is remove the animal class from here now we only have abstract class abstract classes allow us to put animal aware making our NM variable more you can say diverse because now animal can be set to dog animal can be said to cat but animal cannot be said to animal because abstract classes cannot be instantiated so that's what abstraction is abstraction hides the internal details and exposes only the essential features and functionalities which is this part right here it can be achieved through abstract classes or interfaces so now that we've understood polymorphism and abstraction let's get to inheritance and we've already seen what DNA returns is inheritance is basically you know just having a vehicle extending it and then using the properties in the super class we've already seen that so I'm not going to go into inheritance and the last oop concept is encapsulation encapsulation is the bundling of data and methods together as a single unit and the data is hidden from the outside world it provides data protection and supports the principle of data hiding what does that mean well it's basically about the public private thing that I talked about so if I just remove all of this and I have class person and your the name property is let's say private and then I have gettels and Setters about them that thing is known as encapsulation by encapsulation what I've done is bundle the data and methods so the data is name and the method is let's say get name set name or get age whatever so we have bundled all of that data together as a single unit and that data is hidden from the outside world so this underscore name is hidden from the outside world this provides data protection obviously because our data is protected within one class and the principle of data hiding which is as the name suggests it hides the data also these classes can be made private not just these variables you can have class underscore person which will make this class private and even function so if you have get name like this this is also a private function all right so putting underscore before any variable name you know makes it private so now that we have understood the oop concept there was nothing too difficult about it these are just terminologies if you want to remember polymorphism means poly you know poly means many morphism is like many forms so many forms and this usually includes method overriding abstraction is basically using abstract classes abstract or interfaces so that you have a diverse range and this allows you to hide complexity of an object third one is inheritance where if you extend a certain class you get the properties of a class and you establish an issue or parent-child relationship between the classes and the last one is encapsulation which is basically using private public and it encapsulates everything so it's like caps it's like a capsule you know it is bundling all of the things together in one capsule so it's encapsulation so we are done with classes but there's one concept I would like to cover with classes which is mixin now what is a mixing mixin as the name suggests it mixes in you know if you use this mix in with a class it mixes in the properties of the class that you're mixing it with in the class so let's just you know get rid of these words and see a practical example to create a mix in you just type the word mixin just like a class you add class you have mixin and then you have a name so let's say jump so jump is a mix in and then you have a block created after that let's say this has a property of jumping and this jump is 10 centimeters long let's say so you can Define it like this similar to a class and let's say I have a class called animal and my animals can jump so I can just use the width keyword which allows me to mix in stuff so whenever I use width I can use this mix in so it's expecting a mixing wire and now if I do this and have print I get access to a property called jumping also I'll have to create a function now I can just create final animal is equal to animal and then I'm just going to print animal dot function like this now we'll run it and it's giving us an error because we have printed it let's have this so we have animal dot FN and then run it so we have 10 written over here so it's basically mixed in this jump with this class now you might say hey this is very similar to the extends keyword that we had when we had extends we could extend a class so let's try to do that if I do extends jump it gives an error because the extents can only be used for classes not with mixin so I have to use width aware so when I use width I can have jump over here so I can print jumping so what if I just create this as a class and then extend and have jump is that fine yeah it's the same exact thing so you might ask why do I want to use mixin that's because mixin is not establishing a parent-child relationship it's not creating this thing that we saw where it's not creating all of this all of this is for inheritance and extending with mixin you're basically telling hey I have a bunch of code over here I want this bunch of code to be reusable inside of this class so please help me out with that I'm not setting any parent child relationship over here hey animal is a super class of jump no that's not the case I'm just saying animal can use this jump property over here so whatever properties jump class jump mix in has I can use it inside over here that by no means means you know animal is a parent or a subclass of jump so if you have class cat that extends you know animal does that mean I can create a function let's call this Fung and have print jumping over here does that make sense absolutely it does why wouldn't it because animal has a property with jump and with jump has allowed it to have the jumping property and since cat is extending from animal that means it will get access to the jumping property as well what if I use class cat with animal that means I'm using with with a class right that's not allowed this was allowed prior to dot 3.0.0 where dot 3.0.0 classes cannot be used as mixin to use classes as mixin what you have to do is convert this to a mixing class so with the mixing class you can have that but mix and class cannot be used with width because mixing class is class plus mixin right so now you can use with animal over here but you don't have access to jumping but yeah now you can use width Pi 2.3.0.0 you could do that but now you have to do mix and class so let's put this over here and we have our extensor layer great now you might ask if we are not setting any parent child relationship does that mean I can have multiple mix sense you're right we can have multiple Mexicans away if my animal can you know scream we can also have Boolean screaming property over here and we can just have with jump comma screen since we are not having scream and jump as the parent class of animal that means we have the print is screaming property over here and then when I run it you get 10 and false and you can have as many mixers as you want so mixin is great for code reuse but it doesn't create any class hierarchy there's just one more thing that I want to show you which is on as you can see over here makes sense cream on object when we don't specify anything like on it is default by mixin's cream on object on object this object is a data type all right so if you have object over here you can use it but it will give you an error over here because well it's an object it's not an animal what exactly is this object object is the base class for all dot objects as you can see it over here the base class for all dot objects except null that means object is a superclass of string integer Boolean everything but not null so if you try to give this a value of null it won't accept it but if you give it a value of 5 it will accept it if you give it a value of 105 that is a string it will accept that so object is this thing right here the base class and then we have stuff like you know integer double Boolean all of that so I didn't explain object to you before because I wanted to explain with the help of you know inheritance so that everything comes together for you so anyways coming back to our example we have class object over here for a screen so this makes sense cream on object is basically saying you can use it anywhere you want you can mix in this anywhere you would like so with Scream basically I'm having the ability to restrict this cream's usage anywhere I want so I can just put on and mention whatever I want and it will restrict the access over there now let's dive into the new class modifiers that we've got so let's consider I have an abstract class called animal and class is human and dog are implementing the animal class and cat is extending animal now I'll create an instance of animal class and set it to cat and then I'm going to have a switch of animal and the case will be dog and then when I try to run it I get nothing printed out in the console and that's expected because I have not handled the case of cat so the problem I'm trying to solve is that whenever I put animal I want all the subtypes of the animal class to be included here and by subtypes I mean direct subtypes so I should be getting a compile time error or account warning saying you've not handled all the cases of animal class so to do that dot 3 introduced a new modifier called seal so with sealed class now we get an error the error says that the type animal is not exhaustively matched by the switch cases since it doesn't match human so we need to implement the cases of cat and human so I'm just going to add Case cat and case human and then our error goes away since we've handled all the subtypes of animal class we don't get an error and when I try to run it I get the print as cat this is the difference between abstract and sealed class there's obviously more but sealed class is quite similar to an abstract class for example so when you try to instantiate the animal class it says animal classes cannot be instantiated so the sealed class is implicitly abstract another question that might be in your mind is how does dot do this dot does this because the sealed classes prevent other classes from implementing or extending it outside of the same library for example if I have Library a dot dot here and if I have all of these defined in Library b dot dot that's just not allowed all of them need to be in library a dot dot for this to work since you're in the same Library Dart is able to know of the subtypes of animal class and by subtypes I mean direct subtypes that means if I try to have a class cat1 which implements cat I won't be getting this in the switch case because this is an indirect subtype because cat1 implements cat and Cat extends animal it's an indirect subtype but if I directly implement it from the animal class I get an error over here so that's about sealed classes other than sealed Class A bunch of other modifiers were introduced in dot 3. the first one is final modifier this final is very similar to the sealed class it cannot be implemented or extended outside of the same library but inside the same Library it can be extended or implemented a basic difference between them is that animal class can not be constructed but animal one class can be constructed Cecile class is very similar to the abstract class because it cannot be constructed like this but final class can be and another one is that if we have final anim here like this and then if we try to have switch animal like this it doesn't throw any error to us so with the final class we don't get the cool features the sealed class gives us but final class does prevent classes outside of the library from being implemented or extended the third one is base class so base classes cannot be implemented but it can be extended so that means if you try to create class human extending animal 2 it will work but if you try to create class human implementing animal 2 that won't work and whatever class extends animal to class needs to be base final or sealed that means if we have a class called human extending animal 2 you see we will get an error here saying it must be base final or sealed so this should be base final or seal and the same goes for a final class so if you are in the same library and then if we try to extend animal one we get the same error over here this also needs to be base final or sealed this is because the final class encompasses the effects of the base class the cool thing with base classes is that whenever we extend this and call this human class The Constructor of the base class gets called so whenever an instance of the human class will be created obviously that won't be created with sealed it can be created with final so whenever human class is instantiated the animal 2 classes Constructor will be called fourth one is kind of a reverse of Base Class which is interface class base classes could only be extended interface classes can only be implemented so even if you are outside of the library you can implement the interface class but cannot extend it and this interface can also be constructed for example if you have animal 3 like this we can do that so this is not a true interface from other programming languages so to make this a true proper interface what you'll have to do is combine it with abstract so you have abstract interface class which you can use and this is a true proper interface so if you have animal 4 like this now it cannot be constructed it has a properties of both abstract and interface so now this is a proper interface with us in Dot and the last modifier that we have is a mixing class and as the name suggests it's a mixing plus a class so it will be used as a class as well as as a mixing so you can use the width keyword now you might say why do we need a mixing class here if if we have a normal class animal 5 which can be used with a width keyword for example if you have class human we can use this with animal 5 class right but that's not the case in Dot 3 and Dot 2 you could do this but in Dot 3 with keyword for a normal class is removed you'll have to use mix in class for it to be used with the with keyword so that's one breaking change in dot three nothing else is quite breaking these are all additive features so a normal class cannot be mixed in now but a mixing class can be now let's get into lists so what is a list list is an ordered collection of objects meaning it is a collection of objects wherein the order matters so let's take an example you know what if I want to store the marks of the user all right and this user is ravan and I want to store his marks all right so how can I do that well I'll have to store the math Mark English Mark or computer science marks and this is what he's got now I want to store all of them together now I can't create separate variables for it because I just want to store all of the marks together in just one place so that's why list exists list will help us to store all of the marks together in a bundle and this bundle is denoted by a square bracket all right so that is one thing so how do we create list so to create a list we just have list this list thing is a class you can see it is an abstract class all right and it implements some other thing so now we are able to understand whatever documentation says to us abstract class is a list that means if we try to create list as equal to list like this it's not allowed because it's an abstract class and Abstract classes cannot be created so what is the way well first of all we'll have to give a variable name like this so we have list list and then directly we can assign the value so we can just have 10 20 30 written over here and then when we print this list and run it we should be seeing 10 20 30. great so this is how you create a list you're able to store the values together now what if I want to retrieve one value from this list to do that we can just use this operator right here you can see that the square brackets and pass in 0 1 or 2. so remember the example where we had string and then let's say we had greeting which was equal to hello and what I did over there was greeting like this 0 this gave me access to H right why did that happen because it grabbed the first element over here and in programming everything starts from 0 except length so it gave me H over and similar to this if I do list at 0 like this it will give me 10. if I do let's start 1 I will get 20 if I do list at 2 it will give me 30. so if I just try to print it first it should give me H then it should give me 30 and that's exactly what I get second remove the string example from here and we have a list with us now great but what if I have three over here because the length of this list is you know three elements and I'm accessing the fourth element over here and if I run it it gives me a runtime error saying range error index out of range index should be less than 3. and obviously index should be less than three because there are three elements you cannot access the fourth element by doing list at three so you need to do 2 over here and then when you run it you'll get it so this was about creating a list and accessing a list but if you just hover over this list it will tell you list Dynamic list and I've told you before if we have Dynamic we should probably try to avoid it so what this Dynamic has allowed us to do over here is not just create a list of all integers I can also add strings over here so I can add hello I can add a Boolean value Falls and it wouldn't complain why because this is a list of dynamic and this is enclosed in some angle brackets that we are going to talk about in just a minute but the point is if I just have listed three over here I'll be able to access a string but this list is of marks right if I have marks how can I access a string that should not be allowed I should not be able to put anything other than integer how can I avoid that to avoid that here in your list you need to Define list like this you need to put in angle brackets and then pass an integer over here if you do this it will throw an error saying yeah you cannot put string and Boolean values over here this should strictly contain integer values that means I cannot have Boolean values as well I mean double values as well right and if I create list of double I can have this because this is considered as a double value so if I just have listed 0 and then I run it it gives me 10 because double includes integer in itself but double also allows you to add decimal points now you will ask what is this thing right here this angular brackets that we have are called generics these generics can be used anywhere for example when I try to create a class let's say of student all right and this student has final list not list Final string name and Final End marks and I'm just going to go ahead and create a Constructor for this and this is going to be a positional Constructor so we have this dot marks and this dot name and there we go all right now I can use generics in this class as well so if I just go ahead and put the student should be of the type string I can have that my class is of student of the type you know string now you might ask what is the meaning of this well you wouldn't Find meaning over here but what if I remove marks away from here I just have name and here I'm saying this name can be anything you want all right it can be an integer it can be a Boolean it can be a string it can be anything you like so for that I'm just going to put T over here that's a convention not necessary so you can even put a but by convention people usually put T and then you can use this T value over here so you have final T name now let me just comment this list thing out to understand generics I can just have final student is equal to student all right but now it will ask me to do something over here first of all it will ask me to put a name so I can just go ahead and put Revan over here and it will understand that P over here the student you see over here it's student with the generic type string because I passed in a string if I passed in 20 it will be student of integer and the name should be interior now you might ask what's the benefit of this the benefit of this is if we have student dot name it gives us the great type of integer name even if I put string over here it will give me string if I put an integer it will give me end if I had to do this the other way I would have to use Dynamic aware and if I use Dynamic we all know we don't get the nice type checking now I get the nice type checking and that gives me the right type also I can Define it like this surveyor just like we had for list double I can just have student with the angular brackets and then I can have string let's say and then it will give me an error over here saying that you've defined that this student is of the type string that means your final T name should also be string so please convert this to a string and I've converted it to a string so that's exactly what's happening over a list is also a class all right and it's an abstract class and if we go into the implementation of this list it will tell you that even it had T over here and if you didn't pass T it will just consider it as Dynamic so we passed in a double saying yeah this is a double don't give me Dynamic if you give me Dynamic I have some problems with it because it will allow me to pass in anything string Boolean I just want integer or double values to be present inside this list so this generics are very useful you can even use a 10 function so we avoid set name and then you can pass in t like this over here and then create a function but people don't generally use it away they use it inside of these parameters so that you have t name right over here and then you can have you know your print like new name and then you just print out the new name away you're not actually setting you're just printing the new name so I hope that made sense to you this is what the angular brackets are for so let's remove the student class from here let's remove it from here and let's uncomment these things out so now the question is why do they give us this angular brackets why don't they give us like list double something like this that sounds much better right now I agree with you this might seem a lot more intuitive but here's the problem what if I want to create a list of a class for example I had a list of student class right what if I want to create a list of student class I'll just remove this from here I'm just having a strict type that this needs to be a string so what if I want to create a list of student class if I just have list Double Or List string like this I won't be able to access string list of student because student is a class that I created and list of double would be a class that dots dot creates if I just have that I wouldn't be able to create a list of student so to do that we have generic surveyor and generics allow me to pass whatever type I want it can be a student which is the class that I created integer double even object and we know what objects are objects are super cloud or base classes of all the data types so that means again I can have string values over here I can have Boolean values over here but it's different from dynamic dynamic says hey you can pass in any values and object says you can only pass in values that are non-nullable because object is a root of the non-nullable dart hierarchy okay cool so let's pass in a list of student class how would that look well we are just going to have something like this then we are going to have student like this so we created a student class over here then we need to pass in the name let's say first Student's name is ravan and then we'll go ahead the second Student's name is Naman the third Student's name is let's say Rakesh and the fourth student's name is soon all right so we have four students over here I can access all of these students so let me just rename this variable I have students and make sure you have student surveyor or student list like this not just student because that would mean you have only one student and can cause a lot of confusion again descriptive variables right so we have students at zero now so that would give me an instance of student class which is rivan so it gives me instance of student which is what I want now to access the name I can just have students at 0 Dot and it gives me name why because students at 0 gives me an instance of student class which means I can access the name property on it this is just like you know final student which is equal to students at zero let's remove this and then I can have student dot name because student is this student right here so you can literally create list of anything that you want any type that you want that's why these generics are present so that you can create a customizable list of whatever you want but of course if you pass in something like this it will be a list of dynamic and you'll have all the dynamic elements on it that wouldn't allow you to you know just have a list of students you can also have strings over here and if you have strings you know we get a problem we get a problem because if we try to access students at 0 1 2 3 4 so if I have students at 4 it shouldn't give me student.name because string doesn't have a property of name so yeah you can go ahead and use if condition over here to check if student is so this is lets us know what the type is so if student is a type of student which is a class so you're just checking if student variable that we have over here is student or we can just do student Dot runtime type is equally equal to student that also works so either of them if you just use if student it will automatically think that yeah this is a Boolean condition because is allows a Boolean condition so if student a student then I want to print student.name otherwise I can just go ahead and print student because that's not really a student it might be something else like a string like an integer value or it can be a false all right a Boolean value so I'm just going to go ahead and have five over here run it and we have four wire perfectly written no error but if we have students at 2 it should give me Rakesh and it does sweet so we can use if conditions else conditions and you know create a bunch of things that's what the programming language is for you can create customizable things now there is a bunch of more things that list can you know give us list doesn't just allow to you know first add a bunch of elements and then not do anything about it you can just create it first then you can read it but there is a bunch of more operations you can do like add it add an element remove an element insert an element update an element and you know filter some elements and also Loop through some elements so let's go over them one by one what if I have a list of students now all right so we are just going to continue on this example so I have a list of students and here what I'm trying to do is add another student so first we had a few students then another student got involved in a class so I just want to update this list so I'll have students now how do I update it should I do students at 0 1 2 3 so I'll do students are 3 or 4 because students at one zero one two three if I do three that means it will replace the value if I do students at 4 that means I can add a value so if I do students at 4 equal to let's say new kid and then save it obviously it's going to throw an error it throws an error because I'm giving it a string it has a nice type checking saying that this is a list of student give me a student class or instance of a student class so you can just go ahead and create an instance of the student class and then print students again what do you think will happen let's see so you see we get students so we are instance of student class over here and we have one two three four four students exactly like we had over here but then I try to do students at 4 is equal to student new kid which says index out of range index should be less than four it's basically saying this because students at 4 doesn't exist and it thinks that you're trying to reassign it it doesn't know that you are trying to add a new student it thinks you're trying to reassign so you can do students at 3 which is equal to new code so that will replace the student sonal class and add student new class now obviously you can't see this because it's continuously giving you instance of student now to avoid this instance of student and just get the proper value of student what we can do is come to the student class and here create an override method which will be string to string and then you're going to create a function basically which Says student with something like this all right and now if you run it we get student Advanced student Naman student Rakesh student and here you get students so new care so we learn something new over here we already know that we have override string to string student name but how could we use override we are not extending anything right how can you use override directly well that's because it's an inbuild dot thing whenever you have created a class dot has created a tostring method on it right so if I just remove this and you know just have students at 3 dot something we get name which is the name property on it then we get hash code hash code is something related to equality we are not going to discuss about that right now then there's the runtime type then there's two string this two string this runtime this hash code this no such method all of these things are not created by us they are created by Dart itself when we create a new class so what I'm doing is overriding the existing method that the art has created for us so that it can help me in my program so I've gone ahead and created this override property and that's because data has already created the student class for us I'm overriding the existing two string property that dot has for us so that I can display the name so that I see the new updated list over here and it's helping me in my program right you can go ahead and do the same thing for let's say one of the other properties mentioned over here but now I still haven't given you the answer I can update the value all right because I replace sonal with new CAD but how can I add it because sonal is still in my class I also want new kid to be there so for that we have a bunch of properties on list as well so we have students dot so if you just do this much you get properties just like we had on string there is on list as well just like we had on Integer we have on list as well so you can just have students dot add all any asmap cast clear contains we're going to go over some of them let's start with ADD add allows you to add a student and this is also type safe all right so when you do students.add it tells you give me a student value you cannot give me a string you cannot give me an integer give me a student so now you can see how generics were used inside of a list right over here abstract class list and you see here they've used e generally people use T but they've used e maybe because T was already used or for some reason but as you can see they used a generic wire which implements this and in their implementation they've definitely gone ahead and said that whatever value you mention over here should be the value for all of our methods like add or some other properties like students.remove reduce all of that stuff so let's go ahead with ADD and then I'm just going to add student new kid and then I'm going to print students again now I'll run it and we see we get Naman Naman Rakesh sonal but yeah we get a new student kid what has this done we had a list over here it went ahead and added this new kid to the start of the list or to the end of the list sorry now what if I want to add this at the beginning of the list or let's say at the in the middle of the list how can I do that so for that we have another property or another method called insert add just ads over here insert takes two positional arguments over here one is the index which is intendex and then a student here this int index stands for at what position do you want to insert the student's class I want to insert at the beginning right so should I put one no everything starts from 0 except length so we are just going to have zero where which means it will add it over here and push rest of the things after it so we have like this to run it and we should see new kid as the first student and there we go we get the first student now if I want to add after Naman what will I do I'll just do two run it and then it will be Revan number new kid Rakesh sonal perfect now what if I want to remove a student so I've added new kid but then let's say Revan must behaves so we want to remove a student class so to do that we'll just have students dot remove we have already seen this method and what do we want to remove we want to remove student right so I can just run it also I need to print students again so that I can see the updated value run it but as you can see it wasn't able to remove the student driven why is that the case now that's the case because this student Revan class and this student driven class is a bit different why because this is creating one instance of the class and this is creating another instance of the class so they both are not the same thing these two things are not same these two things are different because they are different instances this is one instance and this is another instance so to fix the server what I can do is create final rewind student which is equal to studentrone like this so I'm saving the instance of the student Revan and putting it over here which I can do right now I can just take this Revan student as well and remove it if I do this and run it rewind gets removed so now we have student Naman student new cat student rake student sonal and ravan is removed so this works because we are trying to access the same instance of the student class but earlier we were creating two separate instances of student class because of which it couldn't identify that yeah these two things are the same things now what if I want to filter some list I want to filter this list based on the marks so what I'm going to do is have final into markzware then we are going to have this dot integer taken over here and then we get an error for all our student classes so we can pass 10 20 30 and 40. and when we are updating let's not update it let's just have print students like this and this is not this dot end this dot mark sorry so yeah we've created it this way now what I want to do is I want to fetch all the students with grades above let's say 20 so it can be 20 and more so I want to be able to filter Naman Rakesh sonal out and remove Revan out of here how can I do that so for that obviously I can go ahead and create some kind of for Loop and run it so yeah you're partially correct we can do this what we can do is you know this is my plan first I am going to create a new list of students which will be empty all right why will it be empty because here in this new list of students which will be empty I'm going to create or add all the students who have the grades above 10 or 20 sorry then you know I'm just going to run a for Loop and we iterate over all the elements inside of the student's class and after that I store I check if the grade of one student that we are looping through is greater than 30 if the condition is true so if it is true then I will add the student to my new list and finally I can just print that list outside of the for Loop right this is the normal approach we will take so let's go ahead and create a new list of students but I'll be creating a new list of students because if we try to save students in a new in in the same list we won't be able to Loop through them right it will create some sort of confusion that's why we have filtered student surveyor which is equal to empty list then I will run a for Loop which is 4 and I is equal to 0 I is less than students dot link we did the same thing for a string as well I just want to run from 0 because my list starts from 0 and I want to run till list dot link and this should be less than students.link why because see the student length over here is 4 so I'm running from I is equal to 0 so that means 0 till 4 that means I'll run till 0 1 2 and 3 it will not include four if I try to include 4 it will give me an index range error why because student at 4 doesn't exist student at 3 exists now I can just have I plus plus then I can just have filtered students dot let's say add and what do I want to add well I just want to add students at I right I don't want to put in any specific number I just don't want to add stored inside two that would mean I continuously add Rakesh in the filtered students no here I want to add students at I whatever student we are looping through but as of now we are adding all the students to filter students we have not passed in any if condition so we want to add an if condition checking if student at I dot Mass is greater than 20 or we can have greater than equal to 20 otherwise it wouldn't include Naman I want to include Naman as well and then I can just have filter students dot add students at I so we have grabbed the current student that we are looping through then we have dot marks so it gives me 10 20 30 40 and then I'm just checking if it is greater than equal to 20. if it is greater than equal to 20 then we are adding it to filtered students and then I am printing filtered students and I don't need to be concerned that it will give me instance of student class because we are the override method over here neat now I can run this and I should be seeing student Revan Naman Rakesh and here we have student Naman Rakesh son because Revan only scored 10. what if revance goes 30 and we run it so we get driven included as well so now we have 10 and yeah this is how you would do it right but what if I tell you there are two neater approaches you could take one is the foreign Loop that I talked about I told you in the loop section that we are going to cover something known as foreign Loop where we go to list so that's what we are going to cover here instead of having all of this entire what if I directly get access to the student aware so what if I Loop over this but while looping I directly get access to the student class so I can just have final student in students this is the Syntax for it we have a for Loop then we create a variable using final student then we are having in because it is a foreign Loop you can think of it this way this is a foreign Loop so we are having n keyword right here students so that means I directly get access to a student class or student instance now I can just have if student dot marks is greater than equal to 20 then filtered students.add student and if we run it will give us the same output what just happened in this foreign Loop well we are just saying run a for Loop for every student in students and here we have created a variable using final student you can also have for student student or variable student but you cannot have integer student because it knows we are looping through a list of students you cannot have integer aware so the type checking is there so this was another approach we could take and foreign Loop just makes this easier whenever you don't have to access you know specifically I so you don't want to get access to index at all and you just care about you know what we are looping through for example the student object over here you can just use the foreign Loop you don't have to go through the hassle of having foreignty is equal to zero and all of that stuff because it introduces an unnecessary variable and it can be a bit tough to you know continuously access students at I students at I so a foreign Loop is a neat thing but what if I told you in this case we could go one step ahead and not use foreign loop as well so what we have is not even a list aware what we can have is just use the students list and filter it out so what we're going to do is students and search for a method aware which can do this add basically says it will add it add all basically takes in an i treble I treble is kind of like a list but it loads lazily by loads lazily I mean if you have students created aware all of those get instantiated where but if you have an iter bill of students which you can have like this okay it doesn't give us any error nothing at all but that just means all of these instances won't get created right there and then it will only get created when we access a particular instance of the I treble over here and it gives us almost the same methods that list had to give us but you cannot add you cannot let's say remove you cannot do all of that stuff now coming back to the filtering option how do I filter that stuff out so to filter it students have one of the methods over here which is where all right if you see where now this where gives us an eye treble again which is I treble of student and then this is how it's defined Boolean function student test what is this thing right here well it's basically telling that the students.where function that you call has an argument inside of it that it gives us which is student so we're kind of looping through it all right so we are looping through it because of which it gives me student class because this is a list of student it gives me a student instance and here it expects me to return something so it expects a function out of me so I can either have this or I can just have this and here I can put a condition and this condition is for my filtering so I can just have if the student dot marks is greater than equal to 20 then you know just add it to the list that's what it does and if I do this much will I get rewind removed out of here not exactly why is that the case well that's the case because if you come over here where returns an i treble of student a bear returns an itable of student it's giving us something like a list returned to us it's not like students.ad where the return type is void if you see aware students.ad is void that means it doesn't return anything if it doesn't return anything it's probably because it's already added to the list but when we have students.where it gives me a new list a new I triple and that I travel consists of student classes so if I just print final filtered students which is equal to this now I copy this filter students print it over here and run it I get student Naman student Rakesh and student sonal Revan is removed but this is no longer a list this is an iter Bill if you don't believe me just check its runtime type all right run it and this is where I treble student and if you just hover over this I travel students I don't want an I travel I want a list so to do that what you can do is print fi filtered students Dot and then you can convert it to a list by just having two lists like this and if you do this much you will get a new student list an updated student list and this solution is so much prettier than you know running through so many steps it saves a lot of time for us and it's much more readable how is it much more readable let's go over to this in English so we are getting a filtered students and how are we getting the filtered students where we are going through all the students where student dot marks is greater than 20 right we're going through a list of students where student dot marks is greater than 20. and then it saves it in filtered students and we are converting it to a list and printing it out over here we can do all of this in one single variable we can just have students is equal to students.where but it gives us an error because I triple can can't be assigned to a list so I can just convert this to a list as well run it and I'll get the same output so we don't have to create separate variables for it I could just reassign and print the students so that it gives me the same output so that's where where helps us to filter things out gives us a nighter build which can be converted to US list so we are almost done with list surveyor let's take a look at a few more methods that list has to provide so we'll ask students Dot we know what length means it will just give us the length of the list reversed that means it will give us the list that is reversed that means sonal will come first rakhi is second number third and one fourth if you don't believe me I would recommend you to just have two lists over here just print it out like this all right if you just have this done and run it first you should see number one like this and then sonal Rakesh number one like this great now let's take a look at other properties that we have so we have students DOT first so it gives me the first element first on also if the first element is null it will give me null indexed smt is empty is quite useful it helps you to know is the if the list is empty or not if the list dot length is 0 that means it is empty it is not empty if list dot length is not 0 then we have iterator which gives us the iterable form of this then we have last which gives us the last element of the list last tunnel similar to we have what we had first on null then we have ADD add all add all basically allows us to pass an I triple over here by itable it doesn't necessarily mean that yeah you need to go ahead and pass I travel over here no you can just pass in another list over here because I triple can take in a list but a list cannot be unite treble all right and you can add multiple list elements of AR alright and obviously this needs to be a student class so go ahead and add student classes so it will add all of those student classes together and add will obviously add them at the end then we have asmap so it converts it into a map what is the map you might ask and that's what we are going to take a look at in just a minute after we have gone through some of the important functions in list so we have clear which clears off the list you know it just makes it empty removes all of the elements inside of a list then we have contains and this is also important contains is basically like used in if conditions it gives us a Boolean value and a check so if student contains you know student ravan with grade 10 then you can do something so it helps us to know whether the list contains an element and this contains is basically like running a for Loop and then checking inside so this contains prop method is created by dot inside which is like hey we will run a for Loop and check every element with the element that is passed in the parameter over here and then we have a bunch of methods like index of basically if you want to find index of a particular student class or student instance you can do that then we have first where and last where so if you have first wear it basically means that when we run the where filter and if there are duplicate elements inside of a list so we can have list sonal 30 40 like this how many ever we want or these things are different right because they are different instances of class what if I have final sonal student here which is equal to this thing right here okay so I can have multiple sonal students over here I cannot just have one okay I'm allowed to have as many as I want so it's basically telling me students.firstware will find and return only the first student it finds matching to the condition you've passed in and similar to that is last where so it will give you a student instance which follows the condition that you've passed in over here but it's the last thing so it will give me this sonal student then we have remove ad so if you want to remove at a particular index then we have removed which we've already seen remove last which removes the last element and all of these things are English you know you can just understand that by our own but element at gives me the element at a particular index and index of gives me the index of a particular student all right so these two things are reverse of each other so we have looked in uh add a lot of list methods so now that we've covered list I quickly want to cover sets because search is quite similar to a list remember how in a list we can have multiple type of students you know all these three things are the same students owner students owner students however what if I don't want the same students to exist over here to do that I can create a set so I can just name this as a set instead of student and that gives me an error because sets are not defined like this this is how lists are defined for a set you need to use curly bracket so you can have curly bracket like this and it doesn't give you any error anymore but ravan you said it cannot contain multiple type of students right I mean it cannot contain the same student again and again how is it not giving us an error then well it's because if we just print students out now and run it we get student driven student Naman student Rakesh student sonal and that's it all the rest of the students are not counted anymore so it just removes all the duplicate elements inside of a list that's what a set is it removes all the existing same elements if we do the same thing with the list and then we'll have to convert this to a square bracket and run it we have sonal student like this rest everything is similar to a list but set just removes all the existing elements that are same in uh list what if I want to convert a list to a set so that you know I can remove it but still I want to keep it a list how can I do that well you can just do it using to set okay so if you just do two set and run it it will remove all the existing student sonal classes except the one that was already there okay so that was about set and list the difference is just that set cannot have the same elements again and list can have so it's quite useful if you want to filter out all the existing sonal students you don't have to run where conditions again and again you can just have two set it will remove everything great so now that we've understood about list and sets we need to run into Maps let's get into it so what exactly is this map thing a map is a collection of key value pairs where each key is unique so let me show you how it looks so map looks kind of like this you have a thing like this you know curly bracket then you have a key so you have a key and a value for that key then you can have key 2 and a value for it which can be value or value two so the key needs to be unique over here but value can be the same or different that doesn't matter so it's a key value pair this is how it looks like it's this map thing is commonly used to store and retrieve data based on a specific identifier so let's take an example earlier we had seen how we created a list of marks to store one user's marks right what if I want to store multiple students marks and these marks are just based on one subject all right so in list I would do something like final list which is equal to and I would store the mark so we have 10 15 30. now how do I know that this is ravan's marks this is naman's Mark so this is another Kids Marks I cannot know but map can allow me to know it how I can rewrite this entire structure as this so we have a map then we have marks which will be equal to this curly bracket thing that I told you this is used to create a map yes this is also used to create a set but in set you only have one elements written over here but in map it's different because map is a key value pair so here you'll have the name so let's say the name is Revan and rivan marks is 10 Naman marks is 15 and other kids marks is 30. so this is how you've created a map now we know exactly what student has got what value we don't have to depend on this right and then to know which student has scored what marks we can just have print marks and you know if we do this we'll get this entire thing printed out you can run it and see it but I just want to get ravan's marks so to do this again we are going to use this square bracket Operator just like we did for map for list for string we are going to use that as well but here instead of specifying any position or anything else what we are going to have is the key present over here so I can just pass in rivan here whatever is the key and then run it so if I run it I should be seeing 10 now because that's revan's marks and there we go we see that however now if you hover over this you see this is of the type map dynamic dynamic so in our generics we have two data types first one and second one both are Dynamic why is that because we've already seen this with the list when we didn't specify anything for a list you know if we just had list like this it was list of dynamic the same thing happened here but instead of having one generic type over here we have two because this one is for the key and the second one is for the value so this Dynamic is for this thing right here and this Dynamic is for this thing right here so we can change this what will I change this to I will have string comma integer if I do this I have map which is having string over here and integer over here now since we have mentioned the type surveyor if I do dot I should be getting everything interrelated if we just remove this we won't get anything interrelated no Auto suggestion for this why because yeah we have specified end so it knows that if I do Mark certain one so if I call Marks add the key ravan then it's going to give me a value of 10 and we know that this is going to be an integer that's why it's going to be an integer so we can just have is even let's say so we'll get to know if it is even or not and then we can run it but you can see we are getting an error we're getting an error because the property is even can't be unconditionally accessed because the receiver can be not it means that this thing right here can return a nullable integer so we either need to do this if we are confident that Revan surely exists or we can just do this so that if the key doesn't exist it will give us a null value and it won't throw null operator null check operator used on a null value now you might ask why do we get an integer which is nullable returned aware if you're just passing an integer here we're not passing in like this right we are just passing in so so it shouldn't give us a nullable integer and a partially correct it shouldn't but there's a benefit when it receives when it sends out integer which is nullable for example if I have a key that doesn't exist in this map for example I put in sonar this key doesn't exist and if I just do this like this you know if the nullable operator wasn't there then it would give me something like uncaught type error cannot read properties of null all right so it's basically like the hey we try to get marks at sonal but this key doesn't exist here so there's no value for it if there's no value how are you saying that yeah this thing is not null that's why we can put question mark here and that's why it returns to us an integer which can be nullable because if a key doesn't exist it is going to return null to us so yeah we can go ahead here and have the extra check like if marks at sonal is equal equal to null then let's say I want to print key does not exist otherwise I'm just going to print let's say print marks at sonal all right so with this nice type checking I can just do marks at sonal dot is even all right and we can put an exclamation mark here we can put an exclamation mark because we have already checked if Mark said sonal is null then it's going to pre-print key does not exist but if it is not null that means it's going to print marks at sonal so we can for sure know that this is not going to be null right so now I can run it and there we go we have key does not exist however if I put number near and Naman here and then run it I should be seeing false because 15 is not an even number so I hope that was clear now let's get into the operations map allow us to do also you can have something else like map string comma string so that means you'll have to convert everything to a string over here then it can be map int string so that means it can be 10 20 and let's say 30 you can even do this all right so you can have anything over here even your classes so you're gonna map in student and then you can pass in your student class over here and that will work just fine so I hope you understood this you can pass in any type you want now let's get into the operations like adding a map removing from a map iterating over the map so we can just have those operations really quick so to add to a map we can do marks at let's say I want to add to 40 equal to 200. so what I've done the way we print it I can do marks at 40 and set it equal to a string however if I try to assign it to an integer it will give an error to me because we have specified the data type for a map and if I save this and of course let's go ahead and print marks we should be seeing 10 20 30 along with 40 added and there we go 10 10 20 15. now all of them look similar like it all looks integer but when we print it it just feels like that in reality it's int and string all right and you can see the new value is added wire perfect if we had a string over here you'll have to pass in a string like this convert this to a string and you know that's how you can do it so this is how you can change in a map that's another method you can take for example like if you remember in a list if we die try to do list at 0 1 2 3 so if we try to do list at 3 equal to let's say 45 it would give an error to us but in map this is allowed also you can update the value the same way so you can have marks at 10 equal to 100 let's say and then you can print marks again and you should be seeing 100 in the beginning and that's what we get perfect so you can update and add new values just like this it just checks if marks are 10 already exists then it is not going to create a new key value pair however if it does exist then it's just going to update the value over there and yes you cannot have two keys of the same value and I've already mentioned that before you can see two keys in a map little shouldn't be equal now there's another way of adding marks and that is by doing marks Dot you know list had its own bunch of methods and properties even map has that because map is a class and if you come away or you can see it's an abstract class map k v so it's the same thing so we cannot instantiate map however we can have marks Dot and a bunch of properties on it and to add a map you can see we have the add-all property we can just use that and in the add-on it requires us to pass map of int and string so the exact same thing that you have over here you need to pass that in so I'm just going to pass in let's say 40 comma 45 and the advantage add-on has over the other thing that we saw like marks at 40 is that you can pass in a bunch of maps together so you can have 50 65 you can have 70 and let's say hello you can have all of them together in one single map that you pass in over here and then when you run it it will work also you can also if you found this very you can say a weird kind of syntax you can just extract all of this out in another map which will be equal to this and then you can pass in the map and that will work just fine it's just like you know creating another variable and storing it so no big deal there so this is how you can add if I want to remove something what I can do is marks Dot remove and you see this doesn't ask me to pass in a map it can be an object and here you just need to mention a key and the key is let's say 10. I just want to remove this part over here so you can just do mouse dot remove 10. you don't care about the value to add a value you need to pass in a value but to remove you just need the key and you pass in a key and then when you run it it shouldn't show 10 year anymore and there we go we don't have 10 it starts from 20. so we have learned about adding deleting and updating values now let's go through iterating meaning I want to Loop over all of these things so for that we already know we have something known as for Loop we can just use that over here so we can just have for enter is equal to 0 I is less than Max dot length let's just remove another map we are not doing any calculations over here I plus plus and this works Mars dot length is a valid thing on map as well and the length it will give us is three so this one entry is known as a map and now we can just you know go ahead and print marks at I right if we do marks that I build that work not really because what you're basically telling is print marks at zero so it goes ahead and searches for the key zero is there a zero where you know it's just going to print out null so if you want you can go ahead and run this and you'll see null three times written over here perfect exactly what we expected so how do we read a value on a map so for that we have access to Marks dot keys and if you see this Keys is an iterable why is this an interview because this Keys is giving us access to all the keys that are present in the map in kind of a list format all right iterable is not exactly a list but obviously you can go ahead and convert this to a list so that you have a list with you so anyways coming back to the point it's just giving me a list or like 10 20 and 30. so if I go ahead and print this now I'll see 10 20 30 in a list printed three times and that's what I get now to access the property over here or to access one key over here what I can do is maps.keys at I if I do that much it doesn't work why because it is an iterable if I use this over an i treble it won't work so I need to convert this to a list so that we can get access to this thing now we've converted it into a list so we can access the zeroth element the first element and the second element now we should be seeing 10 20 30 return over here so we've got access to all the keys now what if I want to get access to the values as well so I can run another for Loop over here and print it but what I want to do is print all of them in the same line so to do that what I can do is string interpolation I can just put a string over here cover it with curly bracket then put dollar because this is a big thing so we have a key and then we are going to have a value so to get the value again we are going to put dollar braces and then we are going to have marks dot Keys dot two lists but if I use Keys again will that give me these values that I want not really it will give me again these values because we'll do the same thing so now we'll have marks.values Dot to list because that will be an i treble as well and then we are going to have I over here and now if I run it we will see 10 comma 10 20 comma 15 and 30 comma 30. so we are able to get the value of each Maps keys and values now an easier solution to this could be using a for each Loop that is present inside marks map only so we can do marks Dot and if you scroll down you will see something known as for each or a map so if you do marks.map you'll be able to map through it meaning you'll be able to Loop through every entry that is present over here but I'm just going to use for each because that is going to give me a cool thing so I can just have for each aware and if you see the for each function definition this is how it looks we have void so it doesn't return anything then you have a function which returns an integer and a string why is there an integer under string because our key is an integer our value is a string so it's basically returning key and value to us so we can just have this much done and this is a function obviously so we are going to have this or you can have a single Arrow I'm just going to have this because it looks neater and then I can have key let's have string interpolation here and then value and value is not defined because here I've defined it as Val so you're going to have value like this and then if I run it I get the same result but this is much neater solution because dot has done this for us behind the scenes so we don't need to care about you know running for loops and stuff another thing to note here is I've not mentioned the type but it is correctly identifying the type because for each is giving us integer and string so it knows that yeah this thing is an integer this thing is a string but yeah we need to give variable names to this so that we can access it on code editors like you know Visual Studio code or anything that we will use in the flutter section you'll see that we get autocomplete for whenever we type for each function it will automatically generate those variables and values for us which we can obviously change but it saves a lot of time for us this is an advantage of using Code editors instead of dot pad because dot pad is frankly not much Advanced you cannot do a lot of stuff here for example the file system is not present here so now we have understood about thoughts and we have understood about maps and where we would want to use a list where we want to use a map both are different things not to be confused this list is like an array list and this map is like a hash map in Java or like an object in JavaScript but object in dot is different from object in JavaScript I hope that makes sense if not because you've not coded in JavaScript don't worry about it it's just extra information so that people who know it can follow along well so we have covered Maps as well but I just want to take this opportunity and expand on the concept of maps further by using list of map what if I want my list to have a list of maps all right so this thing right here is suppose marks of one student all right so we are going to have map of string comma integer and yeah this is math marks this is English mocks and this is let's say computer science marks and math I got 20 in English I got 20 and in CS I got 20. so I'm an excellent student so I got all of these values but these are marks of just one student what if I want to store marks of several students so this is marks of user a I want to store marks of user b c d e as well so for that what can I do I can create separate Maps that's true but I just want to store them in one particular list so that I can continuously access that list instead of accessing these variables so for that we can have list of map of string comma enter and you can do this why can you do this because list allows you to pass in any type in map also you can pass a list over here and in a list you can pass a map over here all this wants is a type and this type can be classes Maps lists sets whatever you want so here we have a list of map string comma integer so now we are going to store marks of all student and this is going to be equal to a list so we have created it this way let's push the console behind and for readability I'm just going to go to the next line so we have a list of map so I've created a map and here I'm just going to pass in let's say math marks which is 25 then CS marks which is 30 and English marks which is 15. oh I think a grading is out of 20 so let's put 2020 over here and English is bad so we are getting 50. now we can put a comma over here since this is a list so what we have right now is a map now I can create another map over here so I can just copy paste this and here I'll have let's say math CS English the same keys but the values are different so in CS we got 15 math got 10 and finally the last map over here is Mark's user at a all right so our excellent student comes right over here and if you see marks.fore each is giving us an error because Marx is now a list it is not a map so you cannot run for each aware so what can I do I can just have marks dot map so this is one function which I didn't show you in list so you can use this marks.map function this map is basically iterating all of these list elements so you can use it and when you do this you get let's say e and this e thing right here is a map of string comma integer it correctly identifies that if you map through it you'll get a map of string comma integer this thing right here or this thing right here or this thing right here because this is marks user a so I can go ahead and print e run it and we get nothing printed out over here why because this is an eye treble I told you I treble have lazy loading you can see this it returns a new lazy eye treble with elements now what I can do instead is convert this to a list all right so we can convert an eye table to a list right the map gives us an itable I've converted that I treble to a list and then when I run it we get a math at 20 and all of these stuff automatically printing out because list is not lazy loading an iterator or an itribble is lazy loading I hope it makes sense to you now what I mean by lazy loading so you see we get all of our maths and Cs and English marks correctly however what I want to do is map through the map as well and you know just print out all the values over here so I can just have e Dot and just what we saw we are going to run it we are going to have e dot for each so let's have for each right here then we are going to get a key and a value which we can print out so let's print dollar key then dollar Val and that's pretty much it now when I try to run it I get math 20 cs20 English 15 math 10 cs15 English 15 math 20 and all the values are showing up and there are nine values which is correctly so because there are three maps and the all of them have three entries which is nine great so I hope you've understood the use cases for a list and a map the topic is now enums it is a comparatively short topic but it's quite interesting and has many use cases that people don't know about let's get into it so to understand enums or what they are called as enumerations we'll have to first create an example so let's go ahead and create a class called employee and this employee class is going to have two things inside of it first it is going to have the name of the employee and second it's going to have the type of the employee so the type of work the employee is doing and then we can have employee this dot name this DOT type all right now we can go ahead and create employee one which is equal to employee but then the name will be let's say Revan and the type is going to be let's say software engineer so I'm just passing in swe then we can have another thing here so let's paste it again and this is going to be employed to and Naman and let's say he is related to finance department so we only have two employees as of now but then a third employee comes in and the third employee passes in the name correctly but then the type is open-ended right there's no limited constraints from which the employee can choose so they just go ahead and use something like hahaha so they're just playing with our program since we've kept this as a string they can enter anything over here which is a string and we'll be fine with it but in reality we are not fine with it because the user or the employee cannot just have hahaha written away either they have to be in software engineering Finance marketing or something like that our company doesn't have a position or an employee type of hahaha so this is a problem that I'm facing and enums help solve this problem they help us create kind of boundaries in our application because they will help us to improve the code quality obviously because we are limiting what our strings can be aware of and they also prevent bugs and things that are very error prone for example this part right here because if the type is hahaha it can cause problem when you're trying to you know print some stuff for example if you have a function over here so we have let's say void function which has switch type and then you have case of software engineering so you manually have to first of all type these strings and make sure all of those are same and then you have software engineering written over here then after that you again need to make sure that Finance is correctly spelled and then you can print Finance let's say and finally you have let's say default meaning none of the cases matched over here so you have a print saying something went wrong this default case should never be executed in our case because this hahaha isn't a valid thing right and we want a proper detail of our employee they cannot have something went wrong either it should be software engineer or Finance nothing else so this is what enum will help us to do to create an enum you need to get out of a class you need to get out of a function and you need to globally declare it in your program and then you can just have employee type even here the casing is similar to a class it's going to be Pascal casing so e and t are big capitalized and here we need to mention the boundaries or the options that we have here so what are the options the employee can have either employee can be software engineer and make sure that this is you know all small case if you try to put it like this the linter will throw an error or a warning saying the constant name software engineering isn't lowercase camel case identifier so you need to put swe over here then you have Finance then let's say you have marketing so these are the three things that you have in your enum all right so that's how easy an enum is now you can replace this employee type everywhere so instead of using a string you can have employee type over here which gives us an error in the switch case and even over here so let's first fix this part so here it requires something known as let's say employee type right so to pass in an employee type we'll have to first pass an employee type like this so it's just enough not really because then we have to put dot and that gives a bunch of options Finance marketing and software engineering values is basically a list containing all these three things in our case we want software engineering for the first guy then we can let's say copy this paste it over here and this time I want Finance and this time sonal is actually employee type dot marketing so software engineering finance and this is marketing now we are doing some good work now I don't have to care about you know typing the strings correctly in fact I can just do employee type Dot swe and I'm sure that this is correct because if I spell this incorrectly it will throw an error so if employee type is software engineering we print software engineering if employee let's say type is finance then we print Finance and if it's none of these two things then definitely it is marketing because the user cannot enter any of this also if you just ignore the default case you see we get an error over here why do we get an error because it's saying the employee type is not exhaustively matched by the switch cases since it doesn't match employee type.marketing this is just meaning that hey you forgot to put a case of employee type dot marketing please put that so that's a nice thing that we get with enums it's not possible with strings because how many cases can you handle right cases with strings can be literally anything you want so we have case then employee type dot marketing or you can just put default and then you print marketing so that's good now the error goes away and if I just print let's say employee one dot let's say FN actually I shouldn't print it because I'm already printing it in the function itself right over here we're not returning anything from this function we are printing it so we can do this this will be employee three so let's call employee three dot function as well let's run it and we should be seeing software engineering and marketing and that's exactly what we see so enum is basically providing us with code Clarity and is helping us to avoid and fight bugs in the first place so this was a basic type of enum and this is what most of the people use but dot has gone beyond just enum so enums are more like classes now all right so let's say you wanted to pass some values along with these things right so you have software engineering Finance marketing you want to pass a credit score with it or let's say the salary each employee gets if they are either of these three things so to do that we have something known as enhanced enums that were introduced newly not in dot 3.0 or 3.0.1 they were introduced after dot 2 I think so to do that what we can do is put a semicolinear all right after you put a semicolon after this you can just go to a new line and then have final integer let's say salary all right so you've declared a variable over here but this variable is not like you know final salary is equal to 150 000 like this it's not like this in fact it's like a Constructor so you have constant employee type this dot salary so now we have created a Constructor for this enum which is employee type and we get an error over here we get errors over here because it's basically saying that hey you've created a Constructor if you've created a Constructor that means you need to pass in the values of this employee type for every single one of them that means I'll have to do software engineering like this and pass in the solidity of software engineer let's say 200 000 then of the finance guy so let's say 250 000 and the marketing guy which is let's say 150 000 so the errors get resolved and now the benefit of having this is if I want to print the money each employee makes so if it's software engineering then I want to print type Dot and if you'd see we get type dot salary this type is the employee type that was passed in from year so I can use this type to have type dot salary index name and rest of the things we've already seen for every class every enum that we create so the salary is now added over here because it's a field in an enum now we can access the salary of every single one of them so we can just have type dot salary for each one of them like this and actually we don't want to do switch case anymore you can just have print type dot salary if you just do this much it will print out the salary of your employee right by to do switch case because in switch case you're basically returning type dot salary every single time instead we can just remove all of this and print type dot salary once and for all because you're not doing any specialized task for every single one of them okay so let's just print type dot salary here run it and we should be seeing 200 000 which is the software engineering and 150 000 which is marketing great so I just wanted to show you that you can have many more Arguments for this Constructor for this enum Constructor I should say and then you can use it over here also you can use type dot name let's convert this into string interpolation so we have dollar type dot name if you use type.tame then we'll have software engineering and then if we try to run it we get software engineering this marketing this but as you can see we are getting a warning over here that this thing right here type dot name is available since SDK 2.15 but constraints 3.0.1 which is this version Don't guarantee it so we should probably stop using it now there are many more things you can do with enum for example you can have implements and you can Implement another enum with it and you can do all of that stuff but I'm not diving into it you can try it on your own so now we are done with enums as well now let's get into the world of exception handling and it's really simple so let's complete it really quick so what exactly is exception handling as the name suggests surveyor exception is being handled now what exactly is an exception so I'm not going to give you a definition for this I'm just going to show you what exception is and you've seen it before so when I try to print 10 truncating division let's say 2 or 3 I should be getting three what exactly is this it tries to divide 10 by 3 so it gives 3.33 and then it converts it to an integer so we get three that's truncating division now if I try to do 10 divided by 0 it should give me Infinity right because 10 divided by 0 is infinity then I try to do 10 truncating division zero and then I want to put in the most important thing in my program which is my name so it's fine if this result or this result or this result doesn't get printed but Revan should get printed but yeah if everything is fine then print all of this under one should be down below now if I try to run it I get 3 I get infinity and then I go get this error and because of this error thing right here I cannot see my name printed that's just very bad because the most important element in my program my name is in there and it's not there because an error came along and this error that you see right here is an exception and we want to handle this exception how we are just telling that it's fine if it doesn't get printed but rest of the program should continue working if there's an exception it doesn't mean that yeah you just stop running at all you just exit out of the snow right now the program just got out of this it through an error over here unsupported operation and just terminated this entire function this entire program saying there's an error I cannot go further now that's where exception handling will come into play we need to resolve this error such that rest of the things still continue working so how do we handle exceptions first of all this exception handling technique is only used for things like this all right or if you are calling an external service to get some data for example if you're calling your database then you can have the exception handling done if you're having this kind of thing right here you can have exception handling done but if there's some logical error in your app let's say you print one one two so you're just wondering why is this printing Revan one two I just wanted to print Revan that's an error right I should just handle my exceptions away or no it doesn't work that way it can only handle exceptions which are basically runtime exceptions and you can't possibly know that yeah this thing right here can through an exception so wherever you feel that this might throw an exception something like this you can handle it but not for something like r112 where you obviously know that this error is there because everyone is there this is still possible because let's say the you numbers entered over here are by the user right and if the user enters zero we cannot do anything about it yes to the current portf conditions and check hey the user cannot enter 0 or whatever but an exception handling is just a neata way of doing stuff so to start with exception handling first you need to have a try block so this thing right here try and then you need to have a catch block and this catch block gives us something known as e which stands for exception okay now you just copy this code inside of the try block so this code that you need to put in try block is whatever you feel that can throw an exception so this part of code can through an exception so you wrap it in a try block and then you have a catch block if you don't have a catch block after try block it will give you an error because a try block must be followed by an on catch or finally clause we're going to take a look at all three of them but first let's go over the catch block so we have catch aware and this catch gives us something known as an exception now I can just print this exception to know what just happened all right and that's exactly what exception handling is as easy as you can see so if I try to run it what do I see I see three I see Infinity I see unsupported operation the same error that we got earlier but instead of red it is white why because we've printed e over here instead of e if we printed some error occurred and run it we will be seeing 3 Infinity some error occurred then ravan so the main point over here is after this thing right here through an error my program didn't stop working because I've handled the exception I've introduced exception handling aware because of which I get some error occurred written over here and after that my print statement is still working and other codes might still work over here so that's catch block now there's another block after catch that we can use which is finally so this finally block that always executes all right even if this thing right here doesn't throw an exception so if we just have 10 divided by 0 again and then you know we try to run this now print some error occurred will not happen what will happen is this print here will get called so Infinity will be there and Revan will get called what this finally does is if there is a try block that was executed or the catch block that was executed it doesn't care finally just cares about you know that I just want to run every single time so we just have finally blocked executed all right now if we just do this you'll see that we get infinity sorry 3 Infinity then finally block is executed so this thing right here is executed even if try block is executed so let's have our exception again even if the catch block is executed so it will just print this every single time so this thing right runs every single time this block right here is optional but allows us to specify code that will always execute regardless of whether the exception occurs or it doesn't occur so it is typically used for cleanup tasks or releasing resources in try block or catch block or whatever so this was the thing that we were talking about you know when we didn't have catch block aware you saw like this it said that there needs to be on catch or finally and the final thing that is on so this on is used so that we can catch a particular exception so there are multiple types of exceptions right there as you can see format exception implements exception and exception might be an abstract class so if we just use on exception you can see abstract interface class which means it is a proper interface and we've already studied about this in class modifiers we print e now if this runs what should we get should we get unsupported error or an error account we get an error occurred over here because the type of the exception is unsupported exception error not exception or format exception so this thing right here so on basically allows us to catch some kind of exception all right and this exception can be things that are classes already created in dot so it can be format exception exception and a bunch of other exceptions that you can find if you just Google it out so I hope you're clear with try catch blog they are quite an important concept when we learn about Futures Futures are one of the most interesting things in dot because they're not available in any other programming language or actually they are available in other programming languages like JavaScript but they are named as promises so we are going to learn about Futures now and there we can use try catch block where it will make much more sense right now you might just think hey if I know that this thing this operator right here can have an exception why do I have to do this with Futures that's not the case because in Futures you'll be contacting external apis right if you're contacting external apis or you can say external Services if you don't understand what API is if you're contacting external services that might be a problem because when you contact external Services you don't know if this will run or this will not run because when you contact external Services it's not just dependent on your code it's also dependent on your internet connection your internet stability right if your internet is off and then you try to make a request that wouldn't work why will it not work because I'm trying to connect to something outside of my program if I try to do that obviously I need to go ahead and you know get some data to get the data I'll have to use the internet connection so that's why Futures use exception handling extensively so let's go ahead and understand what Futures are so what exactly is this future this future is basically a class that represents that a function or some computation May complete in the future and this will produce a result or an error it is related to something known as asynchronous programming asynchronous programming allows you to perform tasks concurrently without blocking the execution so for example if we have multiple print statements here so let's have print here then we have print let's say hello and we have print greetings all right so we have three print statements over here how are they going to execute first hey is going to get printed then hello then greetings so only after hey gets printed will hello print and only after hello gets printed will greetings print so this is an example of blocking the execution meaning these tasks aren't being performed concurrently so how this works is hello gets printed only after hello gets printed will hey get printed and only after he gets printed greetings will get printed however this will take some time right and it is fine when we have print statements or something like that but what if we are talking to an external service to get our data right so how will that work in that case so let's say instead of this print we are sending a request to an external service so that we can get back some data and you might ask what is this external service let's take an example of jsonplaceholder.com this thing provides us with fake API API or stands for application programming interface it's basically how two Services can interact with each other so you have if I have my Dart application over here and I want to get some data from external service I can use something known as an API so to get some data from Json placeholder I can use this free fake API that they give for testing and prototyping and if I just do slash users after this URL I get a bunch of things over here and I get all of this in some form of an edited format because I'm using the extension because I'm using an extension in Chrome which is Json formatter and that just prints it out in a Json format and Json stands for JavaScript object notation it's basically a way in which data is retrieved another way is yaml which you will see in your flutter but basically it gives us data in Json format which is Javascript object notation and it's kind of similar to a list of map in dot right so if you have this list we have one map over here then there's string over here a number where string over here a string again over so this means it is a list of map of spring comma Dynamic right because this is a string all the time but this can either be a string this can either be a number it can be anything so that's why your it is compulsory to use Dynamic otherwise it will give us an error because ID is a number not a string so anyways I want to fetch all of this data that it's returning so suppose I send out a request and in some time you're going to learn how to send the request but let's just say this comment here is helping us to send a request so that would mean it sends a request from dot pad to this API then it retrieves all the data from here and sends it back to dotpad so that I can continue but if I do this you know it might take a lot of time that means a request is sent so we wait for that request to complete so it might take like 10 15 20 seconds then only hello and greetings will print I don't want that that is kind of a blocking Behavior right and that's why we have asynchronous programming that allows me to run the tasks without blocking anything so what happens over here is I will send a request and while it is sending the request I'm just going to go ahead and print hello and greetings so it doesn't wait for this request to you know complete and then only move forward this request will keep running and you know whenever it has a value it will print it out but in the meantime it's going to go ahead and perform all the operations so that's what asynchronous programming is just the print statements over here that we had before like print hey that was synchronous programming and this is asynchronous programming so I hope you've understood this concept well now let's move ahead and dive into futures so let's take an example I have a function over here and this function's job is to give a result let's say after two seconds okay give a result after two seconds that's what it does now to convert this into a future what will I do and actually since I'm giving a result let's convert this into a string so I'm going to be returning a string okay and now we are getting this error because it wants to return a string but you're not returning a string but we'll look into that now how do I convert this into a future because it's giving me a result after two seconds if it is giving me a result after two seconds I do not want to wait for it because then my user has to wait for it and that's not a good experience at all so what I'm going to do is put a keyword here called async async here stands for asynchronous right so I've put async here and then the error comes over here this says the functions marked async must have a return type assignable to Future so that means I'll have to convert this to a future okay but if I hover over this this is abstract interface class future of the type T this is again generics and if I just return a future that means it is of the type future Dynamic just like we had before with lists and map I don't want to do that so I'm just going to have string return over here that means this function is asynchronous function it's going to take some time to execute and as soon as it executes and two seconds is over and it gives me a result and the result can be either an error or you can say a proper value then I want to return it and if it is a proper value then it's going to return a string right so I can just return He and that's exactly what a future function is as simple as that we just need to convert this to async and when we convert this to async we have future wear if I remove async I cannot put future like this that will give me an error because I'm returning a string from a future string however what you can do instead is Future like this you can wrap this with a future and then return a string so you have return like this and this works as well so what is this future is a class that I'm returning from here and this class has a function which gets run as soon as you know we return something from here and this is just telling us that we want to return a string so no need of async over here we can just return a future like this async is needed so that we can use a weight and we are going to talk about it in just a minute but let's just get done with it now I can just call this function so let's have give a result after two seconds called and run it and you see we get hey hello greetings but we don't get hey like this fives that the case that's the case because we are returning a future string that means we have not printed anything so I want to go ahead and print it over here obviously that's the only thing that makes sense now if I run it what should I see I should be seeing hey right but no I see instance of future string by is that the case well that's because I'm returning a future string and then I'm calling it so I'm calling a future string so it's returning to me a future strings if I just store it in a variable that's a final variable which is equal to this now let's call this variable result okay now if I print this result obviously it is going to give me a future string it's not giving me a string it is giving me a future string it is kind of enclosed in a future class so I want to get rid of this future how can I do that to do that I'll have to convert this function this main function into async why because this async gives me access to a weight this async is not necessary for future classes this future class can be created even when we return future like this this async is required whenever we want to use await and what a way does is basically await for it right and if you want to search the meaning of a weight you can go ahead and search it according to English only wait for an event right so that's what we are doing we are waiting for this event to complete and then we have access to string result which you are printing over here now now if I try to run it I will see hey four times written over here then hey hello and greetings now you might ask if we've put async over here we should be converting this to Future void right if we did something like this and you know just try to return a string over here and also let's get rid of the future class when I try to do something like this it gave me an error because whenever we have async this needs to convert to a future and you're right it needs to but whenever you have void it's not really necessary you can convert this to a future void but it's not necessary it's a good practice definitely but it's not necessary and there's a difference between future void and void so if you want to know more about it I'll mention an article below which you can refer it basically tells that future void and void are different from each other that doesn't throw any error if we use just void like this with an async but future void and void are different void is like a quick fire and forget meaning if you just call this function like this let's say we call give me a result after two seconds like this and it is of the type void all right so it will just fire this and you know it doesn't care about the result if it gives some result it will give if it doesn't it doesn't it doesn't care about it but if you have future void it will wait for this caller to complete and it will continuously listen to it so it's not fire and forget in future void but in void it is fire and forget I'll mention an article which goes deep into it but that was the basic gist I wanted to provide anyways coming back to this I'm just going to put it as void main because the starting functions are generally y domain that's why now I can run it and well I get he written over here that's cool but give a result after 2 seconds is not giving me after two seconds what are you talking about it gives me right there and there itself and that's because we have just wrapped it in a future class however we can do more with this future class for example add a delay so to do that we need to return future dot delayed and if we do this it asks for two things over here first thing is a duration all right you'll see this what is this duration this duration is another class that you can provide a wire so you'll have duration like this so if you don't understand anything you know this is a new function all together and since this function is new you can just hover over this and it will give you proper examples for this so the thing that it gives over here is duration so we need to mention a duration and then we have this thing in a square bracket which means that it's optional you can pass it and you cannot pass in it doesn't matter and this is computation computation is basically telling do you want to return anything if you want to you can go ahead and return so first of all we want to pass in a duration so duration can be created like this it is a class as well and this duration gives you multiple things you can pass in days hours minutes seconds and in the context of this function duration means how many seconds or how many hours or how many days do you want to wait I just want to wait for two seconds so I can just have seconds like this because it is a named Constructor you can see this curly bracket right here that gives a hint I'll pass into okay and after this I also want to return a string right so I can just have my computation in a separate function because it allows for that you can see it right over here and you have future string computation so I can return some sort of string here let's say hey again with many exclamation marks and we should be done yep there we go we are done if you want async aware you can have that async as well and it will not give any error basically the task of async is just to use await whenever you mark a function as async you allow the use of a weight keyword if you just remove async from here you see away it will give an error it just says that we need to pass the function body or Mark the function body as async only then a weight is allowed and obviously as a result of this you need to convert this to a future so that you denote it but in void I've already mentioned why we don't have to do that okay so now that we are done let's run this and you see we wait for two seconds so we get here written over here like this and rest of the things follow along now what if I have print hello like this and then I run it so after this run gets executed you know you'll see Hello like this then two seconds then hey gets printed and then rest of the things get executed now what if I remove the print result only and then I just say you know you can get rid of this as well then we run it we get hello after two seconds we get hey hello greetings so it is adding a delay of two seconds after which rest of the things get executed immediately now instead of marking this function as async there's another thing you can do so you can get rid of this async and await what you can do instead is get rid of this as well whenever you have a future function like this you can do Dot and then it will give you some functions you have asked stream which returns a stream we are going to study about streams shortly after Futures then we have catch error which helps us catch any error it's like try and catch block but you have catch error function there itself but what we are interested in is then this then gives us some value which we can use okay so we have value over here and that value is a string so basically you call this function give a result after two seconds and after that function is executed completely and you can call Dot then and Dot then will give you a value which will be a string so you can go ahead and print Val like this and then when you run it you get hello written first a hello greetings all of them get executed and hey gets printed at last because it waited for two seconds since it was waiting for two seconds what this decided to do was print hello so let's run it again it will first print hello then it ran all of these print functions and then after we got a value after two seconds it printed the value so that's what then does so you could go ahead and use async await the way you want it to or you can just use dot then so that will print hello hey hello greetings all the synchronous code first and then it goes ahead and prints hey after two seconds also this function doesn't have to be asynchronous anymore because you're using dot then dot then doesn't require us to put is put the function as async only when you want to use await will you use async great so now that we have an understanding of this let's go ahead and fetch data from this URL that we have how can I do that to do that we'll have to use something known as an external package or a dependency now what is this thing well there are certain things that are created by other developers in the dart community so that everyone can use it and one such thing is the HTTP package so if we just go to pub.dev you can see it is dot packages it is basically a package repository it is a registry that contains all the packages you can use for Dart and flutter apps and these packages are basically set of codes it's just like this code base but it performs some tasks and returns some functions to us which we can use and these things are created by the community or the Google team itself but they've not shifted with DOT because that might be unnecessary elements present in the app because not everyone wants to you know have API calls in their apps or in their programs so that would be unnecessary right that's why dot packages are made and you can yourself go ahead and put out your own package on this pub.dev it is a registry of packages so you can search for anything this thing we are going to search for is HTTP you can see this was created by the dot team itself if you see aware dot team themselves created it but they shipped it as a package not present in dot pad only or in dot only because not everyone wants to use it and dots size will increase if they have unnecessary code like HTTP which not everyone wants to use but anyways coming back to this point of this app we're going to use this HTTP package that we have to send API requests and we want to send an API request to jsonplaceholder.com users now how do we use this and first of all I'm still not cleared why do we need packages we need packages because well obviously we can send API requests from Dart itself but that would include using Elements which are really low level by low level I mean things that you know you won't be able to understand because well even I don't understand them it's for experienced developers who can simplify this for us giving us a very usable format in the format that you know people like me and you can understand obviously once you have enough experience you can develop your own package like HTTP that probably would not be a big deal for you but as of now I don't think either you or me is able to do this so anyways you can see this using tab the easiest way to use this library is via the top level functions you know we have something known as URI which is uniform resource identifier then we have HTTP dot post so we are using something known as HTTP we are posting it and that's it but we are not going to dive into apis here because all of this are basic concepts related to apis and you know HTTP the way internet works I'm not going to dive into it because well I want to cover Futures not API this is not an API course but basically to use it first we need to make sure that we can add HTTP in our DART program so if you're using a code editor and you have dot installed on your machine you would have to go ahead in a file called as pubspect.aml and then take this dot copy it and add it to the pubspect.aml like this then when you save it it will run something known as Dart Pub add or something like that and then you'll be able to use HTTP in your apps but we are not using Code editor we are using dot pad what can we do in dot pad we don't have anything like prospect.aml file in fact we don't have any files at all so dot pad is very good with this stuff it has a built-in support for these packages so all we need to do is call import so import helps us to import other files it can be files related to your program we'll see that when we get in the flutter course where we are going to install flutter run flutter and that will contain all the Imports of our own files and of packages like HTTP and many more that we are going to use and I would just like to mention again that it's fine to use packages that are created by someone else because that reduces our work easily like much more you wouldn't want to write your own implementation of these API requests because that can be very time consuming you're trying to create an application right and if you want to create an application or a program let's just avoid all of the extra stuff that we need to do let's just go ahead and use this package so anyways coming back to this we have import and then we have to import this with this import you cannot only import Dart packages but you can also import your own files that you've created so that you can use classes from there or let's say functions from there you can do that but we want to import a DOT HTTP right and this is how we do it it's written over here it's mentioned in their documentation so we need package colon HTTP HTTP dot dot so I'm just going to go ahead and copy this thing over here great now it's not giving me an error but it's just saying unused import we have not used this HTTP package anywhere so let's use it but as you can see over here we have as HTTP as well what is this as HTTP well basically let's get rid of a few things now so let's comment this function let's remove this thing from here let's remove all the call cells as well now if I want to get a URL what I need to do is just call get like this and it's able to get it yeah the warning from here is gone and it's giving me an error over here because I need to pass some URL so it wants me to send in some URI which I can use to you know get some data from that function or from that service and what is my service jsonplaceholder.typical.com users so I can use this get function but here they've used as HTTP because people generally don't like to use just get function like this because your program or your file might have another function which is get like this and that might create confusion so you do not know that you're using get which is just function or get which is coming from HTTP that's why you can suffix it by suffix I mean you can add as HTTP so all the stuff related to http goes in this HTTP variable or you can say module that you have now you can just do http.getlike this and now you can freely create void get and it won't complain it won't complain because this void get is different from http.get if you want to call this get you can just call get like this but if you want to call https get you can call HTTP dot get so I hope that was clear that's why they have used as HTTP over there basically in HTTP source code if you want to inspect it you can just click over here it will divert you to something known as GitHub GitHub is basically containing all the source code related to the package you can just go to lib http.dot and this is the exact thing that we are importing you can see there are lots of import statements over here there are a lot of export statements meaning it is exporting certain files and files contain classes functions all of that stuff which we can use and you can go ahead and see that there's get function defined in this http.dot and it's not enclosed within any class if it is not enclosed within any class it's a global function just like our main function right here or our get a function right here and that's why we were able to use just get like we have over here if it was enclosed in some class we would have to use let's say some class dot get but that's not the case with HTTP because it's a Global function so I hope you understood this if you are interested you can definitely go ahead and check the source code for more this is like the entire implementation of HTTP plugin now let's close this and come over here now what does get required get required something known as URI let's go ahead and again get to http package which I close for some reason so I'm here and now it will help me to use the package because I'm new to this package right whatever implementation they have done they need to guide me through it so that I can use it in my own programs so I'm just going to go ahead and copy rest of the stuff what I want to do is not post because post is basically sending data I want to get because I want to get all of this data right so to get some data what can I do well I need to have something like http.get right and nothing like that is mentioned in the documentation at least but we can take some inference from http.bos usually API elements are similar to each other when they're created by something like dot or flutter team themselves because they know how to you know manage all of these things and bring consistency so we can just have get away and this requires URI dot https and then we just need to pass in the domain name and that's pretty much it right so let's go ahead and do that so we can copy this URL let's go ahead and copy it so we have some URL and then we have uri.https now there are a bunch of other methods that you can use on URI because URI is a class like URI dot file uri.http uri.httpsuri dot pass so basically if you pass in let's say jsonplaceholder.tipcode.com users it will pass that and convert it into a URI and then we can pass it to http.get because http.get requires a URI so I think we can either use https because jsonplaceholder.typical.com is https or we can use uri.pass now I could suggest you uri.pass because I've already used HTTP in the past but let's go ahead and use https but obviously you can use https and if you want to know more about it it will tell you first thing that it needs is Authority then an unencoded path so what is this thing Authority is like example.com you can see that it gets example.com is this thing right here jsonplaceholder.typical.com okay that's fine I'll enclose it in a string now after this it wants something known as a path what is a path well in a URL this thing right here is the main Authority you can say and this thing right here is a path if you want to know more you can just have URL breakdown then go to images for a good diagrammatic representation and there we go we have HTTP which is the scheme so in our case we are using https because this is https then we have authority which is example.com including the port but we don't care about the Port Port is usually used when your creating your own server on your own machine and it allocates a path to the server that is running and yeah dot can be used to create servers as well but that's a topic for another tutorial not for this one then we have path to the file path to the file is basically anything after slash and then we have parameters which is question mark and all of that stuff but let's ignore parameters we don't care about it right now we want path and the path over here is users so I can just go ahead and pass users like this and we are done so I can close all of this stuff pass in the URL over here and there we go but what does get return to us it returns future response you can see I don't obviously know what it's going to return but by seeing the function definition all the time I get to know that yeah this is going to return future response so that means it is encoded in future and it will return a response to me so I can just have async aware so that I can await it or you can just have dot then done thank you and I will save this in a response now this response can be variable or final but this thing right here cannot be a constant why cannot it cannot be a constant because as I said constant is a compile time constant and http.get and any future is not compile time constant it is a runtime constant so we'll have to use final over here and now if I just try to print response what do you think it will give me well it is a class response right if it is a class response most likely it is going to give us instance of response because that's what we've seen for other classes as well right and if I run this function we see instance of response and you could see console was blank for a second or two because it was fetching data from this server or from the service but it's giving me instance of response and since I've used this response earlier you know I can just tell you that response is a very big object what we are interested in is response dot body because response.body will give us this thing right here response will give us a bunch of other properties that we don't really care about like headers status code all of this is you know we need to care about it but as of now we don't care about it all right we care about only the body the thing that it's returning right the 10 items that it has now I can run it and there we go there in my console I get everything so if I just put it down we have this thing right here so we have successfully fetched some data from an external service using HTTP package and external dependency if you just try to do this without it you won't be able to do it just using all of that stuff all right so this is where HTTP can help us and as a matter of fact any dot package but yeah you need to make sure that this is a DOT package not a flutter package to use it in dot pad if it is a flutter package you cannot use it and flutter packages are known as plugins and Dot packages are known as well packages so anyways we have all of this data now this API is actually pretty good you can play along with it by just having user slash one so you're just passing in let's say the ID of the user that you want to get so it just gets you one user so you can just use that so in your path you'll just have users slash one then when you run it it will just give you one object away or one map it won't give you a list as you can see it gives you one object not a lift and if you hover over this body it is actually a string it is not really a map why we want it to be a string like a map right and the reason for that is because our HTTP service doesn't know that we what URL we have connected to we just pass it that yeah we have we want to get data from this URL just do your thing and give me the result but in reality it doesn't know so it's just giving us a string of everything possible so that you know we can print it out and do anything that we want now an obvious thing in your mind would be how can I convert this to a map this is a string and if I want to access one particular property on it like a res dot body at name I cannot do this because this thing right here is not allowed on a string yes you can pass in res dot body at 0 which would mean that it you are telling it to get the first character of this string and the first character of the string is a curly bracket so it would just return to you a curly bracket but you're not really getting any name property or anything so valid question is how do I get the data and to get all of this data you have to use another package but not from pub.dev it is built into Dot and that is dot convert so we have dot convert like this and this will help us to convert string into let's say a map so to do this I will just call call a function which was created by Json which was created in the dot convert package so whenever you have package it's most likely that you are referring to an external package like something from pub.dev or or from your own file system only so from your own program as well when you have multiple files so it would be package the program name that you've passed in and some file over here but when you have dot convert it most likely means that it's coming from dot only so since it's coming from dot only you don't have to register in pubspect.aml file or anything now I'm sure it's not very clear to you but it will get clear when we dive into flutter and you'll understand it better so you can just copy this res dot body and put it in Json encode what is this Json and code well it's taking an object and returning a string that means it is encoding the particular body in a Json format but that's not our point we want to well get the Json out from this right so for that we have Json D code and this Json D code is opposite of Json encode Json encode encodes the Json that means that you know it is converting it into a Json format and Json D code is decoding the Json format in res dot body and this Json D code returns a dynamic to us and now you'll be like hey ravan you said we cannot use Dynamic but the dot team itself is using Dynamic how does that work well it works because well we're not absolutely sure that will it return on a list will it return a map we are not sure why because when we had users it was returning a list but when we have users slash one it is returning a map how will dot know what we are trying to return and that's why it is dynamic I said there are certain conditions where Dynamic is unavoidable but when you have the chance to avoid it you must avoid it so over here what you can do right now is you know just have Json decode like this so it's a dynamic so you can call something like name on it and it should print Lianne Graham properly FFC pronounced it correctly and we have Leon Graham right over here so we have successfully got data from an external API and that data is one Element only so this was about future why did we have to use future here well you could see http.getreturned a future to us if we don't have async await and you know the future classes we won't be able to get data from external services not just external Services we cannot use future.delete or anything but the primary use case is getting data from external Services also sometimes you know all of this can result in errors as well right now we were lucky enough to get data but what if you don't have internet connection so I'm just going to stop the internet connection then I'm going to try to run it well it's just giving me an error compiling to JavaScript because Dart pad doesn't run without internet so I guess I'll have to run the internet but to Showcase this I'm just going to pass in the incorrect URL over here I'm just going to pass in use and nothing like use exists all right so if I just try to do this it's nothing and also here I will misspell Json placeholder like this Json placehold that sounds wrong Json plays HR all right now we can run it and you see we get an exception now we know whenever we get an exception what do we want to do we want to wrap it in a try and catch block and the exception here is XML HTTP request error so to resolve it we can have try block and a catch block whenever we get e we are just going to print e let's say dot to string or print e both of them work and we are going to put both of them inside of this try block and then when we run it we should be seeing the exception printing out XML HTTP request but in white color so we will handle it successfully and then we can save some unexpected error occur and then when we run it we will be able to see the nice output and console now the reason for you know some exception like this is not just because you have named this incorrectly or something this can also be there because the service that we are trying to contact is temporarily unavailable right and in that case we cannot do anything it's not our fault it's the service provider's faults and maybe they're fixing it so that's why error error or exception handling is so difficult also important not difficult sorry it's quite easy as you can see and obviously if you don't want to have a try catch block like this you can go ahead and not use async await as well you can just have dot then which will give you the value so you'll have value like this then you can just print value dot body because that will give you a response and then you can catch an error over here as well so you have catch error like this you can catch it like this and then we have print error so if you do this it will work as well and you will get XML HTTP request error perfect but yeah one thing to note if you're using dot then don't use async await if you're using async await don't use then because either of them need to be used if you use both it's just showing your lack of concept because both are essentially doing the same thing giving us a value out of a future so now that we've understood future you know we've learned quite a lot about futures let's get rid of them and learn another thing present in asynchronous programming which is streams all right so let's dive into streams and then we'll also understand what is the difference between streams and future actually as a fun exercise let's just start with what a stream and what is the difference between future and stream so what exactly is a stream stream is basically an asynchronous generator so it's related to asynchronous programming just like future which allows us to produce a sequence of values over time so you remember how in future what you had to do was send a request so that you could call a function and then it gave you some value back but what if you're creating an app where you want to continuously listen to users input and you know listen if the user changed their name or not how would you do that in future you cannot because you don't know when the user will update the name so that you can send a request to it right so that's where streams come in and stream you send a request similar to future but not very similar to future why because this is not a request it's a request to subscribe basically you're subscribing to an event over here and that event is basically telling you hey just keep giving me updates it's like a YouTube channel only right if you subscribe to my channel you'll keep getting updates about my videos about you know Community posts and stuff over here if you subscribe to an event you get updates related to that event so you just have values returned like this all right so let's say the first time user changes name from revant Revan R thenawat so this is where you would use stream you cannot possibly use future in this scenario why because you don't know when the user will end change the name if the user changes name then only I will send a request so that I get the updated value so let's see a code example for this a nice example I can think of is a countdown app so let's create void countdown and I can just have let's say a for Loop where I say for enter is equal to 5 I is greater than 0 I minus minus and then I will print I all right so what I've done is gone from I is equal to 5 and as long as I is greater than 0 I'm decrementing right it's a 5 4 3 2 1 printing out and then I can just call this function right over here and then when we run it we should be seeing 503 to 1. but as you can see all of them got printed really quick I do not want that what I want is 5 to be present then 4 should come in after while three should come in after a while and so on so in this case I can go ahead and use async star like this whenever I use async star you need to have stream just like when you put async it needs to be a future so in async Star it needs to be a stream like this but if I just do this and run it isn't going to return me anything at all why because well this is a stream so you have a stream of void and why would you call anything like this right if you have a stream it basically means it's going to return something why would you have a stream that doesn't return anything that doesn't make sense so to return something from the stream what can I do I can just have return I like this will that work no because this return will only work when you have future or integer or whatever type is there but it won't work with streams in stream instead of read on you need to have yield why is the yield written over here well that's because if you search the meaning of yield it will tell you to produce or provide that means it is providing me with a value I every single time and then if you are returning a value it makes much more sense if we just have integer where and then if I try to print it will it print anything no I can tell you this because we've not printed anywhere how will you print it you're just returning a value from your your basically providing a value from here but you're not required printing it so should I go ahead and print this function will that work if you've guessed no then perfect because you've understood it you've understood that it's going to return stream of integer that means it's going to return instance of something and that is controller stream integer it's not quite returning me a string so for it to return stream we have to probably access some values returned over here so we can just have countdown Dot and that gives us a bunch of values that are related to controller stream so we have first which gives us the first value and in our first value we should be getting five so let's go ahead and try it out so we have print like this and then when we try to run it it's going to return to us an instance of future end why because if you hover over this this returns to us a future so what can I do well I can just use a weight over here and I should be seeing five now right because it gives me a future integer I awaited it so it gives me an integer perfect but I don't want the first value I want all the values to be printed so I'll have to find another method and you can keep scrolling and you'll find some methods we can't use as broadcast as empty because those are Boolean values we know we want an integer returning listener kind of thing so we can just keep on searching for it so we have async map we have drain we have all of these functions but the one I'm listening for is listen right now this listen function gives us stream subscription what is the same stream subscription thing this stream subscription is a listener on stream and can save a reference to the streams subscription this allows us to pause resume or cancel the flow of data they receive this stream subscription also has multiple hand loss over here these things right here are called handlers it gives us on data Handler so whenever you have data listening you get well a function we can use to handle the data the incoming data then we have a function on error Handler so if there is an error what should we do on done Handler where it says if we are done with this team what should we do that means we've got all the values from five to one and the C stream value has stopped what should I do in that case so that's what ondan is for and cancel on error so if there's an error should we cancel or should we not cancel by cancel I mean should the stream continue or should it just stop so let's go ahead and first let's just pass in the on data Handler and as you can see on error on done and cancel on error are in named arguments but on data is not a named argument so I can just go ahead and create something like this and since it's a function I need to put in a function but that's not it why because this is function integer on data so it's giving me an integer over here so let's have value over here and then we can print value like this and then we should be done because this value will be an integer correct now if I run it I get 503 to 1 instantly so it's no different from five print statements that we have put so to make a difference what we are going to do is use await future dot delayed seconds one so I'm just going to put a dealer once again so that the values keep coming after some time and if you're wondering hey everyone how can you use a weight away isn't this an async star function or isn't this function marked as async star well you're right this is marked as using star but as you can see we have used async wire and async star is a special type of async you can say so we can use a weight with async star as well and here it's giving us an error because it expects a duration and I've put seconds one so I need to put the oration then seconds one a small mistake right there and then we should be able to run it and we see five four three two one and we're done so as you can see stream gave us this output and this was really cool and for fun what I'm going to do here is also have on done but on done cannot be just like this because this is a named argument and you might ask why is this a named argument couldn't they just put everything as positional argument and you're right but it can cause a lot of confusion because well this is function on data then you have function again then you have function again then you have Boolean value so it can cause a little bit of confusion with all these three functions over here so if the first one is on data and then all of them as named arguments all right now we can also have on error over here so let's have on error now you might wonder why are these two things over here as named arguments and these two things named arguments are there because if we don't want on error to be present we can't just pass in all right so if I just skip it yeah I'm done with on error I don't want to have any Handler on it I just want there to be an a Handler on done all right so I'll just have it like this and I've correctly defined it let's have another print statement here and it says hey I completed it and then when I run it I get five four three two one hey I completed it right what if I put a print statement after this I just print Highway and then I run it what will I get in that case I get high instantly why because it's an asynchronous generator stream is an asynchronous generator that means it printed this thing first and then you know it continued with its own thing so this was about the basic of stream there's much more you can do with stream for example stream gives us a bunch of options that we can have for example we can have return stream Dot and as you can see stream gives us a bunch of things we can ask stream.periodic which is like future dot delayed but a bit different why because stream dot periodic is basically like hey in every one second you're just going to put that out so we are just going to have stream dot periodic and now you'll say hey why are we getting an error over here as I told you before when you have stream you cannot have return but that was slightly incorrect why it's not because of the stream that I can order it on it's because of this async star that I cannot return so if I just remove this async star I get to use return because then I'm just returning a stream right I'm finally returning the stream what it wants but if I have async style it's basically telling hey you've already converted this to a stream then you're again trying to return a stream that doesn't make sense to me so whenever you have async star you need to use yield you cannot use ret on but when you remove it you can return but it needs to return a stream just like you know anything else if you have integer past and over here instead of streaming we need to pass an integer right so that way now in periodic what do we want we want a duration we want a computation just like we had for future.dealate but this is going to be a bit different why because we are going to have seconds one and then in our computation I'm going to return 1 let's say and it's giving me this error because we are getting some value here all right now instead of returning one we can just return the value and let's run it and see what we get so we get 0 1 2 3 4 5 but I didn't stop here because you have not set any constraints and it's just returning to me periodically after every one second the value and this value is basically like hey we are calling this once we are calling the second time we are calling this function third time we are calling this function fourth time and it will keep on returning so that's what a stream is and this is what stream dot periodic is now of course a valid question over here is driven how do I stop and to be honest I'm not sure there might be a way to stop this but I'm not very sure about it because there's another approach I would take to stop it and that's using a controller so as of now I'm just going to restart the dot pad so that the console you know stops its work and I can just focus on my coding and right now the other way I was talking about is creating something known as a stream controller what is a stream controller well let's break the word down we have stream controller this is basically a controller of a stream so with this controller you can automatically create a stream you can add the values to the stream for example I can just use the stream controller and add values from any function I want but yeah this stream controllers instance should be passed down I'll give you an example for it a really nice example but for now stream controller is basically a thing that can control your stream by providing methods to add some values to a stream cancel the stream pause the stream whatever just like we have stream controller on this you know the instance of stream controller via this so that allows us to do whatever we want now I can just have final controller which is equal to stream controller and I'm just going to go ahead and instantiate this but the stream controller is not defined it's saying that why because the steam controller is not manually present here we need to import a dart library a library that was created by Dart themselves a package you can say so we can have import dot async right here okay so it's coming from dot themselves and when we have dot async we get access to stream controller now we can use this controller to have the properties we want so it can be controller Dot and as you can see it has multiple options dot done dot has listener so this is also a Boolean value is closed is also there is post is also there on canceled so what happens when you cancel the stream or the stream has been canceled on listen so we already know it's similar to this on listen function but the difference is this listen values listen for any error or it listens for any value but this on listen is basically called whenever the stream as is listened to right it's started listening to so we have on pause so what to do if the stream gets paused on on resume sync now this is a new concept and a very important one stream which is basically returning us a stream of this and as you can see it returns to us a stream of dynamic instead of a stream of integer which is what I want why because the stream controller requires a generic type to be mentioned over here we've already seen that we can pass generic operators or generic types to a class and that's exactly what stream controller wants over here otherwise how will it know what is the stream off and now if you come over here this is now the type stream integer so when you do dot stream it gives you a stream value from this controller then you have a bunch of other properties but we have sync aware what is this thing this sync gives us a bunch of properties or a bunch of functions you can see it gives us ad which allows us to add a particular value to this stream add error which allows us to add any error if we want we can add another stream over here we can close this string so we stop listening to everything we can convert it to a string and we have done it will give you a complete value all right so if you have controller.sing dot add let's say a value one a value 2 a value 3 a value 4 and a value five done will just give us a future of that value so the entire thing that we get the bunch of values that we get we will get them in this future Dynamic get done so anyways let's get back to sync and I just want to add a value to this thing which will be one and now if I just have controller dot I again get a bunch of properties on this and what I want to do here is controller Dot stream so I just want to get access to stream and then I want to listen to it and this will give me some value I can just print it and I'll have the value printed out like this and it's not on listen it's just listen don't confuse that on listen is called whenever you know you start listening to a stream but yeah you want to listen so you'll have this and then when we run it we should have two streams that are going on this one is one all right so this is this team's work and then we have zero one two three four five six seven eight nine that will continuously keep moving so this was controller now there's so much more you can do with the controller let's remove the stream completely and let's call countdown where obviously and we're just going to put void over here we don't want to do anything fancy we have a stream controller we are just going to be satisfied with it now I can just have more values added over here so I'll have at two three four five and now if I run it again I see one two three four five right yeah great instead of just adding some values over here what I'm going to do is add an error as well so I'll have ADD error like this and then I'm going to return an error and the error can be a string because it allows me to add an object and then it should say hey error that's our error message quite good now if I return it you see we get one two three or five and then an uncaught error hey error to resolve this we can add on error property over here which gives us error and now I can just print the error right over here cool so if I run it I should be seeing here or right here perfect so with this controller I get more access to it I can add errors I can add values I can do bunch of stuff over here for example I can also do controller dot sync Dot and then I can add another stream I can close it so if I just close it will the error get printed let's see so if I run it we get uncut error cannot add event after closing so as you could see even though we closed we are adding an error that's why it gave us this exception so to resolve it we can either put it this in a try and catch block that would work as well or you can just resolve your error and that's done but yeah one thing I like to mention that whenever you're done adding values it's always good to close your stream controllers sync surveyor also make sure to close your stream so you will have controller Dot close so make sure to close the controller as well and close the sync as well it's always a good thing to do so so this was about streams there are lots and lots of things in streams as well but I'm not covering all of them because I just wanted to let you know the basics and other stuff is not generally used by 99 of the developers only the one percent user for example there's stream Transformer I have not never used it in any of the app I've built for myself or for client so I don't know why you would use it and I don't want to confuse you any further whenever you want to use it you'll definitely know by yourself we can also create records on our own so to create a record we just create a normal variable then set it equal to the normal parent thesis which is the standard type for a record then we pass in the values so we have 4.5 for a double a string and then a Boolean and integer value now if we just try to print this record and run it we get the correct values and we can access them using dot dollar one dollar two dollar three dollar four one thing to note is that these records are immutable and these dollar two dollar one dollar three dollar four that we are getting are Getters and the records don't have any setups because they are immutable so that just means we cannot do records dot dollar to equal to some value because the error message says the setter is undefined so we only have a getter other than this we can also Define named Arguments for these records so we can just have greeting here and let's say is adult year if we print it we get that and if we go to records we get double an integer which is 4.5 and 2 then the named arguments and if we do records dot we see dollar one and dollar two which stands for 4.5 and 2. greeting and then is adult also these records are type 6 that means if I change this to VAR and then do records equal to let's say 2.0 then I pass in false then I say greeting is high and if adult is false then here I get an error the reason for this is I've passed the correct data type at first which is double but then I've passed in a Boolean value it shouldn't be a Boolean value it should actually be an integer so if I pass in an integer the error goes away which means it's type safe just like other variables in dot we can also make these records nullable so if we just Define it like this double and integer then we put a question mark just to show that it's nullable and then give it a name so let's pass a name equal to 4.5 to then print the name then I set name is equal to null and then print name again let's see what we get so you see for at first we get 4.5 comma 2 and then we get null and the last thing that I want to show you in records is the equality of Records so if we have a record that looks like this int and end then has the variable name of point and that is equal to one two three for x y z respectively and then if we have another record that is similar to the first record but instead of having X here we have a and here since this one was a this will be a as well instead of X and everything else is similar and then if we do point is equal to color you see we get an error this is because Dart considers both of these variables different from each other for a record to be equal to another record all the fields should be matching here so if I just change this back to X and then I'll have to change this to X as well now we see point is equal to color you can however change the values over here so we have 5 10 and let's say 12 you can do that but these arguments should be the same for both of them to be comparable or assignable together records are real values you can store them in variables pass them to and from functions and store them in lists there's more to patterns so suppose we have a list like this so to get access to these elements what we do is list a 0 or let's start one or let's start 2. but with records that's not necessary what we can do here is just put a comma B comma C inside a square bracket just imitating this list and set it equal to this list so let's see what we get here we can print it out like this and we see one two and three but what if we have more elements than just one two three what if we have four five six seven eight nine as well now if we try to run it we are going to get an error right because we have nine elements and we are just assigning to three of them to resolve this error what we can do is just tab dot dot dot at the end now if we have that the error is resolved and ABC contain the value 1 2 3. and the rest are contained in these three dots but what if I want four five six seven eight nine as a separate independent array we can get that as well by just doing D putting a d after these three dots and then having dollar D like this now if I run this we have 1 2 3 which is ABC and D is a separate array because dot dot dot gave it access to the remaining elements and obviously if the second element here doesn't matter to you you can put an underscore so it will neglect that value and this underscore isn't a variable so if you just try to do underscore it will come undefined now what if instead of a list we have access to a Json or a map so if we have access to this we are used to printing the values like this Json user ID then running it and then we get the user ID with Dot 3 this can become much more simpler with Dot 3 what you can do is just have final followed by user ID then the name of the variable let's call it user ID again title and then again pass in the name of the variable so we have title and set it equal to Json now if we try to print user ID and title let's see what we get and as as expected we get the user ID as one and the title as this thing right here so we have destructured this successfully as well we have a map we've passed in the field name over here then assigned a variable name to this which is user ID then we can use this user ID anywhere we want then we have title and then we've assigned a variable name to it as well and passed it over here if you want to do it for body you can again pass body year and whatever the name should be let's call it B and you can pass print B to it and run it and you'll get the desired output doing stuff like this can often be error prone so for this it's recommended to put an if condition and to follow the syntax there's a special type of if condition that was introduced in Dot 3. so if you have if Json which is the name of the map that we have used to get our values case which is now a keyword then this part right here the map the mapping that we have done if this is the case then it means we are successful with our mapping and here you will see we are getting errors the reason for that is we have not put final year and we cannot put that in an if condition so here what we can do is pass string user ID string title and string B this will actually be an integer but let's see what we get if we put string over here and obviously we'll just print stuff out here so let's copy it paste it then you have an else condition and in the else condition let's just remove this we are going to print out stuff again all right so let's try to run it and see what we get and you see we are getting incorrect Json now why is that the case because we've passed in a string over here and the value retrieved is not string it means that user ID is now having a type of its own which is a good thing so we can just pass in an integer run it again and we get the correct output so just revisiting this if condition again we just need to put a name of the map we are using to get the values from in our case Json case and if the case is this that means user ID is there which is integer title which is string title and body which is string body then it's the correct thing and then we print it otherwise it's incorrect Json and if you mention the wrong type we are going to get incorrect Json this if condition can also be Rewritten in switch so let's try to write it if you have switch Json and case is just like this the same thing here so we have user ID and user ID title string title body string B then we are just going to print these stuff out otherwise we have incorrect Json again so let's remove the fifth condition now and run this we get the same output again and again if you misspell anything or do anything wrong here you'll get incorrect Json now let's try to get elements of a class so this is a human class we have the human has name and age and here and in the main function we are creating an instance of human class and printing its name and age and then when we try to run it we get nice name and two as the name and age that's how we did in Dot 3 and before but with pattern matching what you can do is final human then pass the name of the fields your name age with a colon before them equal to Human and now you can print name and try to run it and you'll get access to nice name and similarly for age so this is pattern matching in dot for class related stuff so here you need to mention the name of the class followed by a collinear then the name of the field again colon then the name of the field again which is equal to Human and you can also pass a geode name your then try to run it and we still get the correct output but if you misspell this like this suppose name is nimi and then you try to run it you get a compile time error of course that neem isn't defined for the type human since your class name is human and there's no property of name here you cannot use me so you need to pass name here and if you're wondering why we need to put this colon before the name that's because we want it to rename for example if this is the age property and we want to use AG like this you can use this or if you want name property and want to call it something else so let's call it something else and then try to print it you'll be able to use both of these values it's kind of like mapping and it works so the field is age and you're using the variable name AG or you have the field name name and then you're using something else but if you want to go ahead with the default one you can just go ahead by putting colon at the end or at the start sorry so now I have a different example with me I have a list of items with the elements high and man then I have a switch case where list of items has the case of high and man exactly what we have here and if that's the case then you're printing dual if you're in dot 2 and try to run it you see we don't get anything now if I switch to Dot 3 and then try to run it you see we are getting access to do that means it's able to recognize switch case conditions properly and we can do this for records for maps or whatever we want another cool thing we can do here is check for two different elements in a single list so I can just check here putting an or sign saying if high is this or high is this and man is there in the list if that's the case then we are going to print dude then I'll try to run it and we get the same output so that means if I put high in the list of items and then try to run it I get do it again so we can put all conditions here how it's working is basically if the first element is either high or high and the second element is man or you can also put auror man like this or any other thing you want it will work another cool thing you can do with switch cases in Dot 3 is just put event guard here so when and suppose we have in index is equal to 2 and when index is equally equal to 2 then only it should print dude so when you try to run it it spits out dude so what's happening here is we are checking for the or conditions and the entire list then we are checking when index is 2 then only print dude otherwise we can put a default condition print and let's shift index to 1 then try to run it and you see we get since index is 1 and index is not equal to 2 so it went to the default condition because this case did not match so this is extra Edition guard that you can add to your switch cases another cool thing you can do with switch cases now is use them to assign variables or use them in flutter itself in the UI code so just to demonstrate it to you I'm going to create two variables page is equal to 0 last page is equal to 1 and then I'm going to have a text where I'm going to use switch case so I'm going to have switch then I'm going to pass in page then after the brace we don't need to put the case keyword here instead we can just match the conditions so we have 0 which will be returning let's say click here and then one which says click me and then underscore which means the default case so you don't have to write default like this you can just have underscore and then we can write none and there we are so if you switch keys inside of a variable just to assign it a value now if I try to print text and then run it you see I get click here which means I'm getting the condition executed when it was 0. now if I try to use last page I can run it I get click me now I can also add a when condition if I want Salah when and then if I try to run it I get none because the last page is one but page is not equal to last page so I get the default case executed now if I just make page and last page both one then try to run it I get click me so I have a problem with DOT now if I have let's say a string and that string is let's say motivation and that motivation string just says this is a good word and now what you want to do is in this motivation capitalize this T and keep rest of the string as it is so I just want this to convert it like this this is a good word so I wanted to be like this now it's easy to change right I can just do motivation is equal to motivation at zero so it catches the T and then I can call a method on this called to uppercase so that means it will convert it to an upper case so this T will get converted to a capitalized t but if I just set it to this much my motivation will become a capitalized T rest of the things will disappear I do not want that so I'll have to add rest of the string to this how can I add rest of the string over here we already know about substring right so substring helps us to get certain parts of the string so definitely substring will help us over here as well so I can just do motivation Dot substring and then I have to provide a starting value and an optional end value so my starting value is going to be one because substring starts from zero but I've already passed in the value of 0 which is a capitalized T and I want rest of this thing so I'm going to start my substring from one so it will include H and the rest of this thing and if we don't mention the end it will go till the end of the string right so this is my motivation and I can just go ahead and print motivation over here and if I do this much I get this is a good World exactly the way I want it but if I have hundreds of other functions and everywhere I want this format for my strings so if I have my name passed in like this I want my name to be written like this all right the first part should be capitalized now I can't keep taking this thing over here copying it and putting it on all the strings how can I do something that will make sure that I have a function on the string present itself so I have a function present on this string like we have two uppercase now that seems impossible right because this all function to uppercase substring is created by dot itself if it is created by dot it says how can I change it I'll have to go to the dot source code and change it and obviously dot won't accept my changes just because I want it in my code that's why Dart has made this very easy for us in my code I can have something known as extensions with extension I can specify some code or some function which will get added to the string let's see an example I'll have extension capitalize first letter on string so this is a Syntax for an extension you have the extension keyword just name the extension the extension name doesn't really matter but just so that you can find it later on and it's easy for you to debug your programs after you write the code just name it something good and this should be Pascal case as well then you have the on keyword so it says that this extension and all the methods that you are going to provide in this extension are going to be available on what type so I've passed in a string you can also have an integer so that you can use it on Integer or on some other types you already know more about it and then I'm going to have a function created like a normal function so I'll have string capitalize first letter then I can just copy this thing from here paste it return it but I get an error over here the error says that motivation is not defined and rightly so motivation is defined in this function not over here how can I access the value that we get on the string so for that we have access to the this keyword so we just replace motivation with this this gives us access to the word or the string on which we are calling this method so we have this at 0 to uppercase then this dot substring which gives us a warning saying unnecessary qualifier so you can just remove it and put substring and that works as well and now if I just do motivation is equal to motivation Dot you'll see we get access to capitalize first letter function earlier this was not present on string but from now on this will be present on every string we create not just motivation so if we just do this and run we should be seeing the same output and we see that but now if I just create another string let's call it rivon like this and then we have name is equal to name dot we again get access to capitalize first letter which just shows that this function that we created is accessible on every string we create and that's very useful for me so you can create multiple methods in this and you can create multiple extensions as well this is a great way to reuse your code and reduce the complexity of your program I personally like this feature a lot and use it wherever I can we will use all of the dot knowledge we have till now and that will help us quite a lot now let's get started by installing flutter so to install flutter you need to make sure you're on this website flutter.dev then you can click on docs install flutter and then you'll see a bunch of options to select the operating system on which you want to install flutter so if you're on Windows or Linux you can click either of them and if you're on Mac you can click on Mac OS now I won't be able to cover the windows and Linux installation processes because I don't have either of those systems however there's one thing I'd like to mention that if you just click over here you'll get the entire installation process and most of it is similar to the installation process on Mac OS so we need to get the flutter SDK we need to do the Android setup and if there's anything we can do the Windows setup as well but one thing you need to do additional is install git if you haven't already so for flutter you need to have get pre-installed in your system so you can click on open a new tab and download the git installer from here depending on your system you can either install this 32-bit or this which is 64-bit after you have the installer you can double click on it and run it then follow all the processes the wizard gives you and then you'll have get installed in your system to check if it is installed or not you can go to your system and just type get if you see something like this it means get is installed if it isn't then you haven't installed it properly you need to make sure that it's installed properly all right so let's clear this off and one last thing to mention over here is when you have the Windows installation process you cannot do iOS setup because you cannot build apps for iOS from a Windows machine you can only build apps for Android web and windows from a Windows operating system you can build for Android web and Linux from a Linux operating system but you cannot build for iOS or Mac OS from Windows or Linux so that's a point to know that's why if you see a wire you don't have IOS setup written over here however if you come to Windows or Mac OS installation you'll see iOS setup here we have xcode which already includes git which means we don't have to install git separately on Mac alright you can see it away flutter users get for installation and upgrade we recommend installing xcode which includes get but you can also you install git separately all right so we are just going to install it with xcode I already have it installed it doesn't make any difference but if you don't have git installed we'll install it when we install xq so now let's dive into this so the first part is to get the flutter SDK so to get the flutter SDK depending on what Mac you have Intel Mac or apple silicon Mac you can select either of these buttons since I'm on an M1 chip I'm just going to click over here and it will start the installation process for me on Windows also the first part is to get the flutter SDK you'll get only one button to install the flutter SDK on Windows after that you need to extract the file in the desired location so you need to make sure one particular folder where you can install it for me I already know where I want to do it so if I go to found finder press command shift G then just a forward slash so I go to Macintosh HD put it in a grid format so that it's better to see where I want to install Shredder is users Revan ranavat and over here all right so from the root of my laptop I want to go to users everyone ranavat and here I'll have the flutter folder or extract so once the installation is complete which I think is complete I'll drag it over here so I'll just open a new finder which has downloads I'll have flutter over here I'll drag it over here in my wander on our folder and there we have flutter right here cool now the next step is to add the flutter tool to our path now we can just copy this Command put it in the terminal and run it and then we'll be able to use flutter specific commands like flutter doctor but now you can see flutter command is not found because I've not run this command and if I run this command meaning I add flutter tool to my path then run it so it will locate flutter doctor so it will know what flutter command is but when I exit the terminal reopen the terminal again it will forget the flutter command because it only sets the path for the current terminal window it doesn't set it for the entire terminal or for the entire system it only does for one window so to permanently add it we have to click a wire which is permanently updating a path and follow the steps written over here so the first step is to determine the path of our clone of the flutter SDK so we already know where it is from the root of our folder we need to go to the users flutter bin so this is our path all right then we need to open or create the RC file for your shell then we need to type this command in the terminal so let's go ahead and copy it so we have slash bin slash zsh typing this command gives us access to what shell we are using are we using bash or are we using search shell since it gives us the output as zsh it means we are using Z shell so I need to edit this part right here okay so I'll just copy it then over here I'm going to type Vim which is kind of like a code editor so if I just put Vim like this I'll be able to edit out zshrc file right here in the Vim code editor I can also type Nano instead of Vim followed by dollar home slash dot Zs HRC and that will open it in Nano but I'm more comfortable with whim so I'm going to go ahead and use it now the final step is to copy this line and paste it over here so here we need to mention the path of the flutter get directory where is it it's in users so we can backspace over here but when I try to backspace you see I just go in the left hand side it's not actually deleting anything so to delete it we have to press X so it will start erasing stuff then you can backspace everything and paste this line right here all right so we have export path is equal to double inverted comma dollar path colon slash user slash this is where we have stored right slash user slash flutter slash bin all right then that's pretty much it now we can press enter then we can have colon W click on enter that saves the file then we'll have colon queue a and we exert them like this now if we run the command again you'll see we have this line written right over here that's good so it has saved it successfully and we have successfully added it to our path as well now we need to run this command so that we refresh the current window to see our you know changes if flutter command is working or not or we can just open a new terminal window so I'm just going to close this I'm going to create a new terminal and then I need to run this command to verify that the flutter path flutter bin directory is now in our path so we can run this and we see users rewind out flutter bin that's great now I can clear this off now I need to verify if the flutter command is working or not so I'll copy this paste it over here and there we go this gives us the location of our flutter folder this is where it's located right users flutter bin flutter right this thing right here so we have successfully installed flutter to our system if you are on Windows after updating your path which as mentioned in the documentation you should be able to run which flutter command and see the correct output if you do that means flutter installed successfully now we can just run the flutter doctor command which gives us a list of things now that we need to focus on and flutter doctor gives me a list of things so it's kind of like a real doctor it tells you what all is not there what all is missing and this is what you need to do so Shredder is installed we are on 3.10.5 which is the latest version as of June 21. now the next step is to install Android related stuff you can see that over here android setup then we need to work on xcode so we develop for iOS and Mac OS and after that you know we are basically done with everything Android Studio is related to Android related stuff so we'll have all of those working so let's get to the Android setup not wasting any more time and just start installing Android Studio as well so Android Studio is helping us to build native Android applications so you can use Scotland or Java and start preparing your apps in Android Studio as well so we need to install this as well so we'll just open it in a new tab and we'll click on download Android Studio we have read the terms and conditions and we have the Apple chip so we'll select that now we'll wait for Android Studio to install properly and after that we need to start Android Studio go through the Android setup wizard this will install the latest Android SDK Android SDK command line tools and Android SDK build tools which are required by the flutter When developing for Android so after we do all of that we again run flutter doctor and we see if there's a tick mark over here because we've installed Android Studio so Android Studio is installed successfully let's double click on this TMG file let's transfer it to Applications and Android Studio is transferred to applications now we can also put this installer in bin if you want you can also go ahead and put this in bin which is another installer then we can go to Applications let's go to Android Studio double click over here then it asks us if it is downloaded from internet and if we trust it so you just click on open again we are not going to import any Android Studio settings so we'll just click on OK maybe we can send usage statistics to Google we can click on next choose the type of setup you want for Android so we have not installed anything earlier so we'll just go ahead with the standard one we'll click on next select the UI theme you want let's go ahead with docula then these are the extra things that will install emulator build tools all of that stuff we'll click on next then live sensors for everything we'll click on accept we'll come over here except for this one as well then we'll click on finish it will start downloading the components for this so all the components have now been installed we can click on finish and we have Android studio right here we don't want to do anything with that we are just going to close it we'll close this as well now let's again run flutter doctor and see if there's anything we're missing now as you can see over here Android Studio is already installed now so that was successful Now Android related stuff two things are required we need the command line tools component so for that we are again going to run Android Studio then we are going to go to more actions SDK manager then you're going to search for SDK tools then we have Android SDK command line tools right here we'll click over there and then click on OK click on okay over here that will install it and we are done so we can close this let's again run flutter doctor command and you see that issue is resolved now we now only need to accept the Android licenses that we haven't so we can run this command and it will do that we just need to put it in the same line and run it and then it works all right so yeah we'll review the licenses that have not been accepted then we'll click yes yes yes and there we go so we have accepted all the licenses so I hope everything is working fine for Android now so we'll run flutter doctor and everything related to Android is also fixed now now the last step is xcode developed for iOS and Mac OS so the final step that's required is for xcode so we need to develop for iOS and Mac OS we can do that by going to the App Store and installing xcode or just going to the web download I'll go to the App Store and install it so I'll wait for xcode to install and then we can focus on the stuff that's mentioned later on so I'll see you when xcode is installed completely on the system all right so xcode has installed on our system I'll just click on open here so we like to build for Mac OS and iOS so I'm just going to click on install here I'll have to enter my password and then it will start installing additional components after that we need to configure the xcode command lines tools to use the newly installed version of xcode so we can just copy this line then click on enter again we'll have to enter a password over here and we are done then we can again run this command paste it so this is great I think we've configured xcode for now one last command is left which is this pseudo xcode build license we'll press space for more and then we just need to type agree to say that we are agreeing and we are done now we can clear this off run flutter doctor and see if it is done properly or not so one issue from xcode is gone now we just need to install cocoapod which is not installed so to install it we can just go to their guide the link that is mentioned over here paste it and to install Coco pod we just need to run this command sudogem install cocoapods so we have installed Coco pods now we can again run the flutterdoctor command and as you can see no issues found that means the entire flutter installation is successful so if you've covered this part and everything works fine it's all good now the last step is to install vs code so if you just type in vs code install you'll see this website code.visualstudio.com so this is basically our code editor this is where we are going to write our code type it all out in the dart course we had used dotpad.dev now we don't need to use that anymore we're going to write on our system only so we are going to use our PC and here we have Visual Studio code that will help us to you know debug write a code it will help us and basically everything so you can install it according to your platform again I'm just going to go ahead with the Apple silicon zip file and it will start installing it for me after I have vs code installed I'll just start creating a flutter project and we'll create a first app that is the currency converter app so vs code is now installed you can see it in downloads I'm just going to click on the small search icon over here so it shows that Visual Studio code is in the download I'm just going to drag this to the applications tab because vs code is an application then double click on it then click on open and we have vs code right here I'm going to browse the color themes and select which one I prefer I don't prefer the dark high contrast it looks very weird in my opinion obviously not light modern color we can use this one or you can go ahead look for more themes so now that we have Visual Studio code installed let's go ahead and open it so I'll have Visual Studio code Type like this and open it so we see a welcome tab over here we can close this welcome Tab and explore what all is there in the vs code tab as of now there's no project here so it looks very empty but we'll create a flutter project open at nvs code and that will look much better but as of now let's just take a look at the blank and mtvs code so the first tab that we have here is the Explorer tab the Explorer tab helps us to view the files and the subfolders present in a folder so if we have a flutter project it will have many folders and files of our application we can see all of them over here the second one is the search tab in the search tab you can find a specific word from multiple files and multiple folders so if you want to search just one word or just one function name you can type it over here and it will output all the files that contain that function name then we have the source control tab remember git that we installed this is not the tab we are going to look at because that's a separate world of its own I'll be releasing a separate tutorial on Source control with get so you don't have to worry about it for now the next one is run on debug this is a place where you can run and debug your applications and the final tab we see here is the extensions tab the extensions tab allow us to add additional features to our code editor so we'll be installing a bunch of extensions so that our flutter code looks better and we have an increased productivity in our coding but for now I'm not going to install anything I'll install all of the extensions one by one so that you see the difference of using an extension and not using an extension then here we have the errors and warnings tab so it tells us what errors and warnings there are and when you click on it it opens a separate window of its own here we see problems so it will output any problems that are present in our App application so it can be a warning or an error so in dot pad you remember how we saw warnings that a variable was induced or an error which said like when we had print statement and we put in two to three arguments it said you cannot pass two to three arguments to a print function all those kind of Errors can be seen from here in one particular place then we have output so it will output anything we want then we have debug console so whenever you run your application all the print statements and everything can be seen over here how is output different from debug console then output will basically tell you more about the project as a whole for example whenever you add an external dependency so remember in our DOT code we add but an HTTP dependency where whenever we add it to our flutter project it will show all the dependencies present in our application in the output here and debug console basically tells us what is happening when we are running the application then we have the terminal so this is an inbuilt terminal this terminal that we had right over here that is an external terminal meaning it is coming from the system itself this is coming from vs code so we can eliminate using this terminal right here and we can just start using integrated terminal all the time that makes sense and you can add as many terminals as you want by clicking on the plus button over here and delete whenever you want to delete it then if you close the closed tab it will just close this window right here then we have the feedback option and the notifications tab over here so we can come back to Explorer now the next step is to create a flutter project and the first project that we are going to create is a currency converter application so to create a flutter project there are again two steps you can take you can open up your terminal from your or from the vs code terminal now to open vs codes integrated terminal you can press command J if you're on Mac and that will open the terminal right over here okay and you can again press command J to hide it or you can just use the terminal over here both of them work Now to create a Florida project first you need to go to the folder where you want to create a flutter project I want to go to the desktop folder because that's where I want to create a flutter project and after that I'll run the command flutter create and then the name of the project which is currency converter so this will create a flood up project by the name of currency converter and then when I click on enter it creates a project please note that when you have flutter create you need to put underscore over here in case you want to put a space because if you just put a space it won't be allowed it will give you an error you can try it for your own and camel casing is generally not the convention to name a flood a project it is generally named like this so if you have a space you just use an underscore just like the Instagram usernames now we can just take this folder and drag it over here and there we go we have everything related to a flutter project here and as you can see there are multiple folders over here you can see that in vs code as well but there are a few things more that you can see in vs code which is dot dot tool which you cannot see it over here and Dot idea which again you cannot see it over here to see it you can just press command shift full stop and you'll see all the hidden files over here and again press command shift full stop so you'll stop seeing the hidden files so vs code helps us see the hidden files as well now let's go over the folders one by one so dot tool and Dot idea is nothing that we should be concerned about we should be concerned about folders starting from here so we have Android folder so it's related to all the Android permissions that might require so whenever you have an app that wants some permission from Android related stuff you'll use this folder and it basically has the entire structure of an Android application a native Android application right here then we have the iOS folder this has the structure similar to an iOS folder whenever you want to give any extra permission you'll have to open this iOS folder in xcode and you can give your permissions that are required then we have the lip folder the most important folder in our flutter project this is where you're going to write all your Dart code and here we have just one file which is the main dot dot file and as you can see this might look familiar void Main function and this has a dot dot extension which basically means that this is a dart file and if this is a DOT file we already know main function is where the application begins so this is the starting point of our app and the lib folder is where you're going to install or you know add more of your files and build your entire application then we have the Linux Mac OS folder similar to the Android and iOS folder if you want to give any permissions you'll give them over here for Linux and Mac OS then we add the test folder test folder is related to the testing of our app by testing I do not mean like a normal user testing it you know when a user uses their phone and uses the app that's not called testing I'm talking about automated testing meaning you just write a bunch of code so that you confirm that this piece of code is working it won't make sense now but after you've built a few applications you'll understand what I'm talking about then we have the web folder web folder contains all the assets the index.html file basically the entire web structure then we have the windows as well then we have get ignore which is related to Source control so whenever you have to upload to something known as GitHub you'll need this get ignore files which ignores all the unnecessary files in our project then we have metadata and as you can see it already tells us this file tracks properties of this flutter project it's nothing we should be concerned about so we can just skip this part then we have analysis options dot yianl you remember the warnings and errors we used to get we can configure such that we get more specific errors or warnings in our Florida project then we have currency converter dot IML nothing we should be concerned about then we have pubspec.log and pubspec.yaml so pubspect.aml consists of all the details of our flutter project for example the name of the project the description of the project then this line which is related to pub.dev you remember the site where we went to install HTTP plugin so if we create our own dot project and we want to publish it to pub.dev then we need to remove this line if we are only building a flutter app and that is not to be published on pub.dev we can keep this line that we have the version number of a flutter project or the flutter app so if you've ever noticed every application has a version attached to it so if you just click on an app and go to its app info you'll see the version for it for example the WhatsApp version as of now is 2.23.11.77 that's what this version number allows us to do it allows us to upload to App Store Play Store and all the other stores without creating the confusion that two projects are similar or the same so you can have unique versions every time you upload to app store or Play Store then we have environment so this tells us the flutter SDK we'll be using in this project and the hdk we are using is basically greater than or equal to 3.0.5 but less than 4.0.0 so you can use anything from flutter 3 to flutter 4 over here and it will obey all the rules you can also decrease your SDK so you can just put two over here and it can be less than three so it will follow all the rules related to flutter 2 to flutter 3 but obviously you need to make sure that you have fluttered two installed for that but it's always good to stay on the latest SDK not on the previous SDK because you need to keep up with the advancements in your framework right if we have flutter we always need to make sure that we are updated to it so that we can use all its latest features then we add the dependencies tab and in the dependency the first one we have is flutter which is coming from the flutter SDK itself and we have the Cupertino icons the Cupertino icons dependency can be found on pub.dev but it basically allows us to use iOS styled icons Cupertino everywhere in our flutter code is going to relate to the iOS part so if you have Cupertino icons we have IOS style icons then we have Dev dependencies we already know what dependencies are we have already installed a dependency not DOT pad which was the HTTP Plugin or the HTTP package in-depth dependencies we have dependencies related to the developer so if developer needs anything that will help the developer to you know write code and increase productivity they can use that but it doesn't affect the user Behavior at all okay so whatever you have over here is just related to the developer having a better environment and here we have the flutter lens package and the flooded lens package is Con connected to the analysis option.yaml which is our linter you can see include package flutter lens flutter.aml I know this might not make sense but you're just starting right now as we move ahead you'll understand what I'm talking about then we have flutter which says users material design to true then we have something related to assets we'll get into it then we have something related to fonts as well we'll get into it and that's pretty much all about pubspect.yaml possible.lock on the other hand contains all the packages that we might have installed and keeps the track of the version number the description from where it came everything and at last we have the readme.md so if you want anyone to read your project and you know you have certain guidelines to follow you can have a readme aware which tells everything about it and if you click on this icon all of this text away or translate to this this is what dot MD represents MD is short for markdown so whenever you have hashtag like this it thinks this is an H1 kind of title a bigger title then you have a normal text then you have two hashtags which is a smaller header then you have smaller text then you have links and all of that stuff so this basically allows any other engineer working on your project to read more about it and you know understand how to contribute and all of that stuff so we can close this and we have two the entire flutter project now let's go to the main.dot file which is where we are going to be 90 of the times not in the main.f file but in the lip folder in general we can create more dot files we can do more things and 95 percent of the times you're just going to stay in the slip folder and not move out of it because this is where the entire flutter project is cooked so yeah this is where we are main.file now what I want to do is there's a bunch of code written here by default I just want to run it but even before running there are a few things I want to do for example you might not be able to see this font so I just want to increase the font size over here to increase it I am going to press command shift p settings then click on open settings click on text editor over here click on font and here I can increase my font size so my font size can be let's say 20. click on enter come over here and it zoomed in a little bit too much so I think I'm going to go ahead with 18 this is better but what about 70. I think 18 works well for me and I hope you're also able to see this I'm also going to put this panel like this so that my code gets more space and that looks cool now another problem that I have here is the highlighting part by highlighting I mean I just don't want my code Editor to look blue white and just orange you know I want more colors to be present if you look at take a look at dot pad you'll see extension which of the keyword is in green extension name is an orange color on is again a keyword so green a data type so it's in white color again a data types white color function or a variable name is in blue color so I want a similar kind of highlighting to be present so that it's easy for me to distinguish between dot stuff and a lot of stuff all right so for that I can again press command shift p type preferences and I'll find something like color theme over here I just need to click it and change the theme over here so if I change the team to dark Plus you see there is a colored change over here now it's not no longer just white and blue it has multiple colors over here blue is a keyword a class name has green color again this is a keyword widget is a class built as a function so it has all of the proper highlighting that I wanted now the next step is to run the default code that is provided by flutter and just take a look at how flutter looks when it just creates a project for us and we do absolutely nothing so for this how can we run well we can just go to the Run tab run without debugging and it tells us that we don't have an extension for debugging dot should we find a DOT extension in the marketplace you can click over here but I'm just going to click on a cancel because I know what to do it's not the DOT extension that we are looking for we are looking for something related to flutter vs code tells that because we are in a dart file it doesn't know that we are running a flutter related project so we don't need to find a extension specific to dot we need to find an extension specific to flutter so we'll go to the extensions tab over here type flutter click on enter and it gives us the extension flutter which is provided by the dot team or the Google team itself we can just click on install aware and what this will do is basically provide us with a set of tools which will allow us to edit refactor run and debug our applications and when we install the flutter extension another extension that we get by default is the dart extension because flutter included Dot so it only makes sense to include the dart extension as well now we can come over here close this extension go to the main.dot file and you see we have a new bulb icon showing up here then we have run debug profile three buttons right here on the right hand side we have devices showing up where we can select from Mac OS Chrome IO simulator or pixel emulator which is the Android emulator since we installed xcode we got access to iOS simulator since we installed Android Studio it default created the pixel emulator if you don't see pixel emulator over here you can just go ahead and create your own Android emulator all right and if you see an error like this what you need to do is just go to Android studio right here click on more actions virtual device manager and click on create a device select the phone that you want from your let's say pixel 4 XL or let's go ahead with pixel 6 then we click on next we'll use the API 34 the default one if you want to change the API so let's say you want to use Android or Android s whatever you can use that I'm going to go ahead with the API 34 click on next then we have pixel 6 API 34 all the default options if you want you can change the Android advance settings as well where you can change the ram the virtual memory Heap the internal storage so we can change the internal storage to GB and let's say 550 GB whatever you want I'm just kidding you know just half 20 GB like this then click on finish and that creates an emulator for you if you want to run it you can just click on this launch icon or you can just come over here and you'll see the pixel 6 API 34 emulator scene over here and if you want to default remove the default pixel emulator that it created for you you can go ahead and click on these three options delete and it will delete it for you so let's delete it we only want to keep just one emulator over here and if we again go to the devices the device is no longer there there's just pixel 6 API 34. so let's go ahead and run the project so where do we want to run it well we want to run it on let's say Chrome so we'll select the Chrome device over here then we'll click on run and it will start running it for you you see there are a bunch of things that happened here it opened the debug console so it is launching lib slash main.dot on Chrome and debug mode so this tells us a thing about flutter and Dot by default it goes to the lib slash main.dot file to run the project so this is the first file to get executed in after project then we have this settings thing right here it gives us a bunch of settings over here for example if you want to pause the debugging if you want to restart your application if you want to hot reload your application if you want to stop it so if you stop it this thing right here will get executed exited so if you close this you see the web application is now gone so again let's click on run and it will start running it for you and we also have this search icon which is widget inspector page so if you click over here it doesn't start anything right now but again if you click over here it will open the widget inspector widget inspector is a kind of thing that allows you to see how your application is structured but we'll get to it later on because you don't know what widgets are right so let's close this and there we go we have a floss flutter app right here we have this good looking app and this increment button if I click over here it just increases this thing right here so it's a very basic app running on web if you want to run more apps you can do it simultaneously so you can open it and run it on Mac OS so click on run your run without debugging which is another way to run your flutter apps you can either do it over here you can either do it over here or you can just run the command flutter Run Okay so that works as well so let's just click on run over here as well which opens it on Mac OS so we have our application running on Chrome and Mac OS both we can also run three apps in one place so we'll start the iOS simulator first because it's not running in the background like Mac OS and chrome so we'll first have to start the simulator and here we have iPhone 14 pro Max which is given to us by xcode so it's loading right now we can also start our pixel emulator so we'll just click on this start icon right here and that will launch as well and as you can see the Mac OS part is running here if I just expand this this is our Mac OS app and this is our web app both of them look very similar right almost the same that is because of flutter you can run one code base so you have a consistent looking UI design on both your Mac OS app and your Windows app and it works the same way okay nothing is different right here now we also have our pixel emulator and iPhone radio wire so we can run those as well and they'll work side by side as well just make sure you have the current device selected over here so that you launch it over there if I want to run it on iPhone I'll just click on run run without debugging with iPhone selected over here if I want to run pixel I'll select pixel over here and run it so whatever you select over here and when you click over and run over here that device will be run I hope that was clear and if you click over here there are four devices we are connected to and running at the same time if you press command J it opens the terminal you can go to the debug console you have Mac OS over here Chrome right over here pixel 6 loading and iPhone loading as well now I don't like running all of the platforms at the same time because we can lose out on a lot of battery very quickly because we are running on four platforms together what I like to do is run on two platforms at the most so it can be iPhone Android iPhone web depending on where I want to launch it so if I want to build an app only for Android and iOS it makes sense to only use Android and iOS at the same time or if you're sure that it will have a consistent UI design on both Android and iOS there will be no changes you can just run it on one device if you want to launch your app on all the devices or on all the platforms then you can just have maybe a web platform and an iOS simulator running so it really depends on you if you want your battery to get exhausted very quickly you can go ahead and run on all the four platforms there's no problem with it so our iPhone process is almost done you can see xcode well done and it uses the impeller run rendering back-end we'll get into what impeller is but if we just come over here here is our iPhone application and when we click over here we are able to see the same thing that we saw over here and here so we are able to run our app on all the platforms let's get done with the Android one as well it is installing a bunch of things once it completes installing it will start running the application and then we can start designing our currency converter app from scratch and while Android is being run let's take a look at a few more things I want to get into first one is the file explorer tab over here it looks very plain doesn't it what I want here is certain symbols to be present so that I can distinguish between an iOS folder or a lib folder really quickly so for that we have an extension which is called vs code icons there are a bunch of vs code extensions related to file icons but my favorite one is vs code icons which you can click on install and it will bring icons to your file explorer and here you see after you install it it said it asks you to select a file icon theme vs code icons or city which is provided by Visual Studio code itself I want vs code icons because that's better for me I'll come over here and you see all of my folders now have a unique icon to it so we have Android which gives us something similar to Android build iOS so we have Apple logo Linux Mac OS test web windows so everything has a different icon to it so I can distinguish between all of them really quickly and it just helps me overall also I can see that the pixel emulator is now working so I can just come over here and there we go we have our app showing here as well so it looks similar on all the platforms That's The Power of using flutter so now what I'm going to do is exit from almost all the platforms just keep one platform on the side so that I have a perspective of what's going on so I'll close Chrome I'll close Mac OS I'll close pixel as well I'll just keep the iPhone on the side rest all the things are now gone I can also close the Android emulator if I want so I'll just select this click on command Q it will save the state and close the pixel emulator for us awesome now we just have the is simulator here and now we can start preparing our currency converter app so this is where we are going to start writing real flutter and Dot code so to begin our work on the currency converter app what I'm going to do is press command a so that I select everything present in the main.dot file then I'm going to backspace everything and we'll start writing everything from scratch yes we are going to need a lot of components that are already mentioned over here these are sort of boilerplate code meaning if you don't have them your flutter app won't work properly so you need to have them but we'll start writing everything from scratch so that we understand why we need them in the first place for example the stateless widget thing this material app thing all of those things right so let's backspace it then like every DART program we need to create a main function because that's our entry point to the DART program so what happens is flutter just searches for main.dot file in lib folder when it gets main.dart it searches for the main function in the main.dot file and then you can see we get these three options to run our app so now we have a simple dot program with us what we need to do is tell flutter to come into action and start running the app so how can we do that to do that we have a simple function given by the flutter SDK itself which is run up because we want to run the app right so we'll pass and run up over here which is a function coming from some import line like this so as soon as we had run app over here it automatically imported this line right here now what is this line well let's break this down we have import so it's importing some package some file some other project some other folder and that is the flutter package and in Florida package it's the material.dot now you might say hey this line seems very similar to what we had in the dot section we had import package HTTP http.dot this was the case because we were importing http.dot file from HTTP package we are doing the same thing over here but with flutter we are importing the material.dot file from the flutter package if you're curious how we are importing package flutter if you just go to the pubspect.aml file dependencies this is where all the dependencies come in so anything extra your app depends on that is not related to Dot comes in over here so we have the flutter dependency over here and this is coming from SDK philadel unlike Cupertino underscore icons that is coming from pop.dev unlike the HTTP package that was coming from pub.dev this flutter is coming from the SDK flutter and what is this SDK flutter well it's the same thing that you installed on your system locally and it's good to mention SDK flutter like this and not give any path to it because the path of the flutter can change maybe you reinstall it somewhere else so just having SDK flutter like this is a better thing so we can close pubspect.aml file and when we again come over here we can see package flutter is imported and from there we are importing the material.dart file why material.dot file because material.dot file gives us many of flutters functions classes methods that we can use for example the run app file or the run app function because in Dart we don't have anything like run app in Dart we have already seen we have stuff like string and all of that stuff like string integer Boolean async keyword all of this can be used without importing the flutter library or the flutter package but stuff like run app cannot be run without importing flutter all right and to import flutter you need to have flutter installed and you need to make sure that in pulse effect.aml file you have the dependency present so again coming back to run app so this import line right here is quite important and you'll see later on how many times this material.dot is used in your flutter app it's almost used in every single file you create because it also gives you access to certain widgets or certain UI things which is quite helpful so now coming back to the run app function what exactly is this run up function if you just hover over this you'll see the definition of this function it is void run app and then it requires a parameter of widget app so that means an app is not returning anything and it requires something known as widget app and since we don't know what widget is that is not even a dart related thing so that means widget is again something created by flutter team themselves it's a thing in flutter so it might be a custom class that they created but we are still not sure so to understand this what you can do is press command so you can click on run app then and when you click over here you get dive into the flutter source code as you can see over here users Advance are not flutter so I'm going into the flutter SDK that I installed locally on my system to take a look at this definition and understand what this widget thing is and as you can see when I go in the definition when I hover over widget it says that it's an abstract class widget and we already know what abstract classes are again if you want to take a look at the definition of widget you can press command again and then click on widget and you'll dive into the source code of abstract class widget but we are not diving into the flutter source code now I just wanted to show this to you let's not make things complicated so now this requires something known as a widget what is this widget widgets are the building blocks of the user interface they are responsible for describing what the UI should look like so let's take an example of the counter app over here if I want to describe that hey in my app I want the header like this a pink or purple kind of background with some text on it then I want some texts over here then I want a button over here and on that button I want this plus type of icon to be displayed so all of these things are widgets because they describe what my screen what my user interface is going to look like so that's exactly what we want to pass to run app and this widget can be literally any UI component right so I can just put in a text which is again provided by flutter material.dot and you have to instantiate that text text again is a class if you press command and go to the text definition you'll see it is a class text all right and also one thing that I didn't mention please don't change anything over here if you change anything in the flutter source code it will behave differently for you over here and that can cause a lot of problems so take this as a read-only file if you just want to take a look at what's going on inside and you're just curious in general but do not edit it anything at all because if it stops behaving the way you want it to you'll have to reinstall everything and that can be quite a headache unnecessarily so you can close this now so now we have the text over here and that is a widget so this text requires us to pass in a data as you can see whenever we instantiate a class it tells us what all stuff is required in this text and the thing that's required over here is string data and that is a positional argument that's why we are getting the error over here saying one positional argument expected by text Dot new but zero found we've already seen these kind of errors in the dot section so let's pass a string over here and let's call my text hello world so this string right here is what the text should display right if we have a texture you have pushed this button this many times that is a text right if that's a text the string data part is this thing right here so that's what I've typed in over here hello world then I'll put a semicolon over here save it I'll ignore the warning for now also anything in blue underline is a warning anything with a red underline is a warning or is an error also anything with blue underline is a warning and anything with red underline is an error you can ignore warnings although you shouldn't but you cannot ignore errors because if there's an error your flutter app won't build if there's a warning your flutter app can still build but it's recommended to fix the warnings before moving on and now when we save it you see this thing right over here we get a pop-up saying hot reload completed what is this hot reload thing hot reload is when you have a small UI tweak or some small change made in your code and then when you save the file you don't have to restart your entire system over here to see those changes in hot reload you can just save your file and it will display the small UI tweaks present in your code so you don't have to completely restart your app and start everything from scratch you can just save it and you'll be able to see the small UI tweak if there is no small UI tweak then you'll have to restart your app how do we restart the app by clicking over here on the city start button and as you can see when we restart we get some different kind of message over here with red background this is an error all right the red warnings or the red underlines displayed over here were compile time errors we've already known about that in the dot section but this ones are runtime errors and you can also see runtime errors or compile time errors when you press command J in the debug console and you see they've mentioned the problem over here now these error messages also contain the stack Trace in the terminal over here you don't see the stack Trace what is stack Trace stack Trace basically allows us to know where in our application the error occurred because if our application grows vast it can be a bit difficult to know hey this is where the error occurred right so stack Trace already tells us hey you have a runtime error and this is where data code so that's what text helps me with and as you can see the error is the relevant error causing widget was text okay so some error occurred related to text aware and then you have the exception thrown this was the stack and this just goes deep into the framework telling you hey this file this file this file this file is where the error occurred but we don't have to care that much about these lines because it's related to the framework and we'll anyways not be able to understand what's going on so we can just scroll up and you see the following assertion was thrown building text hello world so it's related to this thing only but to be honest I don't understand anything that's mentioned over here but I do understand this thing no directionality widget found what does this directionality widget found mean it is at least legible English you know but still it's quite difficult to understand what's directionality widget with respect to this text widget well the point over here is this text requires you to pass in a direction property we need to specify the direction property over here because we need to specify the text position on the screen do we want the text from to go from left to right or do we want the text to go from right to left that's what we want to figure out where on the screen should it be over here or over here that's why it was giving us this error so let's understand how we can fix that and many a times you can fix the problem by looking at the properties of the particular widget or the particular text class and see if there is a property related to direction to fix it and the property is text direction right and as you can see this is a named argument the first thing was a positional argument and after that we had named arguments that were optional so we can pass text Direction over here now you might ask if text direction is necessary without text Direction it is giving us this error why don't they make text Direction property non-optional as well just like data right if text direction is required in our text property without it it is giving us an error why do we want X direction to be empty or nullable or optional the reason for that is most of the times you won't be writing text widget like this over here you will be using something known as material app that we are going to look into in just a moment in just a while but their direction for text is already defined so you don't have to Define it over there so it is optional but as of now just for me demoing basic flutter app to you it's required so for now you can blindly just put text Direction it will make much more sense when we have so as of now you can just put text Direction like this blindly but later on you'll understand what I'm talking about when we start using material app and those kind of stuff so we have X Direction over here and this text Direction requires text Direction now is text Direction a class to understand that we have to press command and then we can go into the text Direction source code but it tells nothing about text Direction why because this is the Constructor we have to go to the place where text direction is initialized so we can click over text Direction and here we are final text Direction which is empty text Direction now to understand if text direction is a class or not we hover over this and it tells us it's not a class it's an enum so text Direction can have a certain limit of values now what are those values you can again click command so you go to the text Direction enum definition and here it is and it can have two values RTL or LTR and as you can see it's already defined over here with something known as a documentation comment this was the third type of comment in flutter we or Dot in flutter or dot in the dot course we saw that there are two types of comments first one was single line comment another one was multi-line comment and this is a third type of comment which is the documentation comment by documentation comment what happens is whenever I initialize text direction or use text Direction and hover over it you'll see a definition or the description of this text Direction property and somewhere when you scroll you'll see this thing right here the text flows from right to left example Arabic Hebrew you won't see that over here because this is present inside the enum but if you see documentation comments are present over here as well which is related to the text Direction so if we just go at the top you'll see a direction in which text flows some languages are written from the left to right so if you come over here hover over this you'll see a direction in which text flows so basically with documentation comments you'll be able to see some changes over here some stuff or description written over here which is quite nice because then you don't have to Google stuff up and understand what's required you can just look at the source code and understand what's required so let's close this let's close this and let's give text Direction up value and that will be text Direction Dot and we get Auto suggestion the auto suggestion is LTR or R2L and values is just a list or containing RTL or LTR so I'm just going to have LTR because I wanted to show up over here left to right so it will show up somewhere over here then I'll save it but if I come away a hot reload doesn't work because this is quite a massive change so you'll have to restart your entire app and then you'll be able to see Hello World over here we are not able to see it properly but yeah it is written over there now if I just mention let's say four exclamation marks save it I'm not seeing it again because this is a massive change so after I restart I'll be able to see it but later on when we start adding material app and we make small UI tweaks you'll be able to see the great power of hot reload which is what makes flutter very different from other Frameworks because many other Frameworks don't have the support for hot reload and it's quite a wonderful feature in my opinion and now if I press RTL over here instead of LTR and restart the app I see text over here and my exclamation marks go right in the right so that was about text and you know just displaying some stuff up but now let's get into more complex things because obviously we don't just want to return a text away and for bigger apps this is not possible why because simple apps don't just show UI right they have many more things going on in the back end it's not about databases of servers that I'm talking about not the back end related stuff I'm talking about stuff like navigation by navigation I mean moving from one page to another so if I have one page then I want to move to another page bigger apps can do that for example YouTube if I use youtube.com I see the home page when I click on a video I'll go to another page that contains the video player so bigger apps have multiple pages in them and moving from one page to another in an app is called navigation just like moving from one place to another in real life is known as navigating right so bigger Hub apps have support for that and it can't be done by just using text we need to use something else which is known as material app or it can be Cupertino app now we are going to dive into both of them but before that we'll have to understand some other Concepts now you know just having a text widget isn't what a real app real app will look like it will have one screen of its own and in that screen there are going to be many components as well for example if you just open google.com it's a very simple looking page but it has a lot of components here first of all it has the header right up at the top Gmail images all of this stuff then it has the Google logo over here then it has the text field that takes our input then it has two buttons then it has this thing which helps us in Translation then it has footer and that too two Footers I guess so it has a lot of components and in flutter every component can be a widget right so if you're coming from other Frameworks like react you already know what components are whatever UI building block is there and in flutter widgets are components my point is that this app will grow into something big that will have many components on the screen so what I want to do is make sure my app is broken down into several smaller widgets so that more Engineers can work on it at the same time just imagine my entire app present in this function right here I can do that it's totally possible so I can build my entire app all the widgets let's say the entire Google Chrome screen I can build in this function but do you think that's feasible because it is it will become such a big thing right it will have like hundreds and thousands of lines of code all enclosed within this function so I obviously want to break it down so that more Engineers can work your net together and when it's broken down you can allot different files to it different classes to it and Engineers can work on net at the same time and it will boost productivity so that's what I want to do I want to segregate this text widget in a widget of its own that won't have any UI change but it will definitely have a productivity boost for our application so let's go ahead and create our own custom widget not custom widget but our own widget and we can do that by creating a class because widgets at the end of the day are classes if you press command go to the text definition you'll see text is a class as well and it extends something known as stateless widget to become a widget so we need to do the same thing my widget is going to be named as my app nothing to fancy there because if I name this as text then it will be a problem right because then it will get confused do you want text from material.dot the thing that is coming from flutter or do you want to use your own text widget that you've created so better to just name it something else because there are hundreds of other names you can choose so you can have mic app extending something known as stateless widget now what is the stateless widget stateless widget first of all is a type of a widget and there are multiple types of widgets by multiple I mean three first one is stateless widget which we have seen right now the second one is a state full widget and the third one is inherited widget so widgets can be broadly classified in these three types stateless widget and stateful widgets are what we are going to discuss while building the first app we need to thoroughly understand this then the third one inherited widget is a more complex topic to understand so we'll be discussing it in the second and the third app all right so let's remove this for now and let's just think we have two types of widgets here in terms of UI all right in terms of UI related stuff there are only two widgets inherited widget is for something else so to understand stateless and stateful widget you need to understand what state is all right so to understand the state let's take an example of our counter application what will be the state over here well State refers to any data that will determine how your widget should look like how it should be rendered or how it should behave so this text over here can be a state the text below it the 0 is a state why because these two things are data that determine how the widget should render how it should behave how it should look like right even this app bar this button right here determine how the screen will look like but that's not the definition of state that's the definition of a widget State refers to data that will determine how the widget should look like so these two things are data that will determine how the widget will look like how the screen will look like and app bar and this button will determine how the screen will look like they are not really data right so these two things are data over here so that's what state is to shorten the definition you can say state is some data that your widget will care about right now what is stateless widget so it is State less widget does this mean it does not have any state at all no it's very unlikely that your app does not have any state at all your app will usually have States that's what gives your app meaning right if I just remove the Zero from here and you have pushed the button this many times text from here do you think this apps this app makes any sense at all not really so your app will have state it's very unlikely that your app does not have a state but just means that your app or your widget will have less State and by let's State I mean in a stateless Widget the state is immutable the data is immutable meaning once the widget is created it cannot be changed so suppose this was a stateless widget it's not really a stateless widget you'll understand in a moment but if this was a stateless widget then this text wouldn't change at all this text you have pushed the button this many times does not change at all but even the 0 would not change when I click over here all right that's what stateless would do but stateful does what happens over here when I click on this button the state changes so I hope you understood the difference between stateless and stateful widget stateless basically has the state immutable so the state doesn't change at all and in state full the state can change it's not immutable it is mutable so whenever you want mutable state or state that can change you'll use stateful wizard otherwise stateless measure so for now I've extended my app with status widget but as soon as I extend the stateless widget my app gives me an error it has this red underline which tells it's an error and you can see the error is missing concrete implementation of stateless widget dot build why if I just remove this extent stateless widget this is a new class and that's fine right but I have to extend it with a stateless widget so that it becomes a widget I cannot not extended and put it in run app I have to extend it so after I extend it it gives me this error meaning stateless widget is telling us to override some functions and we've seen that before because at the end of the day stateless widget is an abstract class whenever you extend an abstract class you need to override its function and redefine its implementation so what we need to do over here is ADD add the rate override widget dot build right not exactly why just go to the stateless widget definition scroll down and you'll find widget build aware this is what we need to override this is what is defined in the abstract loss now you'll ask hey stateless element create element is also defined over here right but that's defined with its implementation because stateless widget is extending widget and widget is basically telling stateless widget to override a method of element create element which is what the stateless widget is doing now if you don't understand this don't worry for now you'll understand this later on when we get into widget trees elementaries and render objects but for now don't don't worry about it if you don't get it but if you get it awesome so basically the only thing you need to understand as of now is widget build build context this thing needs to be defined so we can just copy it we can paste it over here with other rate override at the top then create a function out of it but this gives us an error this gives us an error because this is a function right we need to Define its implementation now to Define its implementation we have to return a widget because this is a function this function takes a build context and then we need to return a widget from here so basically we need to return a widget and that is why it's giving us an error the error says the body might completely normal causing null to be returned but the return type widget is a potentially non-nullable type if we had widget like this aware it would have caused no errors but unfortunately or fortunately that's not the case we need to return a widget all the time from a stateless widget so we can just copy this text right at the top then return text like this and the error goes away also now we can just take this my app and put it over here and make sure you have these parenthesis because it's a class right you need to instantiate it and now when you save it and restart your app you don't see any changes there but what happened over here is you don't have to continuously build your app in this run app function you can just pass my app class and now you can start editing in the my app class that's what I was talking about by extending to a stateless widget or a stateful widget you're just making sure that your app is divided into smaller pieces if you have your app divided into smaller pieces many people can work on it together and make more progress so I hope you understood the purpose a stateless widget but still we have warnings to fix we have these blue underlines to fix so let's go over them one by one starting with my app now if you hover over this you'll see Constructors for public widgets should have a named key parameter this is basically saying that hey you extended stateless widget now stateless widget you override the build function that's all good now you can create your app I won't bug you with the compile time or runtime errors but I'll still bug you with compile time warnings and this warning is there because if we again go to stateless widget definition you'll see this Constructor over here constant stateless widget super dot key and it did this because it was extending widget when it extended widget widget required something known as a key for its Constructor right you can see it away a constant widget this dot key so our abstract class widget requires something known as a key and whenever you extend an abstract class you'll have to pass that key to the super class which is the widget and that is what stateless widget did Super dot key but where will stateless widget get its key from it will get it from us us the people who extend stateless.widget the same thing happened in text as well if you go to text definition you'll see class text extending stateless widget because text also doesn't have an immutable State because if you think about it text also doesn't have a mutable State obviously it will only have its own immutable State that's why it's extending a stateless widget then it is having its key defined somewhere over here if you just search for it you'll see super dot key so this is what we have to do over here as well we need to create a Constructor for my app which will be something like this super dot key and now the error goes away now what is the super dot key we've already discussed about this in the dot section if you remember we had a key or something like this let's say string data and then we had to give something to the super class we would do data like this right what happened over here we are saying that hey you can optionally pass data to us and if you do pass or if you don't pass we are just going to pass that value to our super class whenever we use super we refer to the abstract class super right so that's what happened over here this requires key so we have key optionally asked you don't have to necessarily specify key every time you instantiate my app you can just ask for it and if you don't want to pass that key you cannot pass in and then you have to mention key over here so this is what we did when we did Super dot key okay this is just a shorthand syntax of this long thing right here but basically this means we are optionally taking some stuff from The Constructor and passing it to the Super Widget the widget we are extending to in our case the stateless widget and in stateless widgets case widget now if you don't understand the specifics don't worry about it you'll still be able to build apps without this knowledge but it's better to have knowledge so that you can build your apps with much more accuracy and now if you see over here as soon as we add constant Constructor over here my app asks us to use constant so we need to put constant over here what is the purpose of this constant the purpose of constant is to declare that this Constructor is a compile time constant by making the Constructor constant you are just telling flood that hey the widget instance that you've created over here this my app class over here doesn't need to be recreated every single time you can just create it once and that's enough this helps to improve the performance of the app because the number of times this object is created is quite less the same thing comes away when you hover over this text you'll see use const with the Constructor to improve performance so again we have to use constant over here so before returning many widgets you'll have to put cons before them because it just tells that hey this widget doesn't have to be rebuilt you won't understand the purpose as of now but when we get into the currency converter app you'll understand it better which you might have in your mind what is a key now key is a class that helps flutter identify and differentiate between widgets by passing a key to the Constructor you explicitly assign a specific key to the specific widget instance so if I pass a key to my app you are assigning the key to this particular my app instance and this ensures that the widget is properly managed by flutters algorithm to update the widgets whenever they update now this won't make any sense to you because keys are used in updating the widget tree and all of those stuff but you don't even know what widget tree is as of now so again this is a part that we'll cover in the widget Tree Elementary theory part for now let's just get the app working right so yeah I hope you've understood it till now from now every step we take will be towards building the currency converter app so in our app right now we are just returning a text widget nothing else and that's cool but here's the problem I'm not following any design guidelines or design rules within which I'm restricted so I can build whatever I want so that allows me to build really exceptional UI designs or it also allows me to create most of the worst UI designs now I want to make sure that doesn't happen I don't want to see the worst case scenario when I'm working with over 100 Engineers let's say so what I want to do is make sure that my app follows a particular guideline a design system all right so for that we have two types of designs given to us by two major companies now there are many more Design Systems but these are the two most popular ones first one is material design and the second one is Cupertino design so what are these designs and who made them well material design is a design System created by Google and Cupertino design is the design System created by Apple now you can think of the difference between Now Android apps look and how iOS apps look and then you'll be able to know the difference between material design and Cupertino design even if you scroll up yours material.dot and this material.dart is named after this material design itself because material.dot if we click on command and go over there inside you'll see all of the widgets here we are going to use many of them but all of these designs are related to material design and there's a similar file in flutter related to iOS design as well so if we just have package flutter slash Cupertino dot dot instead of material dot you can add Cupertino design in your app we are going to see the difference in both of them when we build our currency converter app but as of now we are just going to focus on material design now how do I make sure my app adds material design so for that I'm going to return material apps from here as simple as that I want a material designed app so I'll return material app now you can guess for yourself if you want Cupertino design we can just have Cupertino app and will be done and as you can see it automatically Imports cupertino.dot but for now as I said we are just going to focus on material app at the end when we are done completing the currency converter app we are going to see how this will look like in Cupertino design and what all stuff we need to change but as of now I'm not going to reference Cupertino design anymore we're just going to focus on material design so coming to this material app there are lots of things we can do over here and material app just does not set the material design for our app it also gives us multiple options to use or to configure for example if you hover over this we have Navigator key scaffold messenger key home routes initial route on generate route and a bunch of routes then we also have theme and all the theme related stuff then we have localization all the localization related stuff and a lot of small small things why I am telling you this is because material app allows us to set up navigation for our app if we just return a text widget we won't be able to move from one page to another without doing anything we have to return either a material app Cupertino app so that we can set up navigation in our app and same goes for theming same goes for localization internationalization all of that stuff now if you're confused what theming internationalization localization navigation means we'll get to it when we get to those certain topics and we dive into it as of now you can just understand that these allows for a lot of stuff which just returning a text can't do okay so now I've returned a material app now what should I do if I just save it and you know restart the app and come over here nothing shows up even my text is gone because well I had returned text from here and I removed it now what should I do to return a text again so for that I can use one of the properties given by material app which was home so I can just pass home property here and as you can see home property requires a widget that can be optional so I can just pass in let's say a text again and now I'll pass in hello world with let's say four exclamation marks save it and you come over here we see hello world and now it's a different kind of text altogether and you notice one thing I didn't have to mention text Direction over here I could just pass in text and it worked fine and I was able to see this text right over here why did that happen that happened because material app sets up the text formatting for your app or the text design for your app if you press command and come over here you won't be able to understand where the text is given its direction and all of that stuff but you can take my word on it otherwise you'll have to dive deep and I'm sure you won't be able to understand any of this even I don't understand it but the point is how can I make this text look better because this looks absolutely terrible right what is this I mean red color text with yellow underline what is that none of the current apps in our world use this so how can I change it so to change it we have to wrap our text with something known as a scaffold and usually material app home property is followed by a scaffold all right so we need a scaffold over here and in this scaffold we can provide the text and we'll be able to see the text rendered properly not in a very bad design so if we put scaffold we'll discuss what scaffold is and in scaffold we have to provide the text widget now how can I provide the text widget well there's no home property over here but there is a property of body and you can see scaffold provides very intuitive names for everything over here we have an app bar app bar is basically the thing at the top the header then there's body so the body is the middle thing just similar to an HTML element right so in HTML you have header header is ABBA then you have body body is this body so it's kind of similar to HTML only if you see it in one way so we can pass body aware then our text widget and then again we will type hello world and then our for exclamation mark we'll save it and you come over here something else only shows up we have a white screen all of a sudden we have a text showing up here and it looks wonderful you know better than what we had earlier how did this happen so whenever we use a scaffold scaffold tells the flutter framework that hey the programmer has used a scaffold widget so we need to provide user or the programmer all the capabilities to add everything related to a material design for example the header if we don't use a scaffold we won't be able to add header in any of our apps material app will set the overall theming and overall navigation stuff for us but scaffold will make sure that something related to one specific page is done and scaffold will give us access to headers Footers and all of that stuff so to make sure you understand this material app and scaffold thing let's take a look at a diagram so let's say this big thing right here is our material app what material app does is set up a playground for us so that we can do everything material design related so we have material design over here we have all the navigation localization internationalization and theming all of them set up over here so this looks after the overall app in general so this is kind of like on a global scale and what scaffold will do is basically in our Global space set up one local space of its own right over here and say hey now you can add a header now you can add a body now you can add a footer then you can add a bunch of more stuff like bottom sheets you know showing up a dialog box we'll see all of that in our app but that's what scaffold does scaffold looks after the local part and material app looks after the global part and in your app you can only have one material app return right it doesn't make sense to have material app two or three times but scaffold it makes sense to have two or three because if you don't have a scaffold your text will be rendered in a very and you won't like it so I hope you understood the difference with this diagram and things got clearer now let's jump back into this and now what I want to do is make sure that my text comes right in the center every time I see my text it's right in the corner who likes the text in the corner I want it right in the center over here how can I do that I can do that by making sure that text has a property of a center is that how it works not really if you look over here you don't see anything related to the text coming in Center yes you can use text align property which basically tells hey where do you want to render your text where do you want to align it do you want it in the left in the right in the top in the bottom but that is only when you have full access of the screen right now a text widget only occupies this much space it doesn't have the entire screen to itself if it had the entire screen to itself then it wouldn't be this small right if a text had access to the entire screen it would spread across the entire screen text only has access to how much space it acquires over here so I cannot use the text align property over here and I cannot use any of text properties to do that because text doesn't have that much control just think about it in terms of a kingdom if a certain Kingdom if our widget if our text widget is a certain Kingdom if our certain Kingdom wants to come over here how can they come they can only come when they have access to the entire area if they don't have access to another area then they can't come over here as a result they'll only stay where they have their control to understand this even better let's take an analogy let's say our widget aware this text widget is a kingdom if this Kingdom wants to come right over here in the center how will it come can the wing kingdom just come anywhere they want no they have to gain control over this entire space so that they can come right in the center without any control on this land or on this space no Kingdom can just move from year to year so same goes for our text widget for it to come over here it needs to have access to the entire space and a text widget cannot have that because it only takes as much space as it requires only this much so this Kingdom can do nothing about it but yeah something outside the kingdom can make sure this kingdom comes away right so if there's another kingdom and the annex this Kingdom then they can make sure that this kingdom comes right away in the center so that's what we want to do we want to make sure from outside that this text comes in the center because from inside text does not have any power so what we need to do is wrap this text with a center widget that's a widget provided to us by flutter so in body instead of having a text returned wire I'm going to have Center and then Center if you see there are very less properties we have key we have double with Factor height factor and a child what I want to use is neither of these two things and key is generally not required so we can just have a child and a child is a text widget so we say hello world and then for exclamation mark save it and when you come over here you see hot reload Works away because this is not a very big change this is quite a small change to the framework and as soon as I save anything I don't have to restart this I can just press command s it hot reloads and I see the changes in real time and even our text is centered now so as you can see material app scaffold Center text whatever I mentioned in the center will be centered the same way as whatever I mentioned in the scaffold will be scaffolded so anything you mention inside of the center widget will be centered so if you want to put a button over here you can do that if you want to put an image inside of this you can do that and it will all be centered and now we have our first good looking Hello World app now we want to start working on the currency converter app but before that I hope you started to realize this kind of chain of widgets that we are making in material app we add home then home required a widget then scaffold body body required a widget then we add Center centers child required a wizard and these are the three things all right whenever there's material app there will be home that you have to use whenever you have scaffold there will be body and whenever there's any other widget other than scaffold or material app you'll have the child property on it except a widget like text you know because text is itself displaying something stuff like Center is not actually displaying anything on the screen right it is just setting the alignment and the layout but it's not setting anything up on the screen for example hello world is being displayed on the screen a button will be displayed on the screen but a center will not be displayed on the screen it's a way to tell the flutter framework that hey our programmer wants the app content to be centered so it's related to layout it's not really related to rendering anything on the screen and this thing right here is also known as a widget tree why let's understand that so let's say we have our material app so we have this giant block of a thing which is called material app so let's call this m then in material app it has something known as a scaffold then in scaffold we have a center widget and in the center widget we have a text widget so what have we got here this is kind of like a tree right because if you just take this and you know just reverse everything up material app is the root of our widget so material app sets the root for everything that's what we saw in the previous diagram as well material art was setting up everything in the global space then we had scaffold which was one of the branches then we add the center widget which was one of the branches branches you can say sub Branch this was another sub Branch so we are creating kind of like a tree that's why this is known as a widget tree okay and as I've already said before it's always good to split up your widgets so what I like to do is material app can have a lot of configurations done inside it for example routing can be set up in material app theming can be set up in material app and localization internationalization and what not can be set up in material app so this material app can be filled pretty much so what I like to do is take this scaffold because it's a separate page of its own and put it in a separate file in a separate class of its own just like we did with my app when it was in Run up right we just want to make sure that the widget tree always stays small so that it's easier to contribute to it and it's easier to understand as well so what I'll do is create a separate file aware and the separate file is going to be called let's say currency converter material page dot dot so you notice the convention of naming aware of currency then I wanted to put a space but if I put a space it will be incorrect naming so I have to put underscore over here so we have currency underscore converter underscore material underscore page dot dot dot dot extension needs to be put otherwise vs code can't identify and even flutter cannot identify that this is related to flutter so you need to put the dot dot extension so vs code automatically identifies hey this is a DOT file okay and we have created a new file over here in our lip folder itself yeah I can go ahead and create my stateless widget again so I'll call this class currency converter material page I've given it a pretty long name you can just call this material home page I am putting material over here because later on in our app I'm going to show you the difference between material and Cupertino app right so not to cause any confusion I'm putting this as currency converter material page however when we are building other apps in the future I'll remove material all together from my names because I won't be experimenting with two type of apps material and Cupertino I'm just going to have one design for my app which is material design because personally I like it much better than Cupertino design so if you have just one design guideline which is being followed then you don't have to name it like this so anyways let's go ahead and extend stateless widget we have already seen this and it automatically Imports material.dot and one thing to note over here is every time you import a new DOT file you'll have to import a new material.dot because these import lines are specific to the file if you've imported material.dot over here it doesn't mean you can use it over here all the import lines are specific to their files now I'll have to go ahead and create an at the rate override widget build then yeah something known as build context which we'll understand and then I'm going to return this thing right here so I can just copy this and go ahead and returns scaffold over here also I'll need to put the key over here so we'll have constant currency converter material page named argument super dot key perfect now I can take this class come to the bin dot dot file remove the scaffold and have something like this done so what I've done is basically transferred my entire scaffold widget from the home over here to a particular specific widget of its own and now I can keep building the widget tree over here so this thing this my app class is much shorter and I can pile up all my UI related stuff related to the currency converter page in this particular widget and now if we restart the app there will be no changes at all because we have basically transferred everything in one class to another class and then call that class so essentially we are just having material app scaffold Center text the same thing but in different widgets it's just for our improved visual or improved working it doesn't have any effect on the app till now okay so I hope you've understood everything till now if you have amazing now again we can put Constable whenever it asks us to let's resolve all the errors we can put constant over here as well save it and this looks good now before moving forward I need you to understand this build context thing which is a very very important Concept in flutter after widget this is the second bigger concept that I'm teaching you which is build context so what exactly is this build context here what does it do and why is it mentioned inside this build function let's understand that build context is a class provided by flutter which tells the flutter framework that hey currency converter material page is present over here in the widget tree not anywhere else it's basically telling the location of this currency converter material page in the entire widget tree and every time you extend a stateless widget or a stateful widget you will have access to build context and every widget has that if you press command and go to the scaffold definition it extends something known as the state fill widget and when we scroll down you'll see that this also has a build context and same goes for the center and this text as well so every widget when extended by a stateless stateful widget will have its own build context because flutter wants to know its location so that's what build context does tells you the location of a particular widget in the widget tree to understand this diagrammatically how will flutter know are present over here how will Florida make sure that it doesn't mess up stuff it doesn't mess up stuff like Center is present over here and text is present over here because we need the rendering to be perfect right if it is not perfect then our app will look very different from what we want it to look like so that's where built context helps and now a valid question over here will be if flutter can do all of this stuff behind the scenes why is this build context exposed to us like why do we have access to build context of air why can't which it build be like this and this will be nice right because we are not using the build context anywhere in our code well that's because we have not implemented anything that's advanced yet and when we do stuff like navigation moving from one page to another setting up the theme of our app all of that will require build context it is one of the most important Concepts in flutter we'll understand the inner workings of how navigation will take place and all of that stuff but keep in mind for now build context is basically telling the location of the widget in the widget tree also one thing that I forgot to mention in the main.file if we come and you see you're in a home we have currency converter material page instantiated over here but this is coming from package currency converter currency converter material page dot dot so as soon as we you know instantiated it flutter automatically imported this particular line why let's break it down we have package currency converter what is this package currency converter well if you go to your pubspect.yaml file scroll up you'll see the name of your project as currency converter over here it's package flutter because the name of the flood up SDK is flutter same way our package name is currency converter that's why we have package currency converter like this and in there we have imported the currency converter material page dot dot which is present in the lib folder it doesn't go like package currency converter slash lib slash currency converter material page dot dot because when you have specific.yaml saying name it is obviously going to be in the lib folder it's not going to be anywhere else all your Dart files are present in lib folder nowhere else that's why it directly Imports it like this however if you create a folder inside of lab let's say pages so that it's more organized right and then we shift it inside click on move you can just drag and drop it and then we do move extension dot wants to make refactoring changes with this file moves basically since you've moved the file the import lines will change now so Dart extension will automatically do it for us so we don't have to resolve those errors now if we click on OK you see now its package currency converter slash Pages slash currency converter material page dot dot dot automatically did it for us and only thing that we need to do is press Ctrl s to save the changes made by the dot extension all right so anything in the lib folder will have its import like this now this is called as package importing now there's another type of importing you can use here let's remove this and instead of importing it like package currency converter what we can do is relative importing by relative importing it means whatever file we are in right now in main.file relative to this main.dot file where is the file present so relative to main.dot file we have dot slash and when you put dot slash you see auto suggestions so right now we are in the lib folder all right because that's where main.dot is present then we need to go to the pages folder so we'll just pass in dot slash pages and there we have our currency converter material page so this also works and this is known as relative importing because this is an importing based on the current file so if you are in main.dot file this is how you will Traverse over it all right so you can use either of them it depends on your preference and it is also based on the tools you use right many people prefer importing like this but many people don't prefer importing like this but if you're coming from web development you might have already seen this in JavaScript code so it shouldn't be too difficult for you however it really depends on you whatever you want to do also when you remove this importing you see the error comes over here because this class is not identified this class is not identified because it's coming from some other file and you have not imported that file that's why so to resolve this again you can type it like this or you can just do command full stop so it will give you a list of fixes that you can add in your app that will fix this error so the Quick Fix is importing the library set correctly I identified that somewhere in our code this currency converter material page class is present so we can use that and then it also has this different kind of importing so both are importing but it's just different kind of importing now we can click over here save it and then we are good to go also let's push this file out in the lip folder again let dot extension do its job we'll save it and we'll delete the pages folder because that was just for demo pages will be required later on in our apps when we build bigger apps right now we just have two three pages what do you want to do with that right so let's come over here and now develop our app now what is required in our app let's break it down so how is our app going to look like well first of all we have we are going to have a big solid texture layer which is bolded which says hey this is your answer all right so this is the converted price and then we have a simple text field which takes the user input and you can type your currency over here and then we have a button which says convert so we are going to have three elements below one another present in our app how do we make sure that happens can we do it over here in the center text widget can we put everything in a text widget not really because there are three different things paste out differently so we have a text showing up at the top then we have a text field and then we have a button those are three different widgets and you can't put everything in a text widget what you need to do is make sure that you have some sort of widget that will make sure you're able to align everything from top to bottom in a vertical manner and it accepts many widgets not just a single child widget like the center has it needs to have children because it will take in multiple widgets it will take a text widget it will take a text field widget and it will take a button so we'll remove this text from here and instead of putting a center away what I'm going to do is put a column what is a column column is another widget which doesn't really paint anything on the screen it doesn't render anything it's related to layout it's basically laying out our widgets in a certain Manner and how is it doing that well it's a column right how does column work it's something that goes from top to bottom and it has an argument of children if you scroll down you'll see children and it doesn't accept just a single widget it accepts a list of widgets and we already know what a list is so let's go ahead and pass children over here then we are going to have a text widget which says 0 for now okay so let's save it and where did a zero go it's not showing up anywhere well that's because we have removed the center widget from here so again it starts right from the top corner and that's why zero can't be seen so a simple fix to this can be wrapping column with Center widget again so let's go ahead and have Center child then we'll take this column and paste it over here something like this all right now if you come over here we can see our zero but still it is centered horizontally it's not really centered vertically it's not coming over here right it's over here it's centered in the horizontal space not in the vertical space to so to center it in the vertical space column has its own properties as you can see over here it has a property of main axis alignment and it also has a property of cross axis alignment we do know that it's something related to alignment that we want and we have two alignment related properties but which one should we use let's understand the name main axis alignment since this is a column what will the mean axis of a column be the main axis of a column is obviously the vertical landscape right this is the main axis and cross axis is this thing right here if we had something like a row the opposite of a column the main axis of a row will be the horizontal thing and the cross axis will be the vertical space but since this is a column column will have its main axis as the vertical landscape or the vertical scape and this will be horizontal which is cross axis okay so we'll go ahead and put main axis alignment now what does Main axis want and is it a class an enum what is it so as you can see main axis alignment has a preset value so if you don't pass anything to main access alignment it has the value of main access alignment dot start what do we want we want Center and as you can see we have suggestions related to it already or if you just pass main axis alignment dot you'll still get all of those values and as we know main access alignment is an enum so since it's an enum we have a bunch of properties that we can select so it can be Center that's what we want but let's try other values first so that we know what we're talking about then we have end which is the opposite of start right so instead of our zero showing up over here it's now showing up over here if you can't see it you see this is this part here this is 0 then we have space around space between space evenly start now I won't be able to show you the difference between space around space between space evenly as of now but when we add two more widgets which are the text field widget and button widgets will understand the difference between all of these three things so stay around till that time and we'll understand the difference but as of now we know what start is we know what end is and obviously Center is basically saying hey come in the center so since we've aligned this in the center does it mean we can remove the center widget like this and make sure your removing it nicely because when you try to remove it you know you have to remove this child you have to remove the center and then you also have to remove a parenthesis related to it because this is a center widget like this right so make sure you remove it nicely or if you can't remove it nicely then press command shift r or you can just right click then go to refactor then you get a certain bunch of properties over here and you see removes this widget so what this refactoring option does is remove the current Widget the widget that you had right clicked on from the widget tree and when you do that Boom the center widget is now gone and there's only a column and we don't even get an error so you can always do that if you don't feel confident in removing it now if we come over here again r0 is gone but where is it gone it's right over here why is it over there because we had removed the center widget which centered the column horizontally not vertically vertically we are main access alignment so for horizontal we have to put a center widget but what's another thing that we can do well I told you column has the cross access alignment property as well which will make sure its position in the horizontal space so we can just go ahead and add cross access alignment then this requires cross access alignment so we have cross access alignment Dot and you see we have a similar set of values we have Center we have end we have start and we have stretch so if we put and you know where it will go we know it where it will go right so if we come over here well 0 is not aware it's still over here why is that the case that's the case because column will only take up as much space as its children want it will not take anything more than that which is why so column is only taking us page this much long all right it's not taking a space like this this entire thing is not being taken only this much is being taken so that's why it cannot go over here because column only has a space of this much only till where the text is if it had the entire space to itself it could go over there now if you still don't understand what I'm going to do is wrap this column with something known as a colored box which will make sure that our column can have some color because column doesn't have a property to give itself a color to give itself a color to give to give column a color we'll have to use a different widget we cannot use column because column doesn't have a color property of its own you can check it away so what I'm going to do is have colored box over here which is another widget provided by flutter and you see we have color over here we have to pass in a color and we can also take this column and pass it as the child so all of this is very intuitive right because colored box what will it do well it's simple English it's a box that is color so let's put color aware but what's color well it requires something known as a color so let's put it over here and color might be an enum but that's not the case color is a class in itself and if you instantiate it it will tell you to give it some value which is an integer and it requires something of this sort and we really don't know what this is so we can't use this this is not for people like us so what can we use then well we can go ahead and use some of the static properties mentioned on this color class well we can use some of the methods over here so we can use from argb from RGB of alpha blend get Alpha from opacity love but what is all of this well from argb is basically telling that provided Alpha red green blue color values and then you'll be able to display it from rgbo says that give me the value of red green blue opacity and then I'll be able to display it why does it require only red green blue because that's the fundamental colors right those are the base colors based on which other colors are made and RGB will perfectly describe any color you want to make so let's go ahead and use from rgbo and then we have to provide a set of values from 0 to 255. now we don't know any of these now what is white color well we don't know but we do know how to make a red color because red green blue is going from 0 to 255 so I can give red the maximum value then we have green blue and opacity so if green is 0 blue is 0 and opacity is 0 will that mean I'll get a red color not really because opacity basically means how much part is visible and you're saying it is 0 if it is 0 visible then it is black color when there's nothing there's black that's why we are going to put one over here which means it is completely visible and now you can see in a preview that we have selected the red color again if you didn't understand since red is given its maximum value which is 255 green and blue are given 0 and 0 values and opacity is one that's why we get a red color now if we save it come over here you see this is what our column is it doesn't extend to the entire screen it's only this much right away here and that's why when we put cross access alignment dot end it doesn't go till here because column doesn't have this bigger space remember what I told about text when text was over here text can only go away if the text widget takes that much space now column can only take this much space so it's mentioned over here now in main access alignment we could position it at the top in the middle in this end because column takes that much space but column doesn't take the entire width that's why we cannot use cross access alignment over here what we need to use is a center widget and let's remove color from here save it and then our widget is centered right over here perfect so that's good we are able to have a column with r0 written right over here now the next thing I want to do is make sure my zero is styled what did I say I want my text to be bolded it should be bigger in size so I need these two things to happen now how can I do that well we can find a property inside of text because text should have that right if a text can't style itself what can a text do and if we scroll down and find something related to bold and font size we cannot find that why because it is all mentioned in one single class which is the textile class so we need to mention the style property put in a textile where font size font weight all of those things are present so we can go ahead and have style then we'll pass textile over here that's called and now if you hover over textile you see a bunch of properties related to styling of the text we have color we have font size that's what we are looking for we also have background color of the text and a lot lot more things this is why all the styling related to text is present in textile since there are so many properties you cannot just put it in a text widget it will be too occupied over here that's why just put everything in a textile class encapsulate it in text style class and textile can be used inside of the text widget so that was the decision making the flutter team took and it's clearly pretty good so now we can put in font size over here let's say font size is 20 because this requires a value of double and save it if we come over here the font size has increased but it's not increased that much so let's go ahead with 25 save it come over here and it is much bigger still not appealing to me so I'm just going to go ahead and put 35. this looks nice now you have to keep testing to see which font size you prefer the default font size is 14 so if you put 14 where it will come back to normal or if you don't mention it at all it will be 14 but when you do mention it let's go ahead with 45 I think that would be good yeah and the next thing I want to do is bold it so for building what can I use well there's nothing related to Bolding that we can see over here but we do have font weight what is font weight well font weight is basically how much weight the font has how much bold it is so we have found weight dot boldavia fontway dot normal and you see font weight requires something known as a font to it and font to it is a class with all of those properties mentioned over here so we can put font to it dot normal which is the default one or we can use W 400 W 500 you can keep testing on your own but I'm going to go ahead with the Bold option because that's what I want I'll save it and you see this is bolded now if you want to see it real time I can do it over here I'll remove this save it the Bold is gone now I'll put it back by pressing command set and save it yep now it is bolded so you can see this works and also if I put W 700 and save it there will be no visible difference because behind the scenes dot bold is using W 700 weight and if I put W 400 it will come back to normal because normal is using W 400 you can see it over here now if you want something Bolder than the normal bolded you can go ahead with W 800 or W 900 and that will keep it very bolded but I'll go ahead with the default bold option that we have and this looks better great now if you again want to increase its size you can do it depending on your preference good so now we have our text displaying as and how we want it now again if you want to change the color of this text you can do it so you can pass a color over here and color can be color dot from argb now what is argb argb is basically Alpha value which is kind of like opacity but instead of 0 to 1 this extends from 0 to 255 so 255 is fully visible and 0 is not visible then we have red green blue just like 0 to 255 0 to 255 0 to 255. and also if you just go on Google and type white RGB you'll see the RGB the red green and blue values of the white color so for white it's 255 255 and 255 so you can just go ahead and pass 255 255 255 and the alpha value is 1 so that will make it white color not exactly because we have put one over here in the alpha alpha requires a value of 255 and you see we get a wider value over here now if we come we are not able to see it very properly but you can see it there's a white color over here now if you're confused that why is this white visible on a white background that's because this background color of scaffold is not pure white it is white but with a different RGB value this white over here is pure white that's why we can see it and if you want to change the background color of a scaffold you can do it so you can come to the scaffold search for a property over here related to color and you'll see background color over here where you can pass let's say a black color so for black you can pass in color dot from rgbo zero zero zero and one why zero zero zero because when red green blue r0 that means none of the colors are present that's when black will be made right black is basically nothing no colors and now if you see we have a black color and a white colored text is visibly seen over here now you might be having a question that hey why does flutter make it so complicated to just put a value to put a right color why can't I just name it well you can instead of using the color class you can use the colors class and then you will have access to a bunch of colors that you can directly mention you don't have to mention there rgba values so if you want to put green over here you can save it then and you see this is green color with white text and obviously you need to put comma before mentioning any other property otherwise it will give you an error because at the end of the day this is a class that is being instantiated right and in a class when you mention a property you need to put a comma to separate it now you can go ahead and test other colors so you can have light blue and there are many many colors but the reason color dot from RGB is present because colors dot cannot mention every possible color because there are infinite colors right you can make infinite combinations not infinite I mean uncountable combinations so to give you more access to what color you want we have from argb and rgbo which tell you to specify the color on your own and make sure that your background color or any color is the way you want it to be so we can for now go ahead and type colors Dot blue gray save it and this looks fine we can keep it or we can just keep the white color anything you prefer I would prefer making the app more visual as of now later on we'll get to the minimalistic designs all right so now we have covered the text widget as well in a column now time to put other widgets in the column before this we have never put any other widget inside of One widget so every widget requires only one child but in column we have children that's why I can mention another widget and what is the other widget well it's the text field widget which will allow me to take the user input and now if I just instantiate it like this save it I get text field over here and I can type anything in this text field right but obviously this is not what our text field should look like because text fields are meant to be more visual you know I don't know what this text field is for it doesn't give me any clue as to what I need to type in over here and also the design is looking pretty bad so let's change it by adding some designs in this text field so let's go over all the stuff we need to add in the text field so if we come over here the first thing that I want to add is basically kind of like a hint saying that hey this is the thing you need to add it's not a placeholder but it's basically something written over here and it should show up only when I haven't typed anything over here and when I start typing a number I should be seeing it so how can I make sure that kind of hint comes up so for that I'll have to look at the properties and see if there's a property related to it and there's something known as style and strut style but if you see style takes up value of textile if it takes a value of textile then it's probably related to text and this is a text field right so this style isn't related to the style of the text feed it's related to the text inside the text field so if we just try to edit it out so we'll type your style text style and let's say we change the color to Colors dot blue all right and then we save it and then if I type anything you see instead of black color I get blue color so this isn't related to the text field style because this is textile textile is always related to the style of the text so from Context we can understand that this isn't what we want although we can convert it to White because the black color over here used to look bad then we can go ahead and look for something else and the thing we are looking for is not mentioned anywhere over here is it well it is if you see over here we have a property called decoration which handles all the decoration related stuff in a text field and if you see it requires a type of input decoration and the default value of it is input decoration with nothing mentioned inside of it so we can just go ahead and add input decoration and now input degradation has a lot of configurations you can do why again it is similar to the textile textile encapsulated all the properties related to a text styling which we can use anywhere outside of text also right so text style could be used over your textile can be used over here as well in a text field so similarly decoration is there where it requires input decoration and we can pass anything to an input declaration which encapsulates a lot of properties there's icon icon color label label text and many more things so let's go ahead with label because this looks something we would want and this label requires a widget so we can pass let's say a text saying please enter the amount in INR because I am building a currency converter which changes the amount from INR to let's say USD all right or we can do the reverse USD to INR okay and now if we see over here we have everything showing up in blue color and when I restart the app we see please enter the amount in USD over here written in black and when I click over here it goes right at the top in blue color it's not really legible but yeah this is what label is let's go ahead and make some changes first of all I want this to show up in white color so what I can do is style textile then I'll pass color to it and the color will be colors.y again then we can save it and we come here it's now written in white color so we can see it in white color now if I click over here again this is white perfect but is that what we want I don't want it to be like this for example if I restart the app I don't want this label to be present over here when I click over here the label should start disappearing you know when I type anything this label shouldn't be there right at the top because it doesn't look good it's not a small word that can stay away it's kind of like a big sentence and it doesn't look good here so it's definitely label is not what we want as of now later on maybe in some part of your app you can use it but label is not what we want over here then let's look at other properties that might help us label text here we just need to pass in a string instead of the entire widget now you might ask why do we have these two different properties over here that's because label requires a widget and you can literally pass any widget to it it's not necessarily a text that you need to pass in it can be anything but with label text you need to pass in a string otherwise you don't have to pass anything so that's the difference with label you get more customizable options with label text you don't get those customizable options however in our case we could have used label texture then we had something like this let's remove the text and only a string over here and when I come we are back to normal we don't have any white color or anything so to add the white color we could go ahead and use label style which requires textile so instead of using a text widget we use two properties over here and it would result in the same output okay then this is all floating label all of that stuff basically how do you want your label to look when it's over here floating in the air right then you have helper text let's go ahead and replace label with helper text and see what it does and here you see it says please enter the amount in USD below it doesn't give me a label kind of thing and when we restart it's the same thing just mentioned over here so that it could give us a hint or kind of like help us to know what is to be done over here but still this doesn't look good for our use case so let's find something else then all of those to helper style related stuff is there and then we have the error text so whenever you have an error related to a text field what should the error show and how should it be shown all of that is written over here again not what we want then we have prefix icon which we'll get to after we are we've added the right text that we want and the right text we are looking for is hint text all right I'll tell it to you right away otherwise we'll be scrolling through a bunch of properties given to us by flutter so that we have full control over the UI which is a good thing okay now let's come back here put a hand text and then we have please enter the amount in USD save it and we have it over here when I click it doesn't go at the top it's not floating anymore it's just there and when I start to type it disappears and when I come back to normal when there's no text again it gives us a hint of what has to be mentioned we can also configure the Style again and then pass in textile and then we need to have a color let's say colors is colors dot why save it come back over here and this might look good or this might not let's try a different shade over here so we have white and then a bunch of different shades related to white white 10 white 12s y24 and so on let's go ahead and drive by 38 save it it's kind of like gray but I don't like it that much maybe White not 12 wide 60 I think I'll go ahead with this it's not exactly White so the entire focus is not over here but it does its decent job good enough and now you might have noticed that when I don't put commas between all of these properties the formatting of the text or the code goes wrong for example when I put a comma here and Save there's a good formatting done however when I remove the comma all of these brackets come together so comma helps with indentation and formatting in our code by indentation I mean you see how bodies written over here then their Center then there's a gap this Gap is known as indentation this helps us to know what kind of widget tree we are in for example this Collins children all have are in the same line all right but the center has its own line over here these lines can help us to know where we are in the widget tree and that will help us a lot when we especially work on bigger apps also you can see these comments right over here which tell you that hey this is the end of the textile this is the end of the input decoration this is the end of text field this allows you to quickly know where you are in your code and add stuff quickly so we have our text field over here that's good now what I want is an icon over here that says you know a money icon kind of thing so it's like a dollar that shows that hey you need to enter the amount here so that people who don't know English can follow along what they need to do so here in our input decoration itself we have a property where that we saw prefix icon right so if we type prefix there are a lot of prefix stuff prefix which requires a widget prefix icon which also requires a widget then prefix icon color prefix icon constraints prefix style and prefix text so prefix text is you know what if we just pass string over here and let's say hello save it you see prefix text is the text that shows up before the normal hint that you have and also when you type something the prefix icon stays there but the hint goes away and a cursor also starts after the prefix icon or the prefix text but prefix text is not what we want what we want is prefix icon or prefix touch it so we can go ahead and use prefix but here what will a prefix be I need to add an icon over here how do I add an icon is there a widget for it yup which is icon icon is another widget if you press command you'll go in the source code class icon extends stateless widget so you can add your icon over here but the icon requires a positional argument of Icon data what is this icon data well let's pass it I can data and when you initialize this it asks you for some code point and this code point is basically used to create what kind of Icon you want now you can ask your AI assistant to create some code point for you but we are not going to do that because I myself don't understand most of the stuff inside of eichen data like there's font family which you can easily understand font package but what is code point and how do you figure it out right so let's ignore that icon data is not meant for people like us it's for advanced developers and if you want to become one you can just go ahead and Google about it however what we can do here is pass icons why because if you click over here with command abstract final class icons can be put inside of an icon widget and with this icons class we have a lot of material icons you can see all of them over here and when you click on this Arrow right here not anywhere else just the icon you'll be able to see the icon preview so we have ABC ABC outline ABC rounded and a lot more stuff you can just go ahead and see what you want I want a dollar sign is there something related to a dollar sign not really so we can skip this let's go back and try something new so we have icons Dot Money related stuff yup money is there then there's money off and money off is a dollar symbol with Slash on it so maybe money underscore on is there without a slash symbol but that's not the case clearly so we cannot use anything like that so you need to experiment over here to find your icon otherwise you can just go ahead and Google stuff but if I just do icons dot monetization on I see this dollar sign now if I put monetization on draw outline I get it just outline then rounded then Sharp then there's money so let's go ahead and see what all is there in modernization and this is all that's there so we're going to go ahead and use this also put a comma so that formatting is there cool so a comma is required before every property mentioned inside a class but it's not required when you have like multiple parenthesis together okay so you can have it like this but obviously Comma just makes stuff better and it's more readable code so let's see if this come over here we have our dollar symbol showing up which is nice now instead of using prefix what I'll do is go ahead and use prefix icon to see the difference and you see prefix icon properly places it like a icon because this prefix requires a widget and you see prefix icon does the proper job of putting an icon before it so it leaves some margin from here you can see there was a lot of spacing added then this icon was properly placed in the text field not above or below and took the default theme of our app which was the blue color so I can obviously go ahead and change the prefix icon color this requires to be a type of color so I can just have colors dot maybe black not black let's go ahead with white again yup and if you want you can just make this outline so you get an outline icon over here perfect and if you want to match the color present over here and color for the icon you can do that so let's copy it and paste it like this save it and this looks better because both of these things are merging with each other you know good stuff now instead now what if instead of I adding my icon over here I want to add it right at the end what should I do then so for that we have similar properties called suffix suffix icon and all of that stuff same things so suffix will make sure your icon is over here and suffix icon will properly place it then we can put suffix I can color instead of suffix icon and then you know you get the same things so instead of adding the icon in the left hand side you have the icon now in the right hand side so it's prefix and suffix right but but in our app it doesn't make sense to put the icon over here so let's shift it in the left hand side let's put prefix icon here I'm just pressing command set to go back then I can have prefix icon and prefix icon color this looks good now the next thing that I want is my text field to be colored I don't want it to be transparent like here I want it to take a white proper color so for that I'll have to go ahead and add another property which is let's find it and we see a property here which is Boolean filled color filled color color Focus color color hover color so let's go ahead and pass fill color and our color is going to be colors.y let's save it and we don't see any changes maybe we need to hot restart so when we hold restart we still don't see anything why is that the case well that's case because you've mentioned the fill color and it says that is the base fill color of the decorations container color now maybe you don't understand it but it basically is the right property to color it but before fill color we need to add filled set it to true and then only we see the white background right now this looks good does it but now since we've made it white everything has disappeared from here all the white 60 and all of them have gone so maybe we can shift them to Black so I'll change the icon and the text to Black again and we see the right thing now this looks much better however if you just zoom in or I'll just zoom in for you by taking a screenshot to take a screenshot on the screen you can press command s so you basically save the screenshot now I've taken a screenshot and when I zoom in you'll see there is a blue background over here not a blue background you can see but a blue border color now how do you remove that blue background color and you know replace it with something you want in my case I'll be happy if it is this color the background color of the scaffold or just a white color so that it merges with all of that stuff so let's look for something border related in our input decoration and we do have a bunch of properties just related to a border let's go over them so if I put in Border there's a border property but we don't have to be concerned with that I'm just going to skip that one and we are going to focus on the focused border why because Focus border is a border that displays when the input decorator has the focus and is not showing an error so what is that thing well right now my border or my input or my text field is not focused when I click over here there is a blue border that shows up correct that is focused border so I just need to use that so I can just have focused border and then I can pass an outline input border then I can just pass an input border the thing that it requires so I'll just go ahead and pass it in over here but as you can see it gives me an error saying abstract classes cannot be instantiated try creating an instance of a concrete subtype basically input border is an abstract class so I cannot use that so let's remove that and find a class that basically inherits from input border so basically extending from input border so you need can type input border and we do see two type of classes here outline input border and underline input border let's go ahead and use outline input border first then save it and now if you see the color of when it is in Focus has changed it has changed a little bit right if I just restart the app again I click over here you see it kind of enlarges and then there's a thick black border showing instead of a blue water why let's take a look at the properties of outline input body to understand that there's Border Side border radius and GAP padding let's take a look at Border Side so if I pass in Border Side it requires a type of Border sites I can just go ahead and use Border Side and when I go over Border Side this class has its own bunch of properties it has color width style and stroke align so the first one is color which has constant color of 0x FF and 6 zeros so how do we understand what color this is to understand that let's understand the format the colors are in so every color in flutter has a type which is like 0x aarr GG BB so first you need to mention 0x then you need to mention that Alpha values then the red value then the green value then the blue value so here we have 0 x FF 0 0 0 0 0 so that's 0x then Alpha is FF then we have two values for r two numbers for G and two numbers for B that means we have RGB of 0 0 0 that means we have a black color and that is why we have a black color showing up over here since the default color of the Border Side is 0x and when we first create an outline input border by default it creates a Border Side instance that is why the color is default by black but we can change it so let's go ahead and change it we have colors dot let's say White or colors.red let's go ahead with colors.red then we come over here and there's a red color showing up now the red color is quite small right so I can increase its width so I can pass the width as let's say 10.0 come over here and here it is a massive width over here now I don't want that much let's put it out to and this looks better then we have style so what style of the Border do you want and this requires a type of Border style so you can have border style dot none or solid so let's have border style dot none and then there is no border at all but if I put solid it puts a solid thick line here and then there's stroke align which has a value of stroke align inside so we have stroke align but stroke align requires a double value how can you pass in stroke a line inside well that's because stroke align inside is a property mentioned inside of Border Side itself so we have Border Side dot stroker line Center border sites dot stroke align inside and Border Side dot stroke align outside that is why in stroke align you see stroke align inside however when you jump inside here stroke align inside is a value stroke align Center is also a value and stroke align outside is also a value this is negative one this is zero and this is one displaying where you want it do you want the border to be inside in the center or outside let's take a screenshot of this emulator to understand it better to take a screenshot you just have to press command s and that will take it and then when you scroll inside you'll see that this is the part where our text field is ending and our border is displaying inside if I want it right in the center or outside where the text field gets over I can do that so I can just have border site Dot stroke align inside stroker line outside let's put stroker line outside and you see the difference now it is at the outside it doesn't feel inside now this is a very minor change but it does affect the UI a little bit let's put some commas and there we go now I'm just going to remove red because red doesn't look good I'll just put black because black looks solid and now let's exit this because I wanted it outside and that's good or maybe we don't want it outside we can keep it inside perfect now the next thing is whenever I type something it shows up in white color so I need to change it to Black again so I can just have the style over here the text style which is related to what the user enters to colors.black and now when I type anything it looks good perfect the next thing that you might want in your text field input is this thing right here is slightly curved you want it completely curved like it shouldn't look very rectangle it should look something like this right so if you want that kind of text field you can change that by editing one property which is the Border radius so you can pass border radius over here and Border radius requires a type of Border radius so you can have border radius but if you do this much it's not allowed because border radius if you go over there doesn't allow you to go because border radius has a Constructor that is private however when I remove the instantiation I only have a type of Border radius so I can click and go over there but if you see border radius Constructor is not present at all a class of water radius is present but there's nothing related to Bod radius Constructor also you'll see some new stuff over here you have border radius dot all and that is not a static method why because it's named after border radius and Border radius is the name of the class so that means it is a Constructor and this is a named Constructor not the named argument Constructor but the Constructor has its own name that you can use so we are going to use exactly that we are going to have border radius Dot and it has a lot of stuff 0 which basically eliminates the entire body radius now you see the curve is gone it is a perfect rectangle but that's not what we want we want border radius dot all so in all the directions of your text field what border radius you need to put in horizontal so from the left hand the right side what you want only so from top left side from top right side what you want so horizontal basically allows you to have a little bit more customization than all and only has full control over your entire text field then you have vertical so you have top and bottom circular so you want to create a border radius where everything looks circular and then you have look which is linearly interpolating between two border radius objects but you don't need to care about it that much you can get most of your stuff done with these five things let's go ahead and try border radius dot all 10 and then save it but if we do this we get an error why because this requires a type of radius not an integer so we need to remove this and pass radius and it's a positional argument so you can just pass in radius and again radius Constructor is not defined you have to use radius dot something so always whenever you want to figure something out because obviously you'll find out later on that there are so many widgets you won't know everything about them but you can always know what all properties they need and it's in very English language there's nothing very UI related language that's mentioned over here that you can't understand so you can just figure out by doing this radius but it doesn't resolve the error because its Constructor doesn't exist so let's try to do something with radius Dot and yeah we do get options for that and you see here we have image descriptions for it what is circular what is elliptical what is love but we are just going to go ahead with radius dot circular and pass in 10 which is what circular requires a Double Radius value then save it become aware and this is more rounded but we can make it more rounded by having 40 and you see this is proper input that one might require then we can also pass in 60 and this makes it even more circular so you get the point now let's try something else we have border radius Dot horizontal and from the left side we are going to have radius dot circular 60 okay let's see what happens you see from the left hand side there is this radius but on the right hand side it's strictly edgy and if we do it for right we have right dot circular like this so this is pointy a perfect rectangle and then we have Circle over here so you can create a bunch of things like this with horizontal with vertical in vertical you have to mention top or bottom you can pass in top and it's something like this then you have bottom where you have something like this so you can try a lot of stuff and maybe it looks cool sometime maybe it doesn't but I'm just going to go ahead with border radius.all because that's better in my opinion a standard way now you can also try to put only here and go ahead and configure everything for top left top right and everything but you get the point I'm not going to dive much into this now and now finally if we try circular circular gives us an error because circular doesn't require radius it requires a double value so let's remove this and put 60. is that fine not really it's giving us an error why we have put a double value right well that's because if we go to the circular part every Constructor here has a const constant border radius dot all constant border radius dot vertical constant border radius dot horizontal but it's not border radius dot circular with a constant it's just border radius dot circular that's why this isn't a constant Constructor and right at the top we have mentioned return constant scaffold since we have returned constant scaffold all of its widgets need to be constant like Center was a constant and column was a constant and likewise even text and textile text field textile everything was a constant but finally we have something which is not a constant so what do we need to do we just need to remove a constant scaffold from here put a constant text put constant textile put constant textile over here put constant Border Side and that's all our error gets fixed and we need to put constant for every single widget which is a const but since this wasn't a const We cannot put constant over here or on any widget here if we put constant aware that won't be allowed We cannot put constant on any parent widget for Border radius the parent widget will be Border Side outline input border not border side only out or outline input border input decoration text field column Center and scaffold so you can't put constant on any of its parents widget parent widget is whatever widget border radius is in and it's in outline input border input decoration text field and stuff like that okay so I hope you understood that we are going to know more about constant and why it's required after we have built a successfully working application but for now just follow along and use constant every time now if we come over here it's the same output border radius dot circular 60 has the same output as borders hook radius dot all radius dot circular 60. all right because at the end of the day we are just saying from all the edges you want to put a radius that is circular which is 60 and Border radius dot circular also says that from all the edges you want to put circular which is 60. okay so it's the same thing however I don't want any of that or maybe I do want border radius dot Circle let's say n or maybe 5 and that will be good enough for me and we are pretty much done with everything but if you see one thing when we restart our app we have our text field looking a bit weird and when we click over it it enlarges and it just feels very weird you know so what I want to do is make our text field look like this from the start okay when I click over here when I have the focus and when I don't have the focus it should look the same thing so for that we have a different border property which is enabled border when I put enabled border it also requires the same thing input border and since input border is an abstract class I cannot use it but I can use underline input or outline input what is underline input underlined input if we just instantiate it and restart our app we can't see anything visible but if we take a screenshot come over here and zoom in you'll see there's a border only in the bottom there's no border at the top there's a border only in the bottom which is black which is what underline input border is instead of having borders everywhere like you have an outline input border you just have an underline border and then you have board properties related to it which is Border Side which we've already looked at over here then it has border radius which we already saw and that's it no further customization so that's not what we want what we want is this outline input border so I can just grab this press command C to copy it and paste it over here also put a comma so that formatting works and when we come over here you see when I click over here and when I don't click it's the same thing but yeah this makes my widget look very big so what I can do instead is in my build function itself I'll create final border which is equal to this outline input border that I just saved so at the end of the day this is a function right and in a function I can create my own variable which I've created a way up I've created a border variable and assigned it a value of outline input border if I hover over it dot currently correctly recognizes it now I can take this border and paste it over here I can take this border and paste it over here what this does is reduce the complexity inside my input decoration because I'm not writing big big stuff here which are the same thing and also whenever I want to change anything I can do it one place if I had two different instances over here and maybe I wanted my border style to have a width of 10 then it would be weird why because right now it looks normal when I click over it it looks very weird because I changed the stuffs in my focus border but I didn't change it in the enabled border I also need to change it over here right and then when I start it it feels the same thing so what I've done instead is created a variable border here then took this border pasted it over here pasted it over here and then whenever I want to change something I can just do it at one place and it correctly changes right so I hope you understood that and this is a build function this is a function where I can create any variable that I want and I've created it over here I can also create it over here in my class but it has some problems because this is a cons Constructor I've used body radius dot circular so I'll have to remove constant from here for it to work and we've already seen that const has performance benefits so you should not remove it from The Constructor of a widget at least as much as you can and we can avoid it by putting this in the build function so why not but yeah one thing to note is don't put any complex task inside of this build function yeah you can put variables and you can put functions that are not expensive that means that they are not doing big big stuff like putting an asynchronous thing over here or putting a timer nothing like that needs to be done in build function build function should have a widget tree that is to be returned and maybe if you want you can put variables over here okay perfect so my text field looks good okay let me change my width back to 2.0 yeah so we are done with the text field and we have taken a look at a lot of text Field properties there are still a lot more that we can cover but let's not get into them so the design for the text field looks good enough I think we can exit from here but there's still two more things that I want to fix first one is this text field being too much in the corners all right I want some spacing to be there from here from here all right from the left and the right hand side and another thing is when I press command K while being on the text field we get our keyboard here okay when I press command key I get access to the keyboard if you're on Android emulator keyboard is constantly there on the Android emulator you see our keyboard allows us to put text related stuff here I don't want that I want to restrict it to numbers only you shouldn't be seeing text you should only be seeing numbers here so let's go ahead and put a property that will make sure text field doesn't allow you to put text only numbers so that property is not mentioned in input decoration input decoration is related to how you want to design and decorate your text field but this is not related to designing the text field it's related to one of the properties or functionalities of text field so we can click over here or hover over here and we'll see keyboard type we want to change the keyboard only right so we have keyboard type here which we can change so let's go out of the input decoration and pass in keyboard type and this requires a type of text input type so we can go ahead and mention text input type Dot and this is an e and this is a class that allows us to put multiple things so we have text input type dot date time so if you only want date related stuff and you can see on iOS it requests the default keyboard but on Android it requests a keyboard with ready access to this because iOS doesn't have an Android style keyboard and iOS doesn't have and Android doesn't have IOS style keyboard obviously so let's go ahead and see what we want we want number so we can have number and we restarted we click over here and we see only numbers that's good right however the problem over here is yeah I cannot put text but I cannot also put decimal points I want decimal points so let's find something else so we'll have number phone street address but we also have number with options so this allows us to put a decimal point if I save this much and restart the app come over here no changes however I do have two named properties that I can configure decimal and signed if I put decimal set it to True save it again we need to restart come over here we have a nice decimal point showing up over here 8.0 and if you want you can also set signed to True which allows you to put negative sign again we'll have to restart come aware and you see we get all of those stuff so basically we get all the alphabets and everything but our keyboard starts with showing a number but that's not what I want so I'll just set decimal to true and set this as constant because this has a constant Constructor so yeah let's restart the app and there we go perfect now the second thing that I wanted is the padding over here or the margin to be left from the left side and the right hand side some spacing needs to be there but I cannot do that by using one of the properties of text field why because text field doesn't have those properties it doesn't have anything related to margin padding all of that stuff but that's not the case it does have something related to padding which is scroll padding and if we see in decoration because we are decorating the text field only we have content padding but those are two things that are related with inside of the text field with content padding basically you can set padding such that you can leave space from here you can make sure that your text field looks bigger and this text has more padding to it so this text field will appear stretched but that's not what we want and the scroll padding is nowhere related to what we want it configures a padding to edges surrounding a scroll level when the text field Scrolls into view nothing that we care about so we can exit this so text field is not giving us any property and rightly so how can text field give us a property related to the outside for that we'll again have to wrap our text field with other widget and what is that widget well it can be padding or container widget let's take a look at both of those widget padding and container so I'm just going to wrap my text field with the padding widget and for that I don't have to write padding and all of that stuff what I can do is press Ctrl shift r which brings up a set of refactoring options or you can just press right click refactor and then you have access to the refactoring option and here you can wrap with the widget you can wrap with a builder other widgets that are present and then you also have container and padding so let's wrap it with padding and you see there's padding then the padding property and then a child set correctly configures itself so we don't have to do much task with it then we save it and then there's padding so what's happening over here is there's text field text field usually takes up the entire width of the device or the entire width that it's given but here you are restricting it to take the entire width that is provided by adding padding and padding is the amount of space by which to insert the child so basically text field has a habit of taking the entire screen you're saying that hey you cannot take the entire screen and you're restricting it by putting a padding widget which eliminates 8 pixels of screen size and also padding requires something known as agencies geometry but if you just do Edge in sets geometry it won't allow you because it is an abstract class but Edge insets extends its agent's geometry so you can use it over here now you see how the entire flood of framework is built on the concept of inheritance encapsulation all the object oriented programming Concepts that we learned about but anyways this is good and I think this is a nice start agencies dot all eight is quite good over here and it looks good however there are more properties on edge instance that you can take a look at agentsets dot all agencies Dot from ltrb which is from left top right bottom then you need to mention all of those things then you have Dot from view padding so you can set a padding based on The View padding then we have only so you can set left upright bottom now you might ask what's the difference between from ltrb and only well the difference is all the properties inside of only are optional you can pass them and you cannot pass them it's fine if you only want to pass left you can pass it and you'll be good right but on the other hand when you have from ltrb you necessarily need to mention all of those parameters you need to mention left top right bottom values you cannot skip any one of them or you can just pass in zero but yeah this is just more customization added for you but we are just going to go ahead with only not all why not all because when we leave with all you live by leave padding from your from here from here and from bottom as well when we add a button you'll see that but with only already symmetric where you need to mention the horizontal and vertical values you can leave spacing from year and year or from year and year so you need to set for vertical together and from horizontal together that means if I pass in horizontal 10 and save it from left I'm leaving 10 pixels from right I'm leaving 10 pixels but from top and bottom I'm leaving 0 pixel that's how it works and I think you're smart enough to figure it out on your own we are going to go ahead with let's say agencies dot all 10 because we need to leave some space from here and we need to leave space from below when our button comes along great this looks good now instead of using padding you can also use container so if I use container instead of padding it all works fine why because container allows you to set a bunch of properties it has alignment padding color decoration width height so it's like a one and all widget right it allows you to set multiple properties and if you just command click on container and just go to its build function you'll notice that container is itself made up of multiple other widgets like you might have seen the agent says geometry the padding widget so whenever we set the padding over here in our container you're basically using the padding widget only then we have the color where we are using colored box and when you see margin or constraints it is using a bunch of other widgets is what I'm saying now here you can set padding or margin now what is the difference between padding and margin to understand that let's take a look at the diagram if I just remove this will be able to draw something so let's say we have a screen like this maybe a better screen okay now this is where my app resides so this is my text that is displaying okay so I have my text over here now the spacing between the text and this container box is known as padding all right this thing right here is padding but this thing right here is margin so to explain it in a short sentence margin is related to stuff outside your container and padding is related to stuff inside your container but in this case the padding and margin will be the same thing so if we save it our text field decreases even further but in certain scenarios you'll see containers padding and margin property behaving differently especially when we have a container with a text inside of it and maybe you can check it out over here how let's press command shift R then you have wrap with container property and your you know you can just pass in a child then in the container you can first of all set the padding property which is going to be constant Edge and such whenever you have padding or margin related stuff you need to use Edge and sets then you have agencies.all 10 then you have margin of agencies.all 10 again this is going to be constant and then you can set a color property and the color is going to be colors.black okay let's save it come over here you see first thing to note is the container takes only as much space the font requires it doesn't take the entire width of the screen like the text field does it only takes as much space as it as its child requires only as much space as this text requires if I reduce its font size to 1 it will take only this much space if I increase its font size it will take as much space as this text requires even column did the same thing right we have seen that earlier container does the same thing so basically the child is determining how much the height and width of the container should be unless I specifically go ahead here and type height should be 400 which should be 299 okay then it doesn't follow the constraints or the sizing of text it takes the entire space however I'm not doing that because here I want to achieve a different purpose as you can see over here there's some sort of padding over here however when I remove this the container is squashed even further right with this padding I am determining how much spacing should be there over here but when I remove padding I'm not configuring anything inside but with margin I'm configuring something over here when I remove margin from here you'll notice that this goes down all right let's save it and you'll see the difference between this text field and the text size decreased because the margin is removed when I put back margin let's put all of them in one screen so that you understand this further and then when I save it you can visibly see the difference over here so that's the difference between padding and margin padding is related to the stuff inside and margin is related to the stuff outside I hope that was clear now let's maximize our code data and this looks good now also let's remove the color and the entire container property so I'll press Ctrl shift R remove this widget so I remove the entire container and its properties and we come over here this looks good now the next thing we want to do is add a button but I hope before going into the button you understood the difference between padding and container padding is just one widget and container is made up of many many other widgets and that includes the padding widget but I always prefer using padding when only padding is required you know I get to know what exactly is happening over here if I use container I'll be curious to know hey am I doing anything else in the container but anyways it depends on your preference there is no performance difference and now the final thing of our UI the button now how do we put a button over here so in material design buttons can be classified broadly into two categories one is the buttons which are raised and other one is where the button appears like a text all right so the race button is kind of like an actual button that you might see on any website appears like a text button is something that looks like a text but is actually a button so first let's take an example of how text button looks and then we can go on to the raised button so to create a text button we have to type text button how convenient and now it requires two arguments which is on pressed and child when I click on text button it automatically completes this for me and asks me to put the required arguments so for on pressed we require something known as void function and that can be nullable so basically we need to pass in a functional wire and we can take the advantage of anonymous functions that allow us to create a function over here so this function does not have a name of its own but it is a function kind of like a Lambda function in Python if you've coded in it then we have a child which requires a widget now why do we require a child in a text button that's because there will be a button but what should the content inside a button be that's what child requires so we can pass a text wire which says click me all right now I'll just put commas so that there's nice indentation now I'll come over here and you see click me is shown over here and this acts like a button why because when I long press over it it gives me a splash effect that you can see in the blue color that's a button now if I click on it nothing happens that's because in this function we have not done anything so in our function over here we can pass let's say a print call so we'll go ahead and pass print here and says button click we already know what a print function is right and here I'm just saying that whenever this button is pressed I want the print statement to be printed out in the console so I'll press command J to open my debug console again now I'll just restart my entire app come over here click on this button and you see button clicked if I click it again I see two written over here that means button was clicked again now if I again click there's three times button clicked so this is what this function does whenever you click on it it runs the particular function and it requires a type of only function you cannot put some integer value over here or some string value over here or whatever you cannot do that because it is of the type function like this and it returns a void so you don't have to return anything from here like this you can just do this or you can just leave it because that's void now let's see why we get these two errors this error we get because we have to put a const before a text this text button does not require a constant now you might ask why why does it not require a constant when this is has a Constructor of constant that's because we have this function over here whenever we have a function to be passed in like this it cannot be a constant button to prove this if I just remove on pressed you see we get a warning here use const with the Constructor to improve the performance but then we also get an error saying the named parameter on press is required so this is the reason why we have to put a const for the text if const for a text button was allowed then we wouldn't have to put a constant for this text I've explained this to you before and let's go ahead put a constable now why are we getting a warning over here and one problem I have with warnings is that I have to hover over them to understand why the warning is there in the first place so what can I do such that my warnings are seen over here I don't have to hover over a particular thing and see the warning so for that we have a vs code extension we can go to the extensions tab type your error lens then we have to choose this one given by Alexander we can install and now you'll see your errors and warnings are seen in the same line so this error lens makes sure that all your warnings and errors are seen in the file itself and you don't have to hover over them I just prefer this way because I get to know instantly what the warning or error is and it says don't invoke print in production code try using a logging framework and this error is there because of a certain thing known as lint which I told you I'll cover later on now if you again go to analysis option.aml you see include package flutter lens and that is coming from the dev dependency flutter lens surveyor what flutter lens does is encourage good coding practices you can see that in the comment over here now you can set your own coding practices in the analysis option.yaml file where you have the linter for example if I an uncomment this line so I'll press command slash to uncomment the line then I'll click on command s which saves the file and come over here the warning for print is gone even if I open the debug console in problems there are no problems because here I've set a rule saying that avoid printlint should be set to false if I set it to True which is by default and come away I get the warning again and I'm not going to meddle with the preset lint which tells us to not use print and production code and that's simply because if you print stuff out you can also print some confidential information and because of that your users might be able to see it if they have rooted devices or they figure out a way to do so so definitely we are not going to use print like this there are two options to use print now either you can go ahead and use debug print the difference is debug print requires a string only you cannot pass anything to a print statement like we could in print because it required an object and we already know object is a superclass of all the data types we know so now we can use debug print and that removes the warning for us or what you can do is pass an if check over here and check if we are in debug mode only then do we want to print this now what is debug mode now there are three types of mode in our applications debug release and profile right now we are in the debug mode basically just testing our application building new features and all of that release is how your app will look like in production and profile is a mixture of debug and release in release you won't be able to see many error messages or later on we'll see that when we add some other packages they also print stuff out we won't be able to see that in release mode we can see that only in debug mode now what profile does is run the app and release mode but give us our nice error messages warning messages if there are any and basically print is saying that hey you can only use me in debug mode so now that's why we are put debug print now we are saying that hey if we are in debug mode now how do we check if the app is in debug mode or in release mode to check that we have K debug mode given to us by flutter now if you see this is coming from the package flutter Source Foundation constants dot dot if we press command and go inside you'll see K debug mode is equal to not release mode and not profile mode that means debug mode is when it's not a release mode or profile mode so it's definitely a Boolean value and if it's a Boolean value we can just pass an if condition like this and print it inside now the error is gone because we are printing in the debug mode in release mode we won't be able to see the Sprint message now you might be asking hey that's fine now I understand this but how do I run my app in release on profile modes to do that you can simply go to the terminal and run flutter run dash dash release to run it and release mode but release mode doesn't work on iPhone simulator you can run it on an iPhone actual device and same goes for profile mode you cannot run profile mode on an iOS simulator so what I'm going to do is at the end Maybe we'll try to run it on real devices and see how it feels cool so now that we are done let's get back to our text button and let's improve the design over here first of all I want this text to say convert instead of saying click me so to change that I can just change the text over here and have convert save it and when I come back over here it's convert cool next thing I want to do is make sure the button background is black so to do that I'll have to use one of the text buttons properties now let's take a look at the properties text button gives us it gives us on pressed which is a required argument on that we already filled that then we have on long press so what should happen when you long press the button what should happen when you hover over the button by hovering it means when you just have your cursor on the top of this button this is especially used in web applications because sometimes you might want to change how your button looks or how your entire UI looks when you hover over a button then there's on Focus change what happens when you change the focus then the style that's what we are interested in right even for the text we had textile property even for the hint text or label or prefix everything had its own style so we can focus on style over here as well so that's what we want let's go ahead and put it over your style which will be button style exactly what it requires and we can create an object of the button style class like this now we have two problems here first one is the child argument should be last in widget Constructor invocations that basically means that whenever you create a new widget child cannot be over here it has to be the ending property all the other properties should go above child and this does not have any performance impacts but it's just readable code because basically you're in a widget tree right and if you have a text button it's good to see the last thing over here it's just a matter of preferences if you don't like this you can definitely go ahead and Analysis option.aml and make sure you add a lint so that you avoid this kind of warning you can do that and the next is we have to use a constant before button style so let's use it all right now if we do this much nothing really changes because we haven't provided any properties to material button Style now the first thing that I want to do is change the background color of the button so let's get access to the background color and it's not simple as it looks it doesn't just ask for a color it asks for material State Property with a generic type of color which can be nullable and material State Property is also nullable and that that makes sense right if we remove background color it works if we want to put a background color that also works so nullable makes sense and then if you want to pass a color you can pass if you don't want to pass a color you can't pass it now how do I make sure material State Property is added over here to do that let's create material state property and create an instance but if I do that it gives me an error because it's an abstract class so we cannot use material State Property however we have something known as material State Property all that we can use now if I come over here you see class material State Property all it requires the same generic type that our material State Property requires and it implements it so that's why we can use written background color now if you hover this it is smart to identify that it requires a property or the value of a color why because your background color required material State Property color and when we use material State Property all it automatically said hey use color so we have to pass in a color over here now what is my background color going to be well colors.black let's try that save it come over here and we have a button showing up the next thing I want to do is change the text style so to do that I can maybe try to change the textile property over here let's go ahead and try to do that we have textile then again we'll pass material State Property all then we'll pass a textile saying let's say color is colors Dot white maybe that looks good then we'll save it come over here and nothing really changes if I try to restart the app still nothing changes the reason for that is if you hover over this property it says the style for a buttons text widget descendants so we are doing the correct thing because buttons text widget descendant is our text over here but the color of the textile is typically not used directly the foreground color is used instead so we need to use foreground color and pass that in so we can have material State Property all then we'll pass colors dot White let's remove the textile property and let's see if that works become aware and boom that works we have a nice button displaying here and maybe you're satisfied with this UI but I'm not because what I want to do is increase the button's height and width and maybe the font size of this text as well so let's do that first we'll focus on the sizing so to increase the sizing we can do size and it doesn't really have a size property but it does have icon size fixed size maximum size minimum size and tap Target size icon size is the size of the icon inside of the button but we are not using any icons so we can ignore that then we have fixed size so what will the fixed size of the button be irrespective of what screen size we are on if we are on a smaller device or we are on a bigger device the size will remain the same so let's go ahead with fixed size and that requires again material State Property all and then we need to pass in something known as a size is size a class is size an enum what is it well size is a class it already gives us an auto suggestion if I tap over it it gives me two things to password width and height to pass a width maybe I can say 200 that should be enough and height will be 50. now if I save it come over here my buttons height and width both have increased but I'm not satisfied with how much the width increased I wanted to take the entire space just like the text field did so maybe I can pass the width as 300. then maybe we can try 350. still not enough so we can go ahead with 400 and that's enough but that's not all maybe we have to do 410 and that's enough but what will happen if I use a smaller or a bigger device or if we just take a different device altogether what will happen will the thing be the same so let's go ahead and try it I'm just going to call my pixel 6 emulator you can just call it like this you know just click over here start the pixel 6 emulator from here you don't have to go to Android Studio to start it now after this device is selected I can click on run run without debugging or you can start debugging whatever you want I'll run without debugging press command J go to the debug console you see we have a bunch of Errors over here but that's related to when we put a textile property for this button Style and then you see we have reloaded which is hot reload when we save it hot Reloaded but anyways I don't want to focus on iPhone emulator now I'll just change the device and focus from iPhone to pixel and now I'll see all the warnings properties calls related to my Android emulator okay and we see that it has started if we come over here there we go we have our app right here but that's the problem when we add 400 on a different device size it looks proper but on an Android emulator it looks different and if we open web it might look different on a smaller device we might even get an error why because let's say I put 450 over here because I want to cover the entire size so this is what fixed size means no matter what the device size is no matter what the device screen is this is going to be the size and it works fine you know it works well the problem here isn't about the fixed size property or any property that we are using it's about the fixed value of the width that we need to give is there no way such that I can give maximum value to the width how much ever it requires it can take well there is a property to do so we have double you know this double dot Infinity so if we click command click on double we'll go into the dot implementation of double and double is an abstract class as well but we are not instantiating the double clocks we are not doing double like this instead we are calling the static property of Infinity on it and infinity is one one divided by 0. so it's basically saying that take maximum amount of space possible and if I save on it right now and put commas come over here we get back our normal button because that's the maximum amount of speeds this button is taking in fixed size property but what will happen if I use minimum size minimum sizes that that you need to take at least this much size on whatever device you're on and if I save it there we go on both the screens our buttons are looking similar because they are taking the maximum amount of space possible and what will happen if I do maximum size and save it we'll get back to our normal button because what's it what it's saying is the maximum size of this button should be double dot infinity and 50. but if you can have this value you should take it but in the maximum screen device this is what the button should have but anyways we are going to go ahead with minimum size because that's what we want we want it to extend till the entire end of the screen now you might ask hey this doesn't look good I want there to be this spacing and we are going to tackle that the same way we tackled our text field we are going to wrap it with the padding widget so we are going to come to the text button press command shift r then wrap it with a padding widget and have Edge and such dot all 10.0 and there we go on both the device screens we have similar spacing perfect now you might have a question why do I have to wrap it with a padding widget why can't I do something like double dot Infinity minus let's say 40 because here from the left hand right side we have 10 10 so not 40 double dot Infinity minus 20 and then save it the reason for that is double dot Infinity isn't a value that you can count it is infinity it is an infinite value and you're saying that minimum size should be this double dot Infinity is saying that you can take as much size as possible on the screen and then if you do double dot Infinity minus 20 using Infinity minus 20 which is still Infinity so it doesn't have any effect over here that's why you have to use the padding also there is no other button style property that will help you to remove spacing from here either you'll have to set proper constraints but that will differ on every screen size or you'll have to make a way like using a padding widget using double dot infinity and all of that stuff so let's put a padding 10 again and this looks good on all the screen sizes perfect now this is what text looks like what will elevated look like then so this is what the text button looks like what will the raised button appear like so to configure that we can just go ahead and instead of text button have something known as elevated button and you see we don't get any errors because it requires the exact same things on pressed as a required property child is a required property and the same style is required all the properties are same on pressed on long press on Hover but what changes is the design year you might say hey there's no difference I cannot see anything but there it is this button right here is raised a little bit what I'm going to do is put this in a side by side view so that you understand this better let's come over here let's get back to text button save it and you'll see some sort of elevation is gone if I save it again some kind of elevation is there elevation is added by putting some sort of background behind it there's some kind of Shadow to it to show this elevation I'm just going to go ahead and Pass elevation 15 and elevation doesn't require double it requires material State Property double so let's go ahead and pass material State Property all 15 like this save it and you see there's more Shadow behind so it appears more elevated it gives a more you can say 3D view it's not exactly 3D but it gives a more 3D kind of effect that's what elevated button does and by default it has its own elevation Setter but text button does not have any elevation set so it's kind of like a simple flat button and the fun fact is elevated button was previously called as raised button and text button was known as flat button because elevated button was erased and flat and text button was flat but then they decided to change it in later versions of flutter so I hope you understood the difference between these two type of buttons now you can obviously go ahead and configure more in these buttons for example you can check the set the shape let's go ahead and set one so we have shape and that also requires material State Property all and then requires outlined border so let's go ahead and pass outlined border but there's nothing like outlined border like this because it is an abstract class so again we need to find something that extends outline border so for this we have multiple types let's go ahead with the one I know oval border you see as the name suggests it will be able to create an oval border also if you press command and go into the source code it over border extends Circle border which is another border you can also use Circle Border in your code if you just go here and use Circle border that will be fine but at the end of the day Circle border also extends outline the border so oval border extends outline border all right now if I save it come over here this is a button looks kind of weird then we also have the circle border you can try that then this kind of Border will look better on a button that requires an icon in our case we don't require an icon we just require a text but what I'm seeing is this might look something like this you can have an icon over here which will be icons dot let's say convert that's nothing like that so maybe icons Dot money just to demonstrate you see this looks good enough and when you add elevated button on top of it this will look much better all right so this is what Circle border can be used with over border might be there to create some different UI style I don't know why anyone would use oval border to be honest in a production ready app that needs serious attention all right then the other border that we have is rectangle border so we have three types of rectangle border beveled rectangle border rounded rectangle border and contain as rectangle border let's go ahead with the rounded rectangular border save it come over here and we have a button looking the way we wanted it to now we can make some advancements here because it requires Border Side border radius everything that we've seen before you can configure over here and all of that is named arguments for example you can just go ahead and mention border radius then you have border radius Dot circular 10 also remove constant here because as we know border radius dot circular isn't a constant put constant for everything so let's go ahead and put it save it come over here and you see this kind of design and this actually looks good I'm happy with this then we also have beveled rectangle border it also has a border radius property but we are just going to skip that save it the difference here is this is pointy instead of having arcs in the edges over here and the last one is continuous rectangle border let's save it if you want you can just go ahead using beveld rectangle board not be weld sorry rounded rectangle border and it will give you a good enough design now if you want to reduce the border radius you can do that also let's put some formatting in place by putting some commas and this looks good I'm satisfied so yeah this works well also I'm just going to keep the text button I'm not going to use elevated button now let's remove all the comments and yeah this looks good now you might see that they're spacing here between this button and this text field already that's there because of the padding property added here here we have added a padding property saying Edge in such dot all 10. so from all the sides there is a padding of 10 from the top from left from right and from the bottom that's why they're spacing over here so we are done with the UI but still you might be not convinced by what the style requires right because every single time we have to pass in material State Property all then mention the color or material state property or then mention the size material State Property all then mention the shape or the Border now that is a lot of tasks to do so instead of doing that we have an alternative what we can do is is do text button Dot and we have an option of text button dot style from by using text button dot style from we don't have to mention material State Property all for everything you directly get options to color shape minimum size fixed size maximum size all of those things so you can just go ahead and use text button.style from but since I'm lazy to type it all again I'm going to undo everything I did copy this line right here press command shift Z to redo everything so that I come back to text button dot style from and I'll just paste everything back now I can remove all the material State Property alls from here and just put the required colors and sizes all right so that will work as well but make sure you do it nicely otherwise you might get confused with the brackets and will miss one of the brackets also put a const here because size requires that and text button dot style from doesn't give us constant thing because it is a function functions cannot be constant right now if we save it like this come over here we have a text button showing as it is as it was before no changes but instead of having material State Property all for everything we have our sample colors and sizes passed cool so I hope you're convinced by this also if you have elevated button you can go ahead and use elevated button dot style from and it won't stop you you'll be able to do all the stuff great so we have a functioning UI now this is all that was required for our simple currency converter app congratulations on being done with the user interface we have learned quite a lot even if you think it's a small output so you can leave the user interface at this this looks decent enough but if you want to add something there's one element you can add which is an app bar an app bar is the header thing that we see right at the top you can add that so let's go to our scaffold it is not included in body right because it's a header why will header stuff be included inside of a body header is included inside of a scaffold there is an app bar so you can go ahead and pass an ABBA an app bar requires something known as a preferred size widget but yeah you can go ahead and Pass App barrier why because app bar extends or implements a preferred sized widget and preferred size widget implements a widget all right and if you see preferred size widget is an abstract class which just has one getter inside of this get preferred size and app bar implements that so we will come over here put an eye bar save it and you see our entire user interface is looking quite different that's because by default the app bar has a color of blue and that is something related to theming which we'll get to when we build our second application but as of now we don't want this to be blue or anything we just want it to take the same color as this background color so to do that we can change the background color and set it equal to colors.blue gray exactly what the scaffolds background color is but still we have this sort of elevation here so we can remove this elevation by setting the elevation property of the app bar to zero and once we do that the app bar is gone now you'll ask hey what's the purpose of adding an ABBA if you just wanted to erase it the reason for that is at the top I just want to mention currency converter so an app bar requires some sort of title and here we have a title it requires some sort of text right title is a perfect choice for it so we'll pass title here and it the title requires a widget so you can just pass in a text widget and say currency converter also put a constable here save it come back and we have currency converter display this is our app bar title in Android it shows up on the left hand side in iOS it is right in the center so you can use either of them if you strictly want to Center the title you can go ahead and set the property of Center title to true and if you do that it is centered in both the places and if you set to false it will be aligned in the left hand side for both of these devices also if you want to change the color of this textile you can change it by passing in a style textile what we've already seen before color colors dot black all right now if we come we have currency converter displaying like this but I don't like how it looks with the style so I'm just going to keep it like this good Abba also has multiple other options like if you want to increase the size you can add a bottom preferred size widget so that can be an app bar again and you'll be able to have two app bars then we have actions which requires a list of widget now what is actions actions is a bunch of buttons or a bunch of widgets that you can show in the right hand side corner over here so we can have actions like this and let's say you want to display a text here saying hello save it and you can show hello there now this actions usually contains icons and stuff so that you know if you want to exit the app or do anything else you can use that using actions actions is not used for displaying text now if you take an example of WhatsApp WhatsApp has a bunch of actions so it has the video calling icon the phone call icon and the more options I can all of those are actions then we also have leading this is also particularly icon or if you want to display an image but it's generally not for text what leading does is shows some widget over here and it only requires one widget actions can have a list of widgets just like a column but they are displayed in a horizontal Manner and leading only requires one widget now we'll get to all these properties later on when we build our shopping app but for now we don't need to get into it and I'm also satisfied with the currency converter app that we have till now now let's figure out how can I make sure my app functions right so when I've mentioned the USD let's say 1.0 to 8 and click on convert I want to convert to INR now how can I do that this sounds very easy all we need to do is first step is create a variable that stores the converted currency value so right now we have the zero the initial value of the variable is going to be 0 then whenever we pass something like 1.08 to it click on convert we'll multiply 1.08 to the standard exchange rate that we have let's say 81 because one USD is 81 so we'll multiply 1.08 with 81 and whatever answer we'll get we'll store in that variable so we the second step is just going to be to create a function that multiplies the value given by the text field with 81 or whatever exchange rate you have maybe you are not converting from USD to INR you're converting to some other value you can use that value not 81. then the third step is to store the value in the variable that we created right so we created a function that multiplies the value with 81 then we are just storing the value in this variable that we created and then we only have to display that variable sounds easy doesn't it so let's try to do this in our stateless widget so let's go ahead and do our first step create a variable that stores the converted currency value and also what I'm going to do is copy all of this and paste it outside of the class that we have I'm not going to keep it inside because it just obstructs my view and will make it difficult for me now what I'm going to do is go ahead and create a variable inside of this class so I can just go ahead and create a variable and result is equal to 0. but then we get an error saying this class or a class that this class inherits from is marked as immutable why because we are extending a stateless widget right and I told you in the beginning of the flutter section that the stateless widget is immutable any Fields inside of it cannot change and here we are allowing it to change because it is not a constant or it is not a final if we put Final End Result over here the error will get resolved but if we just put end result that means this value can be reassigned this is a mutable variable and it cannot be present inside a stateless widget so what can we do if we put final we won't be able to change the value so it doesn't make sense to make it final however what we can do is put it inside of the build function right if we put it end result is equal to 0 it will work fine because this is a function in function you can change the value but inside a class a global variable you cannot change the value if it's immutable so end result is equal to 0 is fine in this function now what I want to do is take this value from the text field and multiply it by 81 whenever the user clicks on convert now how do I get the value from the text field if I come over here does text field have any of the properties not really if you use on submitted which is one of the functions text field provides you'll see we get a value and if we try to print the value I'm just printing it not debug printing it because I'm going to remove this line and open the debug console come over here and let's say I type 1.2 convert button click comes on submitted is not triggered at all because on submitted is triggered when we click on return button from our keyboard once I click on enter from the keyboard we get 1.2 so this on submitted gets triggered when the text field is submitted and that's not the layout of our app if the user clicks on return that's fine or even then we can do something but when the user clicks on convert which is another button that we've given them then also it needs to get triggered so we cannot use the on submitted property then what can we use such that whatever value is present inside the text field can come to this elevated button meaning we want to get a value provided by the text field or the user input which is given to the text field that is available throughout our entire class because if elevated button can access it any widget can access it right so for that again we might have to create something in the build function or you can do that in the stateless widget itself what we need to create is a text editing controller so we'll go ahead and have text editing controller and you're just going to name it text editing controller which is equal to text editing controller now again we get the same errors that we did before but this time there's going to be a change we are going to call this final text editing controller but as soon as you put final aware you see we still have an error can't define the cons Constructor because the field text editing Constructor is initialized with a non-constant value we get this error because text editing controller if we click and go to the source code is not a constant Constructor so we'll have to remove constant from here that means we'll have to remove constant from the material app and as I've told you multiple times before it will not help in boosting the performance of our app and I tell you why when we get into another type of widget in a few minutes so again this text editing controller needs to be shifted at the top we can put the constant back and the constant is here as well great now why is this text editing controller constant because text editing controller's value is not going to be changed we just have to take this value and paste it inside of our text editing text field you see we have a controller property we can pass it over there so we pass that text editing controller paste it and there we go now through this text editing controller will have access to all the user inputs so if we come over here in elevated button let's remove all of this and we'll print text editing controller if we just print that we'll get something like instance of text editing controller because text editing controller is a class right however let's try this I'm also going to go ahead and restart the app I'll enter the amount so let's say 1.5 convert and we get text editing controller and yeah we are able to see all of the properties inside of it so we have text editing value with the text and the text is 1.5 which is correct then the selection is there then text Affinity is there composing is there and all of that stuff what we care about is text so we are just going to access that so you're going to have text rating controller Dot and we see we have text we can use that so this will give us the text that we require now we'll come here again press 1.7 convert Ctrl J and we have 1.7 so it correctly gives us the right answer in the elevated button that's good now what I want to do is print text editingcontroller Dot text into 81 let's say that's the current exchange rate from USD to INR it's a rough value obviously but let's go ahead with this let's restart our app come over here we are going to type 2.5 convert and here we see 2.5 to 0.52.52 so this is not what we want why is that the case this is the case because text editing controller.txt gives us a string and we have already seen in the dot course that string into an integer will multiply the string that many times so we have 2.5 2.5 2.5 written out 81 times it's not actually multiplying but it's just concatenating adding the strings together so what we need to do is convert this integer or convert the string into an integer and then multiply it with 81. so we can have end dot parse and actually we cannot have just in dot paths why because n dot parse guarantees us that we'll get only an integer but what if a double is mentioned over here like 2.5 so we'll have to make this double dot parse and then wrap our text editingcontroller.txt like this so what double dot pass does is convert the string into a double and integer dot parse converts the string into an integer okay so let's try to do this press command J come back over here let's type in 2.5 again click on convert and we have 202.5 which is correct 81 into 2.5 is 202.5 perfect so that means you are getting a value now we just need to store this value inside of our result variable so let's get rid of them we are just going to go ahead and type result is equal to double dot pass text editingcontroller Dot text into 81 but now if you see this we get an error why because a value of type double cannot be assigned to a variable the variable of type integer and that's because the result is an integer and this is converted to a double and double into an integer will give you a double so we'll go ahead and change result to a double correct save it come over here and we have successfully changed the result now if we see this we should be seeing 2.5 convert and this text isn't changing why and we are no longer getting the print statement we are not getting the print statement because we have removed the print statement from on pressed but we should be seeing the change in text right not exactly because in text if we go we still have a hard coded 0 mentioned over here hardcoded 0 is not what we want we want result to be mentioned over here so we can go ahead and pass result and now we get an error saying argument type double cannot be assigned to parameter type string because text requires a string and result is a double so what you can do is result dot to string and that will convert text to a string right so to summarize to convert from into string you have to do the integer value dot to string anything you want to convert to a string you just call the two string method on it because that's present on almost every object and if you want to convert from string to int or double you do string value and wrap it with n dot parse or double dot pass all right let's see with this but you're still getting an error arguments of a constant creation must be constant Expressions the reason for that is this result variable is changing right this is a mutable variable it's immutable aware and it's mutable because of that so it's saying that hey result is mutable so this text cannot be a constant can it so we'll have to remove this constant we'll have to put constant textile save it and we still have a warning over here you can see it over here so let's go at the top and see we have this warning which says unused import basically saying that this line you have imported but it isn't in use in your code so we can just remove this save it let's restart the entire app and Hope that this works so we'll go ahead first of all we can see the change 0.0 because this is a result double value double to a string will give you a string like 0.0 then we'll enter the amount in USD let's say 4.5 convert and nothing changes inside over here why if we press command J there's no error as well it should be changing right not exactly because right now what you've done is created a result variable you've changed the result variable over here but you've not told this function to rebuild so the result value has its own new value all right there's no disagreeing with that the result has a new value but this function is not rebuilt again if this function is not rebuilt again we don't see the changes over here just think about it we have a result variable at the top then you change the value so the value has changed now what that's the end of the function that's the end of everything now what should the function do exactly the function has nothing left to do and it doesn't automatically see the new value compare the new value and display it so we need to make sure that we call this build function again so how do we call this do we go ahead and call build like this and hope that works so let's go ahead and try it so we are going to have please enter the amount in USD we are going to have 2.5 click on convert and still nothing changes it's just not calling the build function again let's go ahead and try it so in our build function what I'm going to do is print rebuild all right so right at the top of this function whenever this function gets called we're going to go ahead and call the rebuild function so that will let us know if this function is being rebuilt so at first this function is getting rebuilt right because as soon as we extend the stateless Widget the build function is the first thing that is called when you instantiate this now the first thing the Constructor gets called First and after that the build function is called and the build function is called automatically that's why we get the rebuilt first but then when I put the value let's say 2.5 click on convert the rebuild is now 2 that means this is getting rebuilt so why are we not seeing the output we are not able to see the output because this function runs again and as a result double result is equal to 0 so it gets re-initialized to zero the text editing controller is now remade and everything else is also rebuilt so the entire thing is rebuilt as a result the result is still zero we are not able to see the changes so what should we do to get rid of this error maybe try creating a global variable try creating it outside of this class so I'll just have double result is equal to 0 like this and maybe that works so let's restart the app and have 2.5 click on convert and we are still not able to see the answer press command J there's no error there's still two rebuilds so this doesn't work so let's get back to normal and just don't ever try to create Global variables unless it's really required because Global variables are bad I've already mentioned why in the dot section its value can be changed from any class any function and if you have like 20 for a small application 20 classes you will be able to change results from everywhere and that's not a good thing because you might get confused at some point and change the value anyways now what should we do to resolve this well the main reason for all of this is stateless Widget the build function is not meant for any initializations like these it's all fault of the stateless widget and it's not exactly a Ford of stateless widget as well it's a fault of us because we know stateless widgets should not have any state and we are still having states away I did so much so that I could explain you why the stateless widget is immutable and why you cannot change any of the output on the screen in a stateless widget so what is the thing we should do to resolve this well extend it to a stateful widget as simple as that so I'm just going to create a new class so that we see the difference between a stateless and a stateful widget so we have a class currency converter material page and I'm going to call this page G all right now we have the error in main.dot file but we don't care about it as of now I've just renamed this class to PG so that I can create a stateful widget with the name currency converter material page now I'm just going to go ahead and extend a stateful widget now as soon as I do this I again get errors because it requires methods what is the method is it the build function no it just requires one thing stateful widget dot create state so we need to implement a create State function if we go in stateful widget and scroll down we have state create state that is what we want to do so we are going to have state create State and then we want to return a state now what is the state can we just return a state like this no because state is an abstract class and in this abstract class we have the widget property we have our build context we have something known as mounted but if we scroll way down you will also see a very familiar thing here and that is the build function so that means we have to go ahead and create our own class that will extend the state class because then we'll have a format that is similar to this thing right over here because we'll have access to build function so now we are going to go ahead and create a class and I'm going to call this currency converter material page State and that is going to extend state and see here how what I have done I've marked this as private class why because I don't want this class to be accessible outside of this file only this class should be accessible outside this class should not be and now I can copy this paste it inside and our errors go away because I'm returning a straight right if we extend State class and return this currency converter material state we are returning a state I hope that makes sense we still have warnings but we'll resolve them later on now what it requires is a concrete implementation of state DOT bill and it's the exact same thing as this thing so you can have either it override widget dot build and then we can return let's say a constant scaffold so we have basically two classes over here first one is currency converter material page that extends a stateful widget and as a result we have to create the create State method and here it requires a state but we cannot create an instance of the state class because it is an abstract clause and the abstract class is basically saying that hey just extend this get the build function and then write your entire apps code over here now you might ask what is the purpose of these two separate classes the reason for that is here we create a state and what state does is very interesting the state will allow us to create our variables will allow us to create our functions and also everything inside of this class can be IM can be mutable so I can go ahead and type double result is equal to 0 and that doesn't give me a warning or an error it's all good inside of this but here if I try to go ahead and create double result is equal to zero we have an error this class is marked as immutable because stateful widget has a constant Constructor but state doesn't have that it's an abstract class that allows so we just need to extend State and that does our work now we have understood the structure of a stateless widget and I hope you are understanding what I'm doing again if you want a brief and you have some questions let's go along the code we have a class that extends a stateful widget then we have create State function that creates the state but then we cannot instantiate State class aware so what we need to do is create our own state that extends the state class and as a result we can put that over here inheritance concept then we need to override the build function and here it's the exact same thing as this thing you can create your own stuff the reason there are two different classes is because you cannot create mutable variables inside of this class so that you know we still have a Constructor that is constant but you can go ahead and create your own mutable variables here because this does not have a constant Constructor and this is a private thing because it should be accessible only for this class so that we could create a state it should not be accessible outside of this file leave outside of this file it should not be accessible outside of this class also but that's how private variables work in dot we've talked about this in the dot course so we'll have to live with this now let's resolve the warnings the first warning that we have is Constructors for public widgets should have a key parameter so just like this we have to create a constant Constructor so we have currency converter material page super dot key inside of a named argument save it then we have creates date and it saves the member create States override an inherited member but isn't annotated with override so basically since this is there because of stateful widget we have to put add the rate override just like we did with the build function right and there we go we have created it now there are still some things you can do if you want to improve for example State takes a generic type of ir T that extends stateful widget so you can have a generic type over here and it should be a stateful widget so you can go ahead and pass currency converter material page but then we get an error over here saying the currency converter material page can't be returned from the method create State because it has a return type of State currency converter material page but you'll say hey that's the same thing happening over here right not really because here extend State we also have to put the generic type again which is currency converter material page as soon as we do that we get the errors resolved basically since you have not typed anything over here in the T it wasn't able to identify that these two things are of the same class and their stateful widget is the same currency converter material page but it's still an improvement and if you don't put it it's fine and if you put it it's better awesome so now what I'm going to do is show you the difference between the stateless and the stateful widget in stateless widget we just add a Constructor and then we add the override here we have a Constructor we have create state that creates our class over here then we have our override build function and then a scaffold now the state just doesn't do this it gives us access to multiple more methods if you press command and go inside of it we get access to a getter called widget we also have access to build context so yeah you can use context over here it's accessible here the build context was accessible only inside the build function but their context is accessible even inside of this state then we have access to mounted which we look at in a while NH state this is one important method that we'll go into take a look at later on then we have data update widget another important thing reassemble then set State a very very important thing that we are going to take a look at in this app itself then we have deactivate and we have activate and then we have dispose another very important thing so it has access to methods like this which will give us more capabilities inside of our stateful widget with stateful widgets with State less widget sorry you don't have access to any of those things okay anyways now what I want to show you is what all things get called over here so I'm just going to remove this we have our currency converter material page only or actually press command Z let's copy the entire build function so that we don't have to rewrite all the design that we created let's put it over here let's get rid of the class now okay so build function has this thing we don't have to type it again now we have rebuilt over here okay inside of the build function I'm just going to call this build function then I'm going to call create state I'm going to convert this to a block this is not an arrow function anymore it's a block and we are going to return currency converter material page State from here but I'm also going to print create state then we are going to have our Constructor and I'm going to have print Constructor and then it says constant Constructors cannot have a body so let's remove constant for now only for now we'll put it back but I just want to show what all things get called okay now we'll press command J we'll restart our entire app then we have Constructor the first thing that gets called is this thing then create state which is this thing and then we have build function but what if you have certain tasks that need to be done before the build function but are accessible only inside of this class I mean let's say you've created a variable double result but you're not getting the value over here it's a late value maybe you call an asynchronous function and you're getting the value after let's say two seconds how do you make sure that you get it before the build function is called because you need to display it right you need to display it over here so for that reason we have a method given by our state class which is init state all right so as soon as we type in it it autocompletes it for us but if you want to know the syntax it's just at the rate override because it's coming from the state that we are extending then we avoid NH state a function then we can remove two to implement in a state then we call super.net state which calls the init state of the parent class and we've already seen this this thing is our state class all right let's go at the top to see this thing right here this is the state class so it calls the energy State of the State class and does whatever it needs to do for example the state life cycle created now what is the state life cycle what I'm showing you right now is widget State life cycle of a stateful widget that means what all stuff gets called what all stuff executes when so when does any state get executed we'll just put print rebuilt over here save it and come over here let's restart the app and we have Constructor create State rebuilt build function so Constructor is called create state but now instead of build function we have the rebuilt being called init state so NH state is what gets executed right before the build function so if you want to assign any values that are coming from let's say some futures or streams you can do it in NH state but for simple initializations like ours double result is equal to zero you can put it over here like this so let's get rid of them and let's convert everything back to normal so let's have something like this done we have an arrow function we have a Constructor and this is a constant even in the main function then or a main file we have to put const three so we have got double result over here let's remove that save it restart come over here and let's put text editing controller outside of this build function why because build function should always be as less expensive as it can be why should the build function be less expensive because build function can potentially be called in every frame because of a function that we call all right there's a function that will trigger the rebuild of this build function so this function can potentially be called in every frames so if you have a phone that has a refresh rate of 120 hertz your build function can be called 120 times in one second and if it is called that many times that means your build function needs to be less expensive it cannot have any asynchronous tasks first of all of that needs to be done in the currency converter material page state not in the build function because asynchronous task can take like one two seconds and in one second you have to call 120 times if it is done so if it is called 120 times per second you have like 8 milliseconds to run all of the build functions or or the stuff inside of this build function because one second is thousand millisecond and it can be called 120 times so 1000 divided by 120 which is 8 milliseconds so it's always good to keep this method as efficient as possible so you don't have to put any asynchronous tasks you don't have to do anything that will be expensive this thing over here is not expensive you're just assigning a variable which does hardly anything you can also push this right at the top but since it is UI related I like to keep it inside of the build function only and if you don't return a result in the given time frame it can result in frame drops so it can cause UI stuttering and will cause lags in your UI which is not a good thing for the user experience so always keep this build function as simple as possible and here it's quite simple anyways we have our result now and we have changed the value but still let's remove build context from here the thing is the same we have our variable created here then we have result is equal to double dot parse into 81 and we are not triggering the build function rebuild so what should we do then well we can go ahead and call the build function like we did and let's see what it does let's restart Also let's print rebuilt aware that looks kind of interesting come over here and we have 2.5 convert nothing happens because in the build function you don't have to call re uh build function again right this is not the good way of doing it what you can do instead is called a function that is provided by state and we've looked at it before in the state class is source code which was such State I told you that this is a very important function right so what you need to do is set date and it requires you to put in a function void function function so you have this Anonymous function here and then you can pass this thing right yeah now if you restart and I don't know why but I removed rebuilt print statement so let's put rebuild again press command J restart the app and now if I put 2.5 click on convert yes we see the output 202.5 and it was rebuilt why that's what set start does what set state does is set the state if you dive into the source code you won't be able to understand anything but here at the end there's one thing element dot marks need Mark needs build basically saying that it's telling the widget tree not widget tree something known as Elementary but we'll get to it after the second app but it's just telling that hey this widget needs a rebuild but that doesn't mean it will start rebuilding this entire class again no it will only build this build function only this function gets called again and necessary widgets are rebuilt now the set States function doesn't do anything okay if you want you can just put it here like this and it will work the same way all right so if you have 2.5 it will still work the same way this function is given to you so that it is a convenience for you to put everything that needs a rebuild inside of here however what set state does is just tell the widget tree or the elementary will get to it that this particular thing needs a rebuild so build the build function again and only build the necessary widgets you see it notifies the framework that the internal state of this object has changed the internal state of our object is the result variable that we created and whenever you change the internal state of a state object we did change the internal State of the State object via our state and this was our object we change the value so we call such state also this function that we have cannot return a future it cannot be asynchronous and then you can read all of this thing if you want to and gain extra knowledge but as of now what's important is that this calls build function only that's what it does triggers a rebuild using the belt function perfect so we've converted our currency from USD to INR now if I change it to 80 and restart my entire app let's say I put 2.5 this gives me 200 great if I put 2 click on convert 160 if I put 150 convert I get 12 000. and if you want to do something extra what you can do is put INR over here but we have to encapsulate everything in a string so we'll just have dollar result dot two string but I've already mentioned it to you if you have result.2 string inside of string interpolation we can skip result.to string and we can just have INR dollar result and now we have INR 12000 if you want to put a Rupee symbol or your currency that you've converted you can put that so that marks the end of our currency converter material app now let's take a look at what Cupertino app looks like I hope you are familiar with all the code that we have written till now we have gone through a lot we've gone through stateless widget stateful widget the state set state in its state we are going to dive into set in its state and all of that such state is almost required everywhere so we'll keep using that and we'll keep brushing our concept I hope you also understood the purpose of text editing controller text editing controller gives us access to text in the entire widget wherever we want and last thing that I'd like to mention is the on press function over here since this is a function that requires a type of void function like this you can go ahead and create a function over here so let's copy it and have void convert and paste this over here also remove the brackets this thing right here convert now you can go down and pass it to on pressed so you can either do it this way convert like this or you can just pass convert like this don't call it like this you have to call it like this why because convert has a function type of void function just like this requires so it's a tear off function since both of them match in what they require void function and this is also the same thing you can just pass it like this however when you call it this it means you're calling the function and you don't have to call the function in on press because when you call it you return a type of void and void cannot be assigned to on pressed so that's why you just have to put convert over here and that will work as well such state is accessible throughout our currency converter material page State and widgets are always immutable the state makes this class mutable so there is no performance impact on our widget this is still a constant but this isn't so we have mutable stuff over here and that is why we have two classes many people don't understand this but I hope you've understood this also let's remove color from here and we have our app ready so we have a currency converter material page ready there's still a lot of stuff you can do there is a lot of edge cases that you can handle for example a UI change just take a look at this you have a padding over here which has agencies.all 10 then you have a padding over here which has agencies.all 10 so what you can do instead is just wrap this entire column with the padding widget instead of wrapping all of the widgets separately in a padding widget so what you can do is select this copy press Ctrl shift r to open the refactoring option remove this Widget the same goes over here Ctrl shift R remove this widget then you can wrap the entire column by doing comma Ctrl shift R wrapping it with a padding widget and pasting our agencies.all 10 over here and once we do that we have spacing left from here but all the spacing beneath it is gone so we need to add that so do you mean I have to put text field again in a padding widget no then what is the sense of making padding widget over here no what you can do is use a container right by container you can mention a height let's say you want to leave a height of 10. then the same thing you can save it and you have your height left out but here's the problem this container doesn't have a constant Constructor and as a result when I have to rebuild this container will also get rebuilt unnecessarily that's what constant does whenever your function is going to get rebuilt your widgets will also get rebuilt what constant sees it is this doesn't need a rebuild because this is a constant if you have a constant it will not read need a rebuild but container doesn't have that and it will be unnecessarily rebuilt because we just have to leave a space we just need to leave a height why can't it be a constant then that's why we have access to constant sized box size box helps us leave a space you know container is a all-in-one widget it will help you to add height width padding margin color but what size work does is just help you leave width height and it has a constant Constructor so instead of using container everywhere you can use a size box it doesn't have any difference in the UI but it does have a difference in performance now it's a very very small impact but it still has an impact so let's try to make our apps as efficient as possible so with this we don't have to wrap any other widgets that we'll add inside of the widget tree with a padding widget all of them will have their automatic padding and now even text has a padding so if it exceeds this length it still has a padding so that's great and one last Edge case that I can see is if I put 2.52 click on convert I have this but if I put multiple digits we have our INR extending till Bello I don't want that maximum I want is let's say one or two digit I don't want it this precise so what I can do is wrap this and have dot to string and we have multiple methods for a two string two string as exponential two string as fixed and two string as precision I'll use two string as precision and pass 2 over here and when I do that I I get INR 2.0 e plus 2. now this is not in the format I want if you use calculator you know what this is talking about if you haven't don't care about it I don't want it like this what I want is to string as fixed Maybe then we can add 2 over here and we have I naught two zero one point seven seven so it only gives me a maximum of two digits and if you want you can give three widget and it will work fine then restart and you add INR 0.0.00 now if you want to avoid this whenever you have 0 you don't want it to extend till 3 does it after the decimal place what you can do is add a ternary operator over here inside of this string interpolation itself what you can do is if result is not equal to zero so if result is not equal to 0 then we want this thing right since our result was not 0 I wanted 204.480 but since my result is not 0 anymore I'll want result dot to string as exponential zero so I don't want there to be any exponents now if I restart I get e again but that's not I want sorry I want to string as fixed and then we can save it we come over here we get inr0 but if I put 2.566 like this I get three digits maximum so we have handled the H key so where you are using the ternary operator now you know how everything is coming back to its places we learned everything separately in the dot course and now everything is coming together you can't use an if condition over here because you know it doesn't make sense how can you use it inside of a string interpolation so you can go ahead and use ternary operator great so this is our app for the material page I'm going to get done with this now now what we are going to do is go ahead in the lip folder and create currency converter Cupertino page dot dot now we are going to have a Cupertino design so let's go ahead and design it so the first thing to do here is to import material.dot right not really because when we import material.dot we get all the widgets related to material design like this elevated button but we don't want that so I'm going to go ahead and import cupertino.dot which is similar to what we saw earlier all right now cupertino. will give us only the things that are following Cupertino design now we have to go ahead and create our state full widget now do I have to type the entire stateful widget here that can be cumbersome right just writing all of these classes I made you type earlier so that you understood what was happening here but now that we have understood it we can type your spfl and you see we have something known as a code snippet when we click on this we get all the boilerplate code required to create a stateful widget this is provided by the flutter and Dot vs code extension that we added so now we have access to the currency so now we have access to the state full widget snippet we also have access to stateless widget snippet I'll show you after we type the name of this class now I don't want my class name to be my widget right so it already highlights everything for me and all I have to do is type the name so we have currency I made a typo we can type currency converter Cupertino page all right and it changes it everywhere there is so wherever it's necessary it will change it now I can save it and there we go now it is returning a please holder for us we don't want that what we want is all the things that are returned over here and then we can go ahead and change whatever is not required so let's go ahead copy this return the build function because at the end of the day we need to have the same kind of layout but now we have many errors we'll solve them but before that let's go ahead and copy the logic as well all the text editing controller result and all of that now we can come over here save it and there we go the errors reduce but in no way are they lesser why because we have introduced cupertino.dot and outline input border scaffold ABBA all of them follow the material design you see stuff like Center padding column text are not affected by Cupertino or material design they are present in both of them Cupertino and material because the typography is not decided by the text itself it is decided by what we are returning away a material app or Cupertino app and then we have column which is a layout thing padding which is basically just leaving space so it doesn't have to follow material or Cupertino design guidelines and Center is again a design guideline and Center is again a layout widget so now we have to go ahead and change everything first of all I'm going to go to the main.dot file I'm going to create a stateless widget here so to create a stateless widget you can type St L and then you have a snippet for stateless widget as well you click on this and then it creates all the boilerplate code for a stateless widget now you can just type my Cupertino app okay then you're going to return this exact thing but instead of material app we are going to have Cupertino app and this also accepts a home argument though these two things are different Cupertino app doesn't have the same theme that it requires it requires Cupertino theme data and this requires just a theme data okay so there are differences but anyways now let's take this put it over here we all have my Cupertino App instead of my app so it will run this class not this class so this class is basically never executed now we can save this also we can have currency converter Cupertino page instead of currency converter material page otherwise it might give you some weird output now let's come back over here now we are returning a scaffold scaffold is apparently a part of material or not so what we need to do here is return Cupertino scaffold we see we have Cupertino Taps scaffold and Cupertino page scaffold which one should I choose Cupertino tabs scaffold is related to creating a tab at the bottom and Cupertino page scaffold allows you to create a an app bar at the top so we definitely want Cupertino page scaffold then it has multiple things it doesn't have the Abba property or the body property let's see what it requires it wants a child property so our child is going to be this thing which is nice and then we have navigation bar so we can return a navigation barrier and in navigation bar it requires obstructing preferred size widget it doesn't require preferred size widget anymore which is what app bar is and also app bar is from material.dot so maybe we can go ahead and type Cupertino Abba and maybe we get something but no but if we type Cupertino navigation bar we get that and Cupertino navigation bar is exactly what we can pass away now Cupertino navigation bar is the same thing as app bar at the top so we don't need to worry about it then it has a bunch of properties what we require is a title and if we come away a we see a widget which is middle and as you already know in iOS Style the title is always always Center if it is already centered it makes more sense to name it middle so what do you want in the middle so we can have middle over here sweet and if you see there's no thing as elevation over here because Cupertino widgets don't really have any elevations or depth to them so we can remove this now to resolve the colors error if we press command full stop to get a list of fixes we can apply to a project we see import Library package flutter material.dot because material.dot also includes the colors your app is going to have so we cannot use the colors class but we can go ahead and use Cupertino colors and it gives me a bunch of colors now I'm going to go ahead and have Cupertino colors Dot blue then we have two type of colors system blue or Active blue I don't want any of those maybe Gray let's go ahead with system gate grade 3 then we can save this much then we can again copy this and the exact same thing let's hope we like the version that it spits out Also let's put a const over here because Cupertino colors are constant all right why because if we come over here it is abstract final class right so let's exit this now let's scroll down we have text field so instead of text failure what we require is Cupertino text field there we go as easy as it gets whatever is there in material or dot just put Cupertino before it and it will become a Cupertino widget it has the same property of controller but color again we'll have to put Cupertino colors dot black so that's fine I'll copy this line again and paste it over here but here the decoration requires box decoration and box decoration is not related to input degradation so we have to get rid of input decoration and just pass in box decoration over here now let's design everything that we have the first thing we need to mention is the border so let's go ahead and pass in a border now the Border it requires is box border so maybe we can type in box border but that isn't allowed however if we just type border dot all it allows us to pass it in so we can just have border.all then we need to mention the color of our border and the color of our border is the default one so we are just going to leave it at that then we also have to mention the Border radius the Border radius is five so let's go ahead with that let's take the default one then we have bought a radius and the Border radius is going to be border radius dot circular five that's good now we can try to mention the color as well so the color of the text field we want is colors.white so we can go ahead and pass Cupertino colors dot y I guess that will work right and that's all that we require so maybe we can just get rid of all of this we still need to mention hint text so let's copy it and then get rid of this and see the decoration doesn't give us properties to change the hint text however Cupertino text field does give those properties and there we have it placeholder we also have the prefix widget and it doesn't have all of those prefix stuff like prefix icon prefix prefix style it just has prefix which requires a widget that is cool so if we go ahead and type hint over here there's no hint related stuff but if we type placeholder and then type please enter the amount in USD that should work and then finally we need a prefix widget which is icon icons dot monit not icon we cannot use icon why because I can is also coming from material.dot we cannot use that so we can go ahead and type something like Cupertino icons and there we have it so we can pass in Cupertino icons Dot money and it does have money dollar sign exactly what I need and put a const over here perfect so this looks good now the final thing that I need to work on is button elevated button is also coming from Material design now you might have noticed that everything that was UI related changed from material to Cupertino dot dot and all the layout widgets like column padding Center and text because that depends on cupertino.settings or Cupertino app settings that's fine so let's go ahead and instead of elevated button we are going to use Cupertino button as simple as it gets then Cupertino button requires a child which we have already passed then it requires a color so what is the color you want so the color I want is black so we are going to have cupertinocolors dot black then I want something sizing related so we have minimum size maybe we can look into that so we have minimum size and that is a double the default is K minimum interaction Dimension Cupertino let's go over that whenever you have something like K it is meant to be a constant that's flutter's way of saying that hey this is a constant now we can dive into this and we have 44 showing here and then it has design guidelines about it so I'm not going to meddle with it I'm just going to keep it as it is and see what the output is if I want to change it I can go ahead and change it right and then maybe I can remove all of this the only thing that's left is to make sure the color is white and the shape is rounded rectangle border with a border radius of 5. so let's get rid of it and almost all our errors are done let's also remove this because border is not being used in text field anymore so let's get rid of this save it restart our entire app Ctrl J no problem become aware and our entire apps design is now changed this is how it looks in Cupertino design and I'm quite satisfied with how the button is looking over here so I'm not going to meddle with the size however you can go ahead and change it also if I pass 200 click on convert it's still working if I press 12 it's still working great so this is how the app looks in Cupertino design this is how the app is going to look like in material design you can design for yourself which one you want I like this one better because it gave me more customizability and I just like the design and feel of it I don't like how the text Fields look in Cupertino design the main difference is that material design follows a more Dynamic and Visually Rich approach it uses Shadows depth effects bold colors and it often incorporates elements that mimic Real World objects and materials that's why material design now Cupertino design has a more minimalistic and flat aesthetic and focuses on Simplicity subtle gradients and although I do like minimalistic design Cupertino design is just not my taste so from now on I'm going to go ahead and design only material designed applications if you want you got a taste of how Cupertino Works basically any widget you have just put a Cupertino before it and you'll get a widget similar to that and if you don't you always have Google where you can ask your question about the equivalent of let's say a particular widget in material design in Cupertino design okay so we are done there's one last thing that I want to mention and that this goes for both of these classes currency converter material page and currency converter Cupertino page and that's the use of text editing controller whenever you any form of controllers later on we'll see that there are a bunch of controllers like there's animation controller or page controller draw controller scroll controller stream controller which we've already seen all of those need to be canceled or disposed of so that they don't have any data leaks or memory leaks in your application so for that reason the state also gives us a nice property or a nice function which is the dispose function in dispose function it is usually recommended to put super dot dispose at the last and in its state you might remember that super.net state should be the first thing and after that you will have rest of the other things because then you want to call the parent class and initialize everything but in this pose you're just removing certain objects from your widget tree and this dispose is called whenever your widget is no longer existing maybe you move from one page to another by replacing the current page this is when the dispose function will get called so in that case you don't want to instantly delete or dispose of whatever is present in the state class first you want to dispose of your own classes your own controllers and streams or Futures whatever you want to dispose and then you'll call super.dispose to dispose of everything that's present in the State class all right so here what I'm going to do is pass in my text editing controller and call dispose method on it so this will dispose of the text editing controller it will basically discard the entire text editing controller and say that hey this object is basically not existing anymore and that avoids memory leaks all right so you can consider dispose to be kind of like the exact opposite of NH state in its state gets called before the build function before anything builds and this pose gets called right after the entire widget is going to get discarded cool so let's get rid of this and now we are done with our entire currency converter app congratulations on building your first ever flutter app which is working quite well to understand about widget life cycle we must first know what widgets are and what a life cycle is everything in flutter is a widget so before knowing about life cycle we must first know what the widgets are and if you are seeing this video there's a great possibility that you have already created widgets in your app to Define it in the least words possible widget can be considered as every class you make and can call in the build function without any errors and if you don't know what build function is it is a function that is used to render something on the screen every flutter app is a combination of two type of widgets stateless widgets and stateful widgets stateless widgets are those type of widgets where the state once created cannot be changed that is it can run only once which is when the app is loaded this also means that this type of widget cannot be redone after any user interactions this is an example of stateless widget a stateful widgets on the other hand are widgets where the state can be changed and we can make this build function over here run multiple times with different widgets to render or different string in a text any value can be changed now let's understand the life cycle of these widgets so we are back to our stateless widget and as you can see that the my stateless widget which is a class name of a stateless widget has overridden the build function here which can written return only one widget at the end which here we are returning a scaffold so whenever my stateless widget is instantiated it will call the build function and draw that one widget on the screen so if we have to understand it in a chart flowchart format first we call the Constructor and then after which the build function will get executed pretty simple right now what about State full widgets we have a Constructor here after which the build function will be called right no you see in this code demo my stateful widget is a stateful widget and we have a build function here but before that you can see create State over here as the name suggests this creates the state of our app it also returns an instance of the associated state now that we have access to the state in our app flutter provides us with some methods to use as and when we want first is in its state and this is how you can create in its state function what is in its state right and its state is the method which runs once after the Constructor of our app and created state is called since it basically runs in the very beginning of the app we can initialize data and properties with some value we can also subscribe to streams and make connections with sockets let me show you a demo suppose I have a variable of data type end and I'll call it ABC and I have to instantiate it with the value I can just do it like this or I can just mark this as late go over your and put ABC equal to 10. now I'll go in the text and over here I'm going to return abc.2 string since text accepts a string format and I'm not going to return it as a constant because the value can change now if I go over here and let me return my state full widget over here you can see that we are getting 10 as our outputted value and that is exactly what we wanted now I'll also take a moment to explain the General Internal working of NH state if we scroll up and we see that our class inherits from state which is an abstract class as you can see over here we also have override over here which means we are telling flutter that we are putting in its state over here and it isn't a mistake we are deliberately trying to add our own energy State function and not use the image State function present in the state abstract class super over here creates a reference to the parent object in state class and then calls the NH State function there as well now where should I place the code I want to execute in the initi state function right over here on the top or over or below it well flutter documentation says that the code should be placed after calling super initi state exactly like I've done for the variable ABC but after further inspection in the state class I'll go to the NF State function in the state class over here I found out that the init State function basically does nothing that affects our app so I don't think it matters wherever we place the code this same internal working is followed in every function that we're going to have a look at uh in the following tutorial the second function that we have over here is did change dependencies this method is called immediately after energy State method moreover this widget will be called again after the piece of the data the widget depends on is updated this function is used very rarely as the build method is called after this next we have a function called did update widget this function runs whenever the widget attached to the state is replaced by another's widget here you can see that we are also getting our old widget which is replaced and if you want to get the data of the new widget you can just do print and use the widget that we always have this function is used rarely as well last method we have to discuss is dispose this function is used to remove all the connections our app has this is a very important function most of the people forget to use and I admit even I have forgotten many a times dispose is a place where we can subscribe from all the connections or listeners thus it helps us in removing some things from the app's memory and prevents our app from memory leaks let me prove what I'm saying with the help of the code now I'll write print everywhere in our app and all the functions that we have I'll write here from init state I'm just going to copy this print command and paste it in all our functions from disperse from did update sorry from dead update widget from did change dependencies and even over here in the create state I'm just going to replace this Arrow function I'm just going to copy this I'm going to return this we have the my stateful widget state and over here I'm going to print from create state over here as well I'm going to replace I'm going to print and we are going to type from Constructor right now we can just ignore the warnings the warnings that we have I'll refresh our app and let me just remove the int ABC part from here as well and I'm going to introduce a part of the code uh where we can see something interesting happening not just a piece of text that's showing up I'm going to replace this with this cool now let me run my app and now you can see that if we click over here we get a model bottom sheet which which three uh with three options and if we go over here in our debug console let me just take this up you can see that we first go to the vprint from Constructor which is from your which proves that uh the Constructor is uh run first after that create state is run as I said before then the image State function is run and then did change dependencies as a run did update widget and dispose do not run because we have not uh you know updated any widget we have not replaced our current widget with any other widget also uh dispose is run after we need to clear off something suppose I have my socket over here and I have initialized it I haven't uh downloaded any sockets package yet but I'm just showing it for the sake uh for showing it that we can use dispose on sockets and if we call dispose over here it will not give us any error at all and it will uh be a good thing for our apps memory and we should always unsubscribe from all the listeners that we have so that it doesn't keep on going and cause harm in our applications right now if you prefer seeing this a stateful widget in a flowchart format like we did for stateless widget here you have it so our state is first created then the initi state function is run then our build function is executed then uh it checks if did update config or set state in our app is called yeah you might be familiar with State Street that's why I have not included this in my tutorial right now so basically if you don't know what such state is set State uh will help you to rerun your build function again so you can rerun this whole entire uh function after calling such state so if you want to update any value and show it uh to the user on the screen you can just use such State then uh if any of these is called then it will again go back and call our build function as we can see in the flowchart over here then we have our dispose function over here and after that our app is cleared off now the second app that we are going to build is a weather app where things are going to get a little bit more complicated but not very complicated so let's dive into it and first of all let's just see a demo of what we are going to build so this is the weather app we want to build at first we have the app bar or the header kind of thing then we have the temperature showing up in Mumbai you can insert any place you want in degree Fahrenheit it also tells you what type of weather it is like if it's raining sunny and it shows the appropriate symbol for it then we get the weather forecast since the time right now is 8 40 AM it shows me the weather forecast from 9 am to 9 PM with 3r interval then we have additional information about humidity wind speed and pressure the good thing about all of this is this is not hard-coded like we did in the currency converter app it is taking actual data from the web and displaying it over here so the actual weather in Mumbai right now is 300.67 degree Fahrenheit also I have the refresh button here in case I want to rerun everything and you see as soon as I press refresh I get a loading indicator and it pulls the actual data from the web so for this purpose we are using an API here and we learn how to do this in flutter so let's go ahead and create a weather app so the first step is going to be to create a flutter project for it so go ahead create your own flutter project I'll CD to desktop which means change the directory to desktop and after that I'll run the flutter create command for weather app all right after that I can change the directory to the weather app and as soon as I type weather and press tab it will auto complete it for me and will type weather app for me after this I want to open it in vs code I can either go ahead and open Visual Studio code like this and you know close the current folder I'm in and just drag this app right over here or what you can do is type in code which will open up vs code for you now if it doesn't open up what you need to do is press command shift p and vs code then pass code like this and you'll see this command shell command install code command and path once you click over here you'll be able to use code like this and open Visual Studio code from the terminal itself Code full stop basically means that open vs code for the current folder if we were back in the desktop we would have to do code dot slash weather app all right and it would open up my weather app in vs code gray now let's open it up back let's start running our app to see if everything is all right here and then we'll also migrate to the lib folder in main.dot because I want to make sure you understand the default code for the counter app that's written now that you know the very basics of flutter so at the top we have the run app and we have my app it also extends a stateless widget where we have material app title this title basically tells you the thing that shows up here in Android devices for iOS it just takes the thing that is mentioned in info.p list now what is info.plist well if you press command p and type info dot P list you'll see iOS slash Runner all right this is present in the iOS folder where they've defined the name for our app which is the weather app so it takes the name from here if you want to change the name of the iOS you know this name here you'll have to change it in iOS slash Runner slash info dot P list and for Android you can change it from here awesome so our app is also running now we have our theme here and it takes a theme data then passes in a color screen and passes in a seed color based on which we have our entire design ready then it also has used material 3 set to true now there's material 2 and material 3 which are basically versions of material design material 3 came out recently and flutter has the option to use material 3 design so this is how the app looks in material 3 design and if I just remove it save it this is how it looks in material 2. so that is the difference between material 3 and material 2. definitely I like material 3 better but you can look for yourself and this is what team does when you define a theme over here it sets up the overall coloring scheme and let's say typography all of that stuff for the entire app if you want to go ahead and change a one particular screen you can do that but what theme does is set set up for the entire app because that's what my DL app is right then we have home where we pass in my home page and in my home page we extend a stateful widget we have a title which we are taking from The Constructor which is flutter demo home page and it's showing up in Abba so if we scroll down we have Abba where we have title text widget.title but an interesting thing over here is background color what it does is theme dot off context to go to the theme then use the color scheme dot inverse primary so it's basically going to this theme widget right over here then it's saying give me color schemes inverse primary property which is defined in the color scheme if you scroll down you'll see inverse primary now if you set inverse primary color over here let's go ahead and try it inverse primary colors dot blue save it come over here you see the I bar is now blue in color because we are accessing color scheme dot inverse primary when we don't specify anything and just specify the seed color it takes a light purple kind of shade but when we specify the inverse primary color it takes a different color and this is what theme is all about you set it somewhere like let's say you set the theme over here and then The Descendant widgets can use it or the child widgets can use it then we have Body Center column and Main access alignment Dot Center because of which these two things are showing up in the center you can see a constant text and a counter text and that is why we have a stateful widget here also we have something known as a floating action button which shows the button over here now if you wanted a normal button over here you could use elevated or flat button or text button but since you want to use a button over here it's better to use Floating Action button which is provided as a property on scaffold and then you can Define The Floating Action button widget and then obviously just go ahead and look out for yourself like whatever named properties are there everything is written pure English for you to understand we also have the tooltip property which is basically like if you long press you'll see this thing right here increment text that is wall two tool tip is then you have the icon as the child because of which we have this plus button and then we have on pressed increment count and increment counter we are just doing such state and in there we are changing the value of underscore counter so that's our counter app now we're just going to go ahead and remove everything because we want to build our own weather app and now let's start from scratch I hope you understood everything in the counter app because you've learned so much about stateless stateful set State everything now let's go ahead and create a class I'm not deleting the main function we'll have a class called my app or you can call it weather app whatever you want to call it this this today should extend stateless widget and instead of doing all of this we can just do stateless widget like this and call Maya cool now you're having a placeholder here because of which we have this lines over here placeholder is basically telling that hey you want something to be put up over here so I'll just put it up for you like this so it indicates that you want to put some kind of widget here and this should take this much space this much height you see we have fallback width and fallback height stroke width and all of that stuff but instead of returning a placeholder we want to return a material app and in material app we first want to set the home which is let's say constant where the screen and that's something I want to create so let's minimize the iOS folder go to the left folder create one more file and let's call this weather underscore screen dot Rod remember the name in convention here then we are going to import material dot so let's go ahead and import material dot dot then we'll go into create a state less widget let's say because I don't know if I need to put a state or not so for now let's put a stateless widget here then we'll save it I'll take this weather screen put it here then press command full stop so that I get a list of quick fixes where I can import my weather screen package all right then another thing that I want to do is after I save it you see this debug Banner is showing this tells that our app is in debug board but for now I just want to remove it completely so what I can do is debug show check mode manner set it to false with this property set to false the debug Banner over here is removed and the last thing that I want to set over here is the theme so right now my theme is going to be light mode so if I just return let's say a scaffold here you'll understand what I'm talking about it's light mode right I want to change it to dark mode so I can just do it in theme otherwise I'll have to do it in the background color yeah so we have colors.black but what if my weather screen or my weather app has more than just one page do I have to go about and change the background color everywhere remember our diagram the theme over here is going to set it for the entire app it's going to be the global thing but for weather screen in the scaffold it's just going to be there for one particular page and now you might be able to see the results but it doesn't set it for the entire app it's just for one screen so what I want to do is go to the main dot dot set the theming up so I'm going to have theme data and then you can pass in theme data but what I want to do is use the preset themes given which is theme data dot doc or light mode you can use either of them or you can just Define your custom theme data all of these work all right with custom theme data you can go ahead set your background color you can set much more stuff but that's not what I'm going to do I'm not going to start writing from scratch I'm just going to use theme data dot dot with Doc I have access to the dark background you see but still this is team data.doc and this is fine but I want to use material 3 because I like that very much so you see it has a named property of use material 3. I can pass and use material 3 and it requires a Boolean value so I can set it to true and it will start using material 3 and you see the background color over here changes now at if at all you want to change the background color what you can do is dot copy with and set your own custom stuff over here so it will have the dark color properties and if you want to change anything at all you can change it with copy width so let's say the Abba color over here is blue it's not actually blue but let's say in theme data.doc the app bar color is blue you want it to set it to White you can just go ahead and set the Abba theme over here so what it will do is copy everything from theme data.doc including app bar then it will see this copy with function and it will override the existing app bar theme with the app bar theme I provide over here all right so it just takes this and copies whatever is present inside of it with the existing theme data so I hope that makes sense it's quite intuitive but I don't want anything like that I just want this simple line to be present all right now let's go to the weather screen and designer app now what do I want the first thing that I require is an app bar so with me I have the iOS screenshot here now what I'm going to do is go over it step by step and we'll see how to make this kind of UI if you want to try it on your own go ahead try it it will be a good learning but if you can't let's design it on our own we'll get some practice and maybe after that you can start designing your own stuff because this is going to have many important widgets discovered so the first thing that I require is an app bar with a title weather app so we are going to go ahead and have an app bar s in Abba maybe already seen and you see as soon as I call Abba I have to remove constant from here because Abba isn't a constant you can see it inside of here in the Constructor no const now we want the title which will be a constant text and we're going to call this let's say weather app let's go ahead and type it save it and we see whether operating over here perfect now still the textile doesn't look very good because this is bolded so let's go ahead and set the textile Vilas Style textile font weight to be font weight dot bold we've seen exactly this and this is nice the next thing I want is a refresh button over here also I want to make sure that my title is always centered irrespective of whether it is on Android or iOS so I'm going to set Center title to 2. great no visible changes but on Android you'll see the change now the next thing I want is a refresh icon over here how do I add that now I told you in the first app that whenever you want to add any icons over here or any sort of widget we have to use the actions property present inside of the app bar so we are going to use exactly that we are going to have actions and here we are going to mention our icon which is going to be icons dot refresh Also let's put a constable here save it and we have our icon showing up but the problem with it is this icon is not clickable you know if I click on it it does absolutely nothing I want to make sure that it still does something whenever I click on it so for that we'll need an on tap property and like some sort of detector that hey this has been clicked so for this we need to use a button right not always you can use a button over here but sometimes you just don't want to use a button what you want to use instead is an icon wrapped with a widget known as gesture detector so you can press Ctrl shift r on Mac and then you'll get these refactoring options and you can wrap with something known as a gesture detector and gesture detector isn't a constant so let's remove it let's put const for our icon now we'll put a comma so that the formatting takes place and we get in a format like this now what I want to do is use some of the property given by gesture detector which is on tap with ontap we have access to the click property so whenever we click on this we can run a particular function just like we do in a button so we can have the ontap property defined here and let's say print refresh let's save it press Ctrl command J restart an entire app let's click over here and it says refresh again if we click it says refresh so this is being clicked on but one problem I have is there is no splash effect like when I click on it there should be some kind of radial Splash shown so for that kind of detection what I want to do is wrap it with inquel Widget Inkwell also has similar set of properties it doesn't have as advanced properties as a gesture detector it has lesser properties than gesture detector but what Inkwell does is give you a splash effect so when you click on this you get this nice flash effect so you can use either of them in this scenario and it will work fine I'm going to go ahead with gesture detector and be done but there's another thing you can do instead of using gesture detector and icon we have something known as an icon button so it is an icon and a button so it allows you to pass the on press property and an icon so now I can we are going to have icon icons dot refresh and then you have the on press property so you can do the same task in multiple ways and you can have the same UI it depends on you what you want to do but with icon button basically you have the nice cool Splash effect which is not a not a square it is a circle plus you get the nice padding overall ingest a detector and I can you would have to set your own padding property so that it didn't get stuck in the right hand corner with icon button it provides you with the padding by itself cool now we are done with the app bar now let's get to the body and make some stuff so the first thing I want to make is this big bulk right here we're not going to actually get some data as of right now we're going to put in some false data here and when we connect to an API which is after creating our UI we'll replace all the values but as of right now we are going to put in random values so let's go ahead in our scaffold we are in a scaffold let's make sure and then here we are going to pass a body property and in a body what do we require well first thing to analyze is the proper layout what is the layout of this app well everything is below one another in a vertical manner so obviously we need to use columns so that we have access to children and because of that we can put everything inside of one particular widget and it should be vertically below each other so let's go ahead and pass a column over here column will have children and the first child is going to be this main card so let's put a comment here saying main card so that we know what we need to work on then if you want you can put in a placeholder here saying that hey this much space is going to be given to our main card now to change the height you know it's taking a lot of height maybe you can go ahead and change the properties here and the property I want to change is fallback height so let's change it to let's say 250 and maybe it takes this much space which is fine and in the child we are going to pass in a constant text saying main card save it come over here you see main card but now the fallback height and fallback width will disappear why because you've said the child as a text now this parent will take only as much height and width as this text requires as much as a child requires this is not height but fallback height fallback height is basically like hey you haven't mentioned any child if you haven't mentioned any child this is the height we are going to go to but if you have mentioned a child we are going to take as much speed as the child requires so if we remove the child and come over here this looks great all right now after that the second thing we require is where the forecast cards we need these cards over here right so where the forecast cards again you can place a placeholder here and let's say the fallback height is 150 looks good enough maybe we need a sizing wire so we'll have constant size box height 10 which will help us to leave spacing we've already seen this before but this is two lesser space so let's go ahead and add 20 let's say this looks good and after that we'll have additional information so again we'll leave some height and then we'll have a placeholder again let's say 150 again so this is the overall layout of our app very simply laid out first we are going to have our main card then we are going to have a weather forecast cards and after that we are going to have our additional information so let's get started by designing everything the first thing we need to design is the main card so how is our main card going to look like well let's analyze it it does have a color of its own it does have a 3d effect it has its nice own curves because if we just use a container which would be the first thing that goes in our mind that hey this is a very big thing and it has these curves it has a color it requires a children over here like we want to display a text we want to display an icon we want to display again a text so the first thing that might come in our mind is a container but it has an elevation and container doesn't have an elevation property so definitely we cannot use a container however what we can use is something known as a card widget so if we just use a card widget we'll be able to use it now as soon as you have a card you know one placeholder goes away but now let's start designing a car in a card we require these three children so we need degree Fahrenheit text we need this thing right here and we need drain so in a card we are going to have a child property we are going to we are going to have a column and here we are going to mention children obviously because everything in is in a vertical format so you want a column over here without column you won't get access to Children you can use row which will also give you access to children but it will be in a horizontal manner we don't want that so we'll use column over here now we need text so we are going to pass in a text and the text is going to be let's say 300 Fahrenheit now I also want access to degree but there's no degree sign on my keyboard at least what I can see so what I'm going to do is go to Google search for degree symbol and just copy the degree from here close my Safari tab have 300 degree Fahrenheit like this and we see 300 degree Fahrenheit cool let's put a comma so that we have a formatting in place perfect now I want to design this further now first of all let's go ahead and increase the font size and the font weight of our temperature so we're going to have style textile and the textile is going to be font size 32 font weight font weight dot bull I want it bolded and this font size is a tried and tested value I've built this app before so I know I want the font size of 32 but when I was building this app I constantly tried and see you saw what font size I preferred and this is the font size I prefer now if you look closely at it you'll see there's some sort of background on it that is quite evident and that is our card widget card gives us access to an elevation stuff which you can see over here and you can toggle it on or off like if you want elevation to be zero it will be completely gone but if you remove this it has some sort of elevation of its own now we have a card but the problem right now is the card is not taking the maximum width it is only taking as much of it as this text requires so what I can do is wrap my card with a container which will tell it to take the maximum width so for this I'll press Ctrl shift R get the refactoring options and wrap it with container and here I'm going to mention the width which is going to be double dot Infinity saying that hey take maximum amount of width and you see it takes the maximum amount of width however we have a warning here I mean the entire app is in warning but even here we have a warning saying use a size box to add white space to a layout so whenever you want to set up width as I've already told you before you always need to use size box when you have to use something more than just a width or a height let's say color border radius all of those stuff you have to use container then but then but if it's only with then go ahead with size box and we see the same thing now the width is stretched it takes the maximum amount of width possible so I hope you are understanding how flutter layouts work earlier we had not set any width constraints on this card it was free to use whatever space it required and therefore it depended on its child and its child was column columns width depends on its children and its child required only this much space but then we added a constraint on our card saying that hey take the maximum amount of width possible so it went ahead and took double dot Infinity which has the maximum amount of space it can take right so keep this layout thing in mind because it's the most important aspect of flutter you need to understand how layout and UI work now the problem is it's taking the maximum amount of space I do want it to leave spacing from here and if you see in a layout everything in our column takes this amount of space so I think on the column property they have set the padding property padding is not specific to One widget that hey only this much only this widget requires spacing from here not these widgets well all of the widgets required the spacing from here so we can safely assume that we can set the padding property on this column not on One widget of course you can go ahead and set padding property on every widget in our chat in our column but it would make much more sense to do it for the entire column so we can have Ctrl shift R then we are going to wrap it with padding and we are going to set it to let's say 16. because it's much more than just eight it would be somewhere over here and 16 as over here which looks good great now you see there is spacing over here here everywhere that's good now let's put more children to our column we are going to have our icon now so we are going to have I can ikins Dot Cloud as of now it's going to be a static value so let's put a cloud and the size is quite small so let's increase its size so we're going to have a size of 32 it's still small nothing big so let's go ahead with 48 still quite small and let's go ahead with 64. now it looks big enough so we can go ahead with this also if you want to increase the height of your emulator you can do it by stretching it then after this icon what we require is this subtext so let's put that you're going to have text drain style is going to be let's say textile font size 16 let's go ahead with that it's quite small what my thought process is is like hey this is almost 32 then this is 64 and this is very small compared to both of these things so we can go ahead and let's say set the font size to 20 so it will look decent enough in front of them and I think that looks good so we have the content inside of the card setup but if you see there's much more spacing over here between these things so we can set that up as well we are going to have a constant sized box of height 16 and don't worry about the errors if you are concerned about them because these errors will go away as soon as you put a const for example if I just put a constable here most of the errors just go away right I am not putting them because I know that later on I want to set a border radius property and Border radius as you know border radius dot circular is not a constant if it's not a constant I cannot set it to a constant right so instead of doing and wasting time setting up cons what I'm going to do is let the warnings be there and wait for the Border radius property to be set up so that we can put a nice curve over here so we've put a size box over here this leaves a good spacing we're going to do that again after the cloud icon that's nice now if you compare it to this in layout terms it looks quite similar except if you see over here there's pacing if you see over here there's spacing but here there is no spacing added over here so there are two options we can take in the column we can set the size box over here as the first child in a column and at the end again or you can just wrap this column property with padding again and this padding is limited only to our column so I'm going to go ahead with the column property because I don't like putting size boxes where it's not actually necessary so I'm going to go ahead and press Ctrl shift r ape it with padding and it's going to be Edge and such dot all 16 save it come over here and this looks better definitely the next thing I require is the elevation to be bigger as you can see the Shadows are bigger so let's go ahead and set our custom elevation property for our card which is going to be elevation let's say 10. when we do that this is much stronger and appears more 3D it gives a better visual effect the next thing we want to do is set a nice border radius it should be more curved than what we have right now so in our card we can go ahead and set the shape property where it requires a border and here we can pass in a rounded rectangular border what we've already seen before right most of the widgets are repeating we did learn a new thing about a card but rest of the things are quite similar you just need to understand what you need to do and start doing it for yourself and you see as soon as I put track rounded rectangular border and save it I get a pointy border because I need to custom set my border radius over here so I'll go ahead and set my border radius to border radius dot circular and as soon as I do border radius dot circular the warnings should go away and here my border radius is going to be 16 and as soon as I do that look there's more curve attached over here that looks perfect the warnings go away from here however there are warnings over here so let's go ahead and put Constable here let's put a move unnecessary cons because their parent is a constant cool so we have this thing over here it doesn't look very same to this but it does have the proper layout the thing that we are missing is the nice merging filter between them right now it's clearly visible that hey there's an elevation property and doesn't merge with the background to make it merge with the background like this we need to have access to One widget which is a backdrop filter what backdrop filter will do is basically blur the background in the X and Y directions so X will be the horizontal Direction y will be the vertical Direction think of it in graph and blur the background and once it blurs the background you'll have a nice effect let's see what I'm talking about if I just wrap my padding Widget the column is wrapped by padding and if we wrap the padding widget with backdrop filter we get access to the named parameter of filter and here we need to pass an image filter so we need to pass an image filter and if we do this much it's not allowed because image filter is not an abstract class but it doesn't have a Constructor of its own or actually it is an abstract class and it doesn't have a Constructor of its own meaning this abstract class cannot be extended you see so having something like this image filter dot underscore and then parenthesis basically means that this Con the Constructor of this abstract class cannot be called any time that's why I said this is not an abstract class it's it just has its Constructor privatized but in reality this is an abstract class whose Constructor is also privatized you know privatized as always by underscore so they've put an underscore over there okay so let's come back over here and use image filter dot because we know image filter is not extended if it's not extended there can be no class we can put here except image filter itself that's why I call Image filter Dot now if you didn't understand what I was talking about what I was saying is image filter is basically a privatized Constructor so that means image filter cannot be a parent class of any other class because extended is not allowed so definitely I cannot put anything else over here I need to put image filter only so I called image filter Dot and that gives us access to multiple methods we can use you can use blur compose dilate erode I'm going to go ahead with blur that will blur my background and here I can pass in Sigma X which will be let's say 10 and if you hover over this you see creates an image filter that applies a gaussian blur and then we have Sigma Y which is again going to be 10. so from the X and Y direction we want 10 and you see it basically merges with the background but then its elevation kind of goes away to prevent that we can add a border radius property to this backdrop filter itself so you can press Ctrl shift R then wrap it with a clip or rect widget which allows you to put a border radius property if you wrap it again with a card so that you can set up order radius property it wouldn't make sense what you need to do is put clip rack what clip rack will do is clip it clip it according to the properties you mentioned and it allows you to put border radius and it also has a custom Clipper you can pass in but right now we just want to put a border radius for that clip our wrecked is enough so you can put border radius and Border radius is going to be the same thing as this one if it is different values it will look a bit weird and you see as soon as we add border radius the elevation properties there and we get a nice cool effect looking like this card so I hope you understand what I did over here I applied a backdrop filter because of which everything was leveled into one place and there was blur over here then I wrapped it with a clip rack widget because of which it applied its own border radius it separated the blur from the background and gave it a nice look so we have a nice little backdrop filter as well as the Border radius which looks exactly like this widget now I know this is an important or a difficult concept to grasp but you can play around with yourself you know you can just remove this widget again and see how it looks after adding clip RX widget you'll again see how it looks great so we have our main card design angle and in my opinion it looks just perfect now let's go ahead and design the weather forecast and additional information tabs so for weather forecast we have to leave some spacing which we've already done I assume here we have it size box height 20 after that I need a text saying weather forecast so I'm going to have a constant text saying whether for cast save it and when you have an error and you save it it doesn't hot reload but when you save it after no errors you see where the forecast over here now let's put style over here we are going to have style as textile then we are going to have font size as 24 which is a big value then font weight which is going to be font weight dot pull and we have our weather forecast showing up over here which looks good now what I want to do is it is mentioned in the center I want to take it to the left hand side so for that I can wrap my text widget in a widget known as align what align does is basically certain alignment of where you want it to be in the column do you want it in the left view do you want it in the center you want it in the right top right whatever and align has alignment property now instead of using a line you can go ahead and use container which also has an alignment property but at the end of the day container inside uses alignment or align widget which is the same thing so let's go ahead and pass alignment now alignment requires alignment geometry but its default value is alignment Dot Center we can set it to a different value by using alignment Dot and you see we have a bunch of options bottom center bottom left bottom right center Center left center right top Center top left top right what I want to do is Center in the left hand side so I'm going to use Center left save it and we have it displayed over here now instead of doing this alignment Dot Center left what you could do is remove the Align widget go to your column this column not this column that we have over here this column is related to these things over here we want to go to the column that controls all of these things and here set the cross access alignment to cross access alignment dot start as soon as you do that everything starts from the left hand side from here so as I've already mentioned before and I'll do it again if you've forgotten main axis is this thing right over here and cross axis is everything from year to year so when we set cross access alignment dot start everything starts from here if I set it to cross access alignment dot end everything from will start from here okay the difference between using a line widget over here and using cross access alignment is this cross access alignment will set it for all the descending widgets for these cards that we'll display for additional information for these things over here but align only sets it for one particular widget in our case that was the weather forecast widget cool so let's go down we have our weather forecast looks good now we are going to have our size box again so we are going to set a size box of height 20 again save it then what we want is a list of widgets showing up over here and how this works is something like this this is scroll level okay because there are more than three things that we want to display on the screen together and we still want to display more stuff so it is scrollable over here so I want that scrollable thing to be present how can I do that well I can put a row that would be good and inside of the row I can display these cards that sounds good so let's go ahead and create a row in our row we are going to have children and my first child is going to be well this thing over here so I have to design this component on my own so let's go ahead and Design This so we are going to have well again a card because it has an elevation and this sort of looks like a card only just like we had before right it has elevation of its own so it gives like a 3D visual it's coming on the top of your screen and that is what a card is so we can use a card again then we can use a child and the child is going to have well a column directly which shows a Time the cloud icon again and the temperature so we're going to have our child column then children and the first child is the time so my time is let's say zero three zero zero let's save it come over here and we see this perfect but the problem right now is my card only taking as much width as my text require and definitely my text is not going to require this much space so what I can do is set a custom height or width again so I'm going to wrap my card widget with a size box again where I'll set a custom width to let's say 100 save it come over here and this looks bigger nice now after this text we are going to have a sized box but even before that let's go ahead and set the properties of this text this text is bigger in size than this thing right here and it's also bolded so we need to set two properties inside of the style and we've done this so many times I hope you can do this on your own in the textile we are going to have font size and the font size is 16. font weight and the font weight is fontway dot bull save it come over here and this looks good now after this we leave our space again so we have constant sized box and then we have our height set to 8 we leave 8 spacing and after that we need a cloud icon again so we have icon icons dot cloud and the size is let's say 32. save it and we'll have a cloud icon if we remove the size icon and just display it it's quite small and since I know it's small I set it to 32 but it really all depends on how you want it to look it can look a different and you'll be fine with it but I like this look better I'm trying to replicate what I just created over here in our third app we're going to design a dribble UI so you'll understand how to create one specific UI but this weather page is your own creativity so you can just do whatever you want I'm going to follow this kind of design again we use a spacing and to be consistent with what we used above I'm just going to copy paste my size box and then we are going to use the temperature so I'm going to copy this text now paste it over here and let's say my temperature is 320 save it and this is bolded I don't want it boldered Also let's put decimal aware 320.12 let's remove bold save it and it's quite big if you can see over here closely look at it this text is bigger than this text why it's not because it's bolded it's because its font size is bigger so we need to reduce its font size let's try to remove this textiles totally and then we are able to match it this looks better in my opinion all right so I'm going to use this now after this um I do want padding to be present just like we had in this card it's a total replica if you want to call that so let's go ahead and wrap our column with a padding property so we are going to have our column wrapped with padding and padding is going to have Edge in such dot all it save it and you'd see it right over here looks good and this looks just like how this looks also the elevation is kind of small I just realized so let's increase the elevation as well to six then it looks much better and much similar to what we have already and one last thing that is there is the Border radius this border radius is more curved and this is slightly less curved so we want to set a border radius on this card so we can either wrap the padding widget with a clip or Rec widget again so that we have the nice padding or we can just remove this padding and wrap it with container then you pass a border radius property to it now container doesn't have a border radius property mentioned over here you can check for yourself but what it does have is decoration and what it requires is box decoration it requires just a decoration but if you try to create just a decoration that's not allowed because it's an abstract class what you can use instead is box decoration and we've seen this class before where in Cupertino design when we were trying to design something we had to pass in decoration remember the text field that we had Cupertino text field that had a decoration or a style property that required box decoration and we passed in box decoration that's exactly what we need to pass in over here and then we can pass in the Border radius which has about radius dot circular to let's say 12 or 10 or 16 whatever you want try test it on your own just see what you like and use it don't blindly follow what I'm following because you're building an app for yourself you want it to look how you think it should look so this looks more curved now and that's good however this card doesn't look as good as this one why because if you'll see this text has more padding and you can increase the padding over here let's go ahead and set it to let's say 18. save it and you have more padding but it still doesn't feel as good the reason for that is quite simple we have set a restriction over here that your width should be 100 no matter what the width should be 100 for the card now if I remove this and you know let's set it back to 12 again we have a card looking like this and it doesn't look very good that's why we had set the size box to a card in the first place but even with that we are just saying that hey the card should have a width of 100 that's not what we want because then we are limiting the height of the card what I want to do is set the content inside of it to have a width of 100 so what I'm going to do is wrap this column with a width and since we already have a container we don't have to wrap it with the size box we can just mention the width property over here and set it 200. and once we do that you see this card looks much better than we what we had before other problem that I have right now is there's too much spacing over here that this card feels disconnected from weather forecast it doesn't feel that this is a weather forecast it just feels like this is a thing of its own so let's reduce the size box height over here let's set it to 16. and then it looks much better otherwise it just feels disconnected from weather forecast text simple now what we want to do is take this card and paste it five times right so we can have one two three four five save it and we have the cards showing up nicely but the problem is they're exceeding the limit of the screen obviously why wouldn't they exceed the limit of the screen we only have space for 4.5 or 3.5 cards plus we have a padding property over here which restricts it even more right we have over here in the top of the column padding agencies.all 60 so we are leaving a padding of 16 from here because of which our cards can only come till here so that's why we had this now how can I make these cards not these cards this entire row scroll level so for that we have a widget we can just press Ctrl shift R then we'll have rapid widget and we have a widget known as single child scroll View when we use this widget whatever child we have inside of this is scrollable and when we save it you see it's not really scrollable even after hot restarting and that's because it has a direction of its own it is scrollable only in the vertical Direction but not in the horizontal Direction so we can change its scroll Direction over here so we have scroll Direction access dot horizontal and once we do that the error goes away and this thing right here is scrollable so with single child scroll view you're basically telling that hey whatever widget you have and it exceeds a certain width or a certain size you can wrap it with single child scroll View and it will make the entire screen scrollable and that's quite convenient and this is single child scroll view because it only has one child and its one child is a row now if you want multiple child scroll view you can look for multi-child scroll view but there's nothing like it because most of the times you'll only need a single child scroll view because then you can pass in a child and then your row column which it's whatever you want okay so let's go down and we have our stuff over here but you'll see we have to scroll much below just to see one card widget and since we are used reusing the same card everywhere it causes a problem for us what problem let's say I want to change the size of this icon I change I want to change it to let's say 40. I want to make it look bigger now what happens is when I change it over here I only change it for one card I have to change it for all the other cards so I'll have to go ahead copy this for T paste it over here over here over here and there's a possibility I miss out on something also since you have warnings I want to make sure that everything is constant over here so the warnings go away so I have to manually do it for every single card now that's not suitable is it so what I can do is extract this widget out of here also press command Z to set it back to the original height because this size 32 is perfect for me so coming back to what I was talking what I can do is extract this card widget into a separate class of its own that way I can just return One widget and I have a single source of control if I want to change how a cloud looks I can change it in one particular widget itself I don't have to go ahead and change it every single place just like we did in Border remember when we had our currency converter material page and we had a border for our text field we made a variable that made sure that you can have it over here now what I'm going to do is instead of creating a variable I'm going to create a particular widget of its own so that I can store it so what I'm going to do is take this card control X then go outside of this class and create a stateless widget let's go outside of this class not inside of this class here we are going to create stateless widget and then we are going to call this widget early forecast item all right this is what I'm going to call it why because it shows me the forecast for every r as simple now I can copy this card I think I already copied it but let's just do it again let's return a card from here then put a constant Also let's remove the unnecessary constant from size box because their parent is a constant itself now we can take this Ali forecast item instead of returning a card I'm going to return Ali forecast item instead of returning a card again I'm going to return an Ali forecast item let's copy this again instead of returning a card Ali forecast item instead of returning a card early forecast item so we have our four hourly forecast items we are missing one let's put another one so we have five cards perfect so we have our layout done for this as well then next thing is the last section the additional information section so similarly we are going to remove this placeholder now no need for that we already have that the last thing is this additional information we're going to leave a size box of height 20 Also let's put a cons for the entire single child scroll View no errors now you see perfect then we need a text again which has the same height as the weather forecast so I'm going to copy paste it and call this additional information save it come back over here and there we have it now I challenge you to make this on your own we have sufficient knowledge of what we need to do do you have to use a card do you have to use something else you have your own knowledge for this so go ahead and try it out on your own and let me know in the comment section if you were able to do it now your code doesn't have to match mine if it looks similar then it's all good if it doesn't then maybe you can copy my code however it's always good that you try it on your own so let's go ahead and create first of all a row and even before that let's put a height over here constant size box height 16 and after that I'm going to have a row where we are going to have children and the first child is going to be our first additional information item which is this thing right here so since they are vertically laid out I'm just going to put in a column so we have a column in our column we have children in our children we have an icon at first and the icon is icons Dot and this is kind of like a drop icon so let's search for something icons dot water water is kind of like a wave so let's put drop there's nothing like Drop maybe water drop and we have water drop exactly like this thing okay cool so we have our icon over here and what I'm going to do is make sure my icon is as big as this icon there's consistency in our UI which is good so we are going to have a size of 32 which increases its height then we are going to leave some spacing again constant size box height eight again consistency even here we had a spacing of eight same thing we are doing then we have our text which says what's the label for this so like what is the thing we are showing we're showing humidity so let's have that save it looks good enough if we just scroll this back to the normal thing yeah I think they're pretty much the same after this we can again leave a height and then we need the value like what's the value of this humidity let's go ahead with 91 product text then we need a style and this is definitely bigger so we just want to leave textile font size 16 save it 91. but this is not bolded so let's go ahead and bold it now you understand what I'm doing it's the same thing we are doing repeatedly because these are a very few widgets that continuously keep repeating row column icon text icon button gesture detector Inkwell container size box you know same things keep repeating for 90 of the uis things like backdrop filter come once in a while so you don't have to worry about those kind of widgets okay so we have humidity over here and again the same logic if I want to change the design of this thing I'll have to change it three different times if I paste it like this you know since I want three columns over here I'll have to keep pasting it again and again so instead what I can do is put it in a widget of its own and I can do it right over here but the problem I'm facing right now is I can stack everything up in one single file but does that make sense if I put everything in one file not really so I'm going to put everything in different files all right so I'm going to go to the left folder I have whether forecast item dot dot import flutter material dot over here then I'm going to paste it Ali forecast item not weather forecast so let me rename this to early forecast item good naming is a must when it comes to programming just like variables then we can press command full stop it tells us to import Ali forecast item let's do that save it then we can copy this column make sure you copy this entire column and we can create a widget of its own now there's a trick you can do instead of creating it on yourself you can press Ctrl shift r then you say extract widget give the widget its name the name of this widget is going to be additional info item not N4 info item and you see it creates a widget by itself it also automatically puts additional info item over here let's put a const let's remove size box from here save it and we'll take this in a separate file of its own again so we have additional info item dot dot we can import flutter not physics dot dot material dot dot now you might say hey this is quite redundant and why do you have to continuously keep doing it well that's because when more Engineers are working segregation of files and having one particular component in one file will make much more sense than having everything stuck together in one file what would happen if I just stuck everything in just main.dot file it wasn't a good thing so I'm sticking everything in one particle of file of its own now let's import this thing right here by pressing command full stop again and let's put additional info item three times cool now the problem here is everything is stuck together so do I have to add a padding widget not exactly because padding widget will not make sure that they are spaced out evenly if you see aware everything is spaced out evenly what can I do such that just paste evenly so for that row gives us a property in its mean access alignment which we didn't discuss remember we add main access alignment Dot and we add a bunch of options over here Center was basically centering everything end was basically taking everything to the end start was putting everything to the start but there were three options that we didn't talk about space around space between space evenly because those required you to have multiple components and in our app in our first app we didn't have those components and when we did have those components like text text VLAN button I forgot to mention it so here I'm mentioning it and this same thing is even there for our column all right we'll take a look after we take a look at this main access alignment properties so first option we have is space around what happens in space around is you tell it to space around each and everything so there's space away or space aware then for this widget also space away your space aware then for this widget also space away or space away up if you use space around all of the widgets what happens in space between is everything is spaced between those widgets it's not around it's not happening in both the direction the space is not being left from here and your both it's only being left from here here so it's around so for the starting widget it's going to be only here for the middle widget it's going to be year and year and for the ending widget it's only going to be from here that's what space around is or space between us space around says to leave space around everything space between says that hey leave space between everything I hope English makes sense you know it's all in the English and then we have space evenly what we require it spaces evenly everything but to be honest space evenly doesn't look as good as space around so I'm just going to keep space around all right now you can use space evenly if you like that design I like this much better because there's much more spacing and much more clarity now the benefit of using main axis alignment and not using padding is if I have four widget let's say it automatically adjusts I don't have to add a padding to the fourth widget over here if I have a fifth widget you see it automatically adjusts according to the conditions that's the good thing about it but anyways I only need three things great so I have our entire UI created and it looks awesome in my opinion but if you see additional information doesn't have that much of height over here this does have so you can reduce it to Heights to let's say eight and this will look better also for weather forecast if you want to decrement this size you can go ahead and decrement that let's say put 8 and that will look better for you so yeah this is our UI design perfect now to show you the column thing that I was talking about column has the same main access alignment properties if you have main axis alignment dot start or dot space around let's say everything is based around in the entire screen first widget over here then spacing so that space around again space around so this space around every single widget here if we have space between the space between all of the widgets and it looks quite similar to space around then we have space evenly this also looks quite similar but there is some change so my point is you have the same stuff you can do in Center everything gets centered but for me I want the default option of main access alignment dot start because that looks perfect great what I want to do is make sure that everything can have a different value of its own right now what we are doing is saying that hey additional info item is going to have humidity text it's going to have the water drop icon is going to have this constant text whenever you initialize additional info item these are the things that get created unlike the design over here I cannot put wind speed I cannot put pressure I cannot put all of that stuff because whenever I create this widget we have this stuff displaying So to avoid that what I can do is take everything here from The Constructor why because every time you initialize 10 you ask what the icon should be what the label should be what the value should be and that's exactly what we want we want different items for every time we create an additional info item so let's go ahead and create a Constructor how do we create a Constructor now well first of all we Mark every widget a final because it's a widget right and widget are immutable especially stateless wizard and even stateful widgets are immutable all widgets are immutable so we need to have final for all our properties so we're going to have final I can data because I can requires icon data then we are going to ask for the icon and we are not going to initialize anything because if we initialize then we are itself giving it a value so it doesn't make sense to put it over here we can just put it over here we need to ask it from The Constructor so we are going to have required because this is a named argument we have learned it in Dot required this dot icon now I can take this icon and pass it over here now you see we get an error over here saying that whenever you initialize additional info item you need to pass your own icon we get an error here also saying that hey you cannot put a const because this is coming from the Constructor and the value from The Constructor can change so this cannot be a constant it's a dynamic value so let's put constant for the size box now even for this text we need to take it from the Constructor itself so let's take final string label then we have required this dot label so I can ask for label over here again this is dynamic so text constant is not required so any value that is coming from the Constructor cannot be a constant then we need a value text so we have y null string value required this dot value now I can take this value and paste it over here so text string value is not is a is a non-constant but textile can still be a constant right so we can put a constant over here simple and now with this we have access to all of these properties over here so every time you initialize additional info item you need to pass in these particular properties so let's go ahead and pass icons dot water drop as the first icon because our first thing is going to be humidity then our label which is going to be humidity and then finally the value which is going to be let's say in 91. and when we come over here well the error gets a result now we need to do it two more times so our icon here label here and value year is required now what is our label wind speed so let's go ahead and type wind speed the icon for it is going to be icons dot air because that's what wind is and then we are going to have seven point 5 let's say then again we have to mention I can label value so my value here is going to be let's say 1000 pressure and I didn't find any particular icon for pressure so what I did was go ahead and use icons Dot Beach since I didn't find it if you have anything related to pressure you can use that but I like this much better so you see everything has its own value now same thing we are going to do with the weather forecast as well here in our Ali forecast item you'll see every time we initialize it gets its own static values we need to pass it from The Constructor so that the values can change every time we initialize so do the exact same thing pause the video try it on your own and I hope you're able to do it if you're able to do it then congrats you've understood the entire concept if you're not then maybe you need to re-watch the entire thing so I hope you were able to do it let's go ahead and try it on your own and Ali forecast icon item the first thing we require is final string time then we need final string temperature then final icon data icon now we need to mention required for all but I have a trick for you you can press this bulb icon add final field parameters and it automatically adds required Arguments for you great saves a lot of time for us let's go to the Ali forecast item and mention it so we need to mention time time is let's say 0 0 first then we have icon it will be icons dot let's say it's cloud because it's raining then the temperature is going to be what's the temperature over here 301.22 let's save it I'm going to paste it four more times so one two three four let's remove them so this will be 0 3 let's call it sunny and let's say it's 275 I hope 275 degree Fahrenheit is sunny and I think if I think about it 275 degree Fahrenheit is quite a lot of heat it's more than 100 degree celsius so we are making a mistake here instead of 300 degree Fahrenheit we need 300 Kelvin that's what the correct thing is so I apologize and I know you might be thinking all the time that hey this is incorrect it's not actually in degree Fahrenheit it's actually in kelvin I misinterpreted it so my bad so anyways uh let's go back to our stuff 275 is not at all Sunny so let's go ahead with 300.52 then 301.22 then 302.22 let's call this sunny again we have 300.12 and finally 304.12 then also change the time zero three zero six zero nine and twelve so yeah we are able to change everything let's also put everything over here so time over here is going to be time I can here is going to be icon and the text here is going to be temperature constant let's put everywhere constant now if you're wondering how I selected multiple cursors at a time I did that by pressing option so when you select one place put option on another put option on another and then you're able to do it that's how I do it on Mac I'm not sure about Windows but you can Google it okay now let's restart it and there we have it that's our app perfect now again I apologize and you know I had been thinking it wrong it's not actually degree Fahrenheit it's Kelvin because it makes more sense degree Fahrenheit would mean that this is like over 100 degrees Celsius and that just doesn't make sense right so this is Kelvin which basically means that it's 27 degrees Celsius Also let's correct the spelling of humidity there Okay cool so yeah we are done with the basic structure of the app now the next thing is to get data from API from the web so that I can display it on my screen real time and we also need proper loading indicators we need proper error indicators all of those stuff so let's go ahead and set it up so to get the real-time data we need access to an API and to call an API we will need the HTTP package we've already seen that in the dart section so let's go ahead and install the HTTP Plugin or package to our flutter code in dot pad it was available for us but here in flutter when we are on our local system we have to install it so we need to go to pubspect.aml in the dependencies section we need to add that dependency Also let's get the HTTP version now we have pub.dev packages slash HTTP where you can find the HTTP Plugin or a package then you can just copy it paste it over here save it and then it will run flutter pop get command flood up get command gets all the dependencies all of the things that are mentioned over here we'll see fonts assets everything and then it refreshes our project now we'll be able to use the HTTP plugin in our code so let's go ahead right at the top and we are going to create our function over here and that is going to return a future and let's call this function get current weather we can Define functions in a stateless widget that's not not allowed you can definitely do it so let's put async over and we already know how to put HTTP calls it's all given over here first thing is to import it and to refresh your memory as HTTP is given here because we don't want to call just get function like this which is present in http.dot file which you can come over here and see so we are using HTTP dot get this makes it easy then it requires something known as an URI and to pass a URI you can just do URI dot parse or UI dot https either of them work but I'm going to go ahead with uri.pass because I already have the URL it's going to give me now if you're wondering what URI is URI stands for uniform resource identifier URL stands for uniform resource locator the difference between URI and URL is that URL is a subtype of URI URI has a particular scheme which is followed by URL as well but URI is like a bigger set and URL is a subset of it so let's go ahead and pass our URL here and how do we get our URL well to get it we have to access the API and the API we're going to use is given by open weather map in dot section we are used Json placeholder that was just a dummy and a fake mock API all right this is the real API it's giving us real data so what will be the temperature in London Mumbai England New York Etc so how do we get access to its API well first of all I'd like to mention that there are multiple websites that offer apis for weather but I like open Weather the best because it offers a free API that everyone can use it also has a paid version for advanced stuff but for us the free API is enough all right so what you need to do is go ahead click on sign in then you need to create an account first so let's go ahead and create an account my name is I'll enter my email password repeat password click on these two things and the captcha and create an account and I'll see you after I do these steps so I'll check my email I'll confirm it and you see they've sent a verification email then just click on verify your email and this email address has been successfully confirmed now what we need to do is wait for another email open whether team will send us which will contain our API key it will contain the URL we can use for free in our projects so let's wait for it or if you don't want to wait for it you can click over here my API keys and you'll see your API key don't use mine because I'm just going to deactivate this after this tutorial kindly use your own API key and you'll also see aware that the email has arrived and it contains my API key and it says within the next couple of hours it will be activated and ready to use if I use it right now there's a possibility that I won't be able to use it and it will give me an error however I can do it later on and I can also create more API keys on my account page which we've already seen over here I can generate more API keys and it says to always use the API key in each API call now you might ask hey why do we need API key the Json placeholder didn't have API key right well it didn't have it because it was a mock data it was a dummy data it doesn't have any real value but this is real-time data it contains actual data of the weather and some user might call this API like a hundred thousand times a million times by just using a simple for Loop that means the API will be called a million times so that will cost the company a lot and the company obviously doesn't want that that's why API keys are there so that they can authenticate you they know that it's you who are using and they can put trade limits to how much times you can call it for our URL over here we have I think 1000 free API calls and after that it will stop working for us so let's go ahead copy this URL put https colon slash slash put this thing over here and save it let's break the this URL down and see what all it contains first one https which I had to add then API dot openweathermap.org data slash 2.5 this is like their model if you're familiar with chat GPD it also is working on certain models right it is working on 3.5 model this is their 2.5 model open weather maps 2.5 model the three model is a subscribed version I'll show it to you over here if you go to open Weather API you see one call Api 3.0 and it has minute forecast early forecast daily forecast it has a lot more stuff than a simple API cool then we have weather because we want the weather you're just having the path then you have question mark Q is equal to London most of the interesting stuff happens after the question mark where you can change it because this is what is known as queries even if you go to Google after the question mark you'll see the cool stuff the stuff you can change so we have question mark Q as equal to London so this is basically this place name you want to get the weather off so we can take this out and put it in a variable of our own let's call this London over here let's take the city name and put Dollar City name like this then we have comma UK it's just telling London comma UK this is where I want to get the weather off then we have app ID and this is our app ID Now app IDs need to be stored in dot EnV file which can be hidden by get ignore and even when you want to deploy your website but assuming you're not going to deploy this website let's put it in a separate file of its own which you can ignore if you're pushing to GitHub now if you don't know what GitHub means don't worry about it just save it in a different file let's go ahead and call this secrets. and here I'm going to have constant open whether API key which is equal to this time now we'll copy this come over here and have Dollar open Weather API key also press command full stop to import the particular secrets.file let's see if this much and let's see what we get let's put a weight here we already know the protocol let's have final result is equal to this then we are going to have print result dot body because I just want to see what all it gives me and now if I restart I see absolutely nothing why because this function is not called we need to call it somewhere right we can go ahead and call this in build function but I already told you before that build function needs to be kept away from asynchronous stuff and I've also mentioned the reason before build function should always be the least expensive so you can you should not call this function in the build function so what should we do well we can do one thing we can convert the stateless widget to a stateful widget then use the init State method and then we can call this particular function over there right that sounds reasonable so to create a stateful widget we'll have to do stf L and create a stateful widget right not really the dart and flutter extension is quite generous with this you can just press Ctrl shift r you get the options to change stuff and you have convert to stateful widget if you just click on it it will make the appropriate changes and convert it to a stateful widget without giving any error so our stateless widget is Now stateful widget with just one click and our method is also defined over here correctly not inside of the stateful widget class it's correctly defined inside of this class now let's go ahead and create nth state the super.net state should always be at the top then we have get current weather save it command J and you see as soon as we reload it gives us an error if we restart it will again give us an error the reason for this is 401 error 401 error stands for bad request as you already know 404 stands for page not found so 404 is so four zero one is there so that you say that it's a bad request and a message is also provided for further context saying invalid API key please see this thing for more info now if I click over here open it you see API calls return and error 401 and these are the possible things that's why it gave us an error you did not specify your API key we did your API key is not activated yet next couple of hours it will be activated and ready to use so this is a problem rest of the things are fine we are using the free subscription we are not using the wrong API key and only we have not waited for the uh for a couple of hours so I'll see you after a couple of hours when our API key is activated and we can use it so I'm back after three hours and the data is now coming we have all the data we require to display it on the screen so now let's just understand what is useful for us and what is not so that we can only include parts that are useful to us and extract them right so the first thing that we require is well I just want to take this and put it in some form of visualizer where I can properly see the data so what I'm going to do is copy this URL go to Google Chrome paste it and obviously we need to pass in some stuff like the city name should be London the app ID should be present so let's go ahead and pass in the app ID which is present in secrets and when I press enter I see all the stuff that I require right now if you see this data this data is giving me the weather the main temperature so I'm getting what the temperature right now in London is and I'm getting wind speed and all of that stuff but I'm not getting the forecast and that's because we have used the wrong API the API we should be using is not data 2.5 weather because this will give us the weather I want forecast so I'll just go ahead and pass in forecast here and I'll be able to get the forecast of the weather you see this list has 40 items and if you're wondering how I'm having this Json in this format it's because of an extension and the extension name is Json formatto all right now you see we have a list that returns 40 items and in every list we have an object and in this object or a map we are getting the temperature then we are getting the weather name that we require in our app over here then we have the pressure humidity all of that stuff right so we need to use the forecast wire and using this we can extract the data so what is the data we require well first of all I want to check if it's a status code of 200 or not the status code of 200 basically says that hey this request is successful otherwise we get a status code of 401 which was like bad request so here first of all I want to make sure that it's a correct request also I want to try it in a wrap it in a try and catch block so let's go ahead half try catch block then we have throw e.2 string I've not talked about throw in the dot section because I wanted to specifically show it over here what through does is basically like if you want to return something from a function and suddenly you encounter an error so you just throw that error you're saying that this function when it was called did not give any result it resulted in an error and that means your app will crash if it is not handled so I'm just throwing the error that hey I received an error just take it and display it on the screen or do whatever you want so we need to correctly handle this throw all right otherwise our app will break the next thing I want to do here is first of all check the status code if it's 200 or not so for this I can do if response dot status code is equal equal to 200 this is one way of doing it the other way of doing it is taking the status code that they've mentioned over here so first of all we'll have to decode the response dot body because it is in a string format we already saw that in the dot section so we have Json dot Json decode put it in rest dot body save it and also you see as soon as I import Json D code dot convert gets imported now you can see Json decode required a string source so we have passed in response dot body it returns a dynamic so what I want to do is final data is equal to Json D code and after I have the data with me I can just check if data at COD that's what it's called right Cod is not equal to 200 and I'm putting it in strings over here because Cod returns to as a string right the alternative to this could be converting this to an integer so you could go ahead and do n dot paths what we have learned before to convert from string to an integer and then you can check is not equal to 200 like this both of these things work you can use whatever it be you prefer and that will work fine all right so let's go ahead with this part right here so if the status code is not 200 that means some error occurred if some error occurred then we again want to throw saying an unexpected error occurred I hope you are understanding what throw means I mean of course you won't understand it right now but when we call the function it will basically throw you an exception saying that hey there is an unhandled exception saying that an unexpected error occurred all right and in the else condition or you can just have it over here no need of health condition because through basically returns from the function it doesn't execute any further just like return does all right so if you put through here it will terminate the function at this point it won't go any further and finally what I'm going to do is print data at and the thing I want to print is the temperature wire so we are going to have data which gives us this thing data at least so with list I'll access this thing so I'll have data at least and since it's a list I will access the zeroth element on it to get the first prediction or the First Data stuff so here I have it and I'll do listed 0 then I'm going to have Main and after that I'm going to have temperature okay so list at 0 which is the first map then we have Main and then we are accessing the temperature so that should give us let's say 291.8 or something similar let's go over here let's restart the app and we do c291.65 so we were successful in retrieving the correct stuffs now we just want to display it on the screen right I want to display it over here how can I display this thing over here it's enclosed in a function right so what I can do is create a global variable let's call this double temperature which is equal to let's say 0 initially or you might be tempted to use late double because we are assigning the value late right so this should work but let's see if it actually works I'm going to set temperature equal to this okay and now I'm going to pass temperature over here so I'm going to have dollar temperature k so it gives me 291.12 Kelvin now I'm also going to remove constant let's put the correct constants everywhere again I'm pressing option to select multiple cursors and put constant cool let's come back over here and you see late initialization error field temp has not been initialized let's restart it maybe that works not really this doesn't work why because if we come aware we get current weather this thing runs before the build function and that's cool but what if I do print build function or let's call this init state then I'm going to print this statement again over here function called then I'm going to print after this API call all right after this API call I'm going to I have API ended all right and finally I'm going to have a print statement saying build function called now let's open by using command J restart and you see over init state so we have in its data layer then we have function called and then we directly have build function called so it skipped this part but earlier we printed this value and it got printed correctly right then why is it giving an error right now well that's because what you're doing is assigning this to late late basically means that you have a contract you need to assign it before the build function is called if you're using it obviously in the build function if you're not using it in the build function late doesn't really care but if you're using it somewhere it will start to care so what happens is late double temperature then you are having init State then you have get current weather this function gets called and this API call is there now this API call is going to take time right you're retrieving some data from the web that will take time depending on your internet connection but while it is waiting we have already executed the build function because that's how asynchronous stuff works it won't wait for it to complete it just said hey just complete this in the future I'll just go ahead and do my stuff so it called the build function and here when the build function was called you also called The Late variable temperature which hasn't been initialized that's the problem so what should we do then what is the fixed aware well first of all let's just remove all the print calls I don't like seeing warnings that much unless they are constant warnings so we are back to normal now so one possible fix here is having double temperature is equal to zero as soon as we do that press command J restart the app come over here we get 0.0 Kelvin again the value is not initialized why is that the case well that's the case because you again set this to zero then you have get current weather it is getting the data in the background let's say and in the meantime it also called the build function if it called the build function it already used the value of temperature given to it which was zero and later on when the value arrived the build function was already ready and displaying it but then you said hey set temperature equal to this thing over here so you're reassigning the value after the build function is called it's as good as calling a function after ontap so my point is you just need to wrap it with a set state if you do such State what will happen is when you restart you see 0 and then it converts to 291.65 because initially the value is 0 then it's retrieving the value in the meantime you'll show the value of 0 over here and then you finally got the value of temperature which you have assigned and then you call such state to rebuild the build function and that way you get 291.65 Kelvin so I hope that made sense to you if it did not ask me in the comment section and I'll explain it to you again but anyways if we again restart the app this does not look good it's not a good user experience to show zero Kelvin first then show 291.65 Kelvin it's just not a good experience so what I want to show instead is a loading indicator so as long as this function is loading and we are getting a data we are just going to keep loading the screen so I'm just going to replace this body part with a circular progress indicator instead as long as as it's loading all right so this all would disappear and only a loading indicator will show up so let's go ahead and have a body here now how do I show a loading indicator here well the first approach is to use the temperature and have if temperature is equal to zero then we can use a loading indicator now what is the widget for loading indicator well it's just progress indicator and you can have two types of progress indicator or three types I don't know but you can have linear progress indicator refresh progress indicator circular progress indicator the one I like the most is circular progress indicator however go ahead and try linear progress indicator and refresh progress indicator for yourself I'm going to go ahead with circular progress indicator now I'm also going to have Constable air the reason I'm doing temperature is equal equal to 0 is because the temperature can never be zero Kelvin if it's zero Kelvin then we are freezing it's absolute temperature right that's why if it does some other value I wouldn't put is equal equal to 0 because some other temperature can be attained let's say the initial value was 270. I wouldn't do temperature is equal equal to 270 because temperature can be 270 Kelvin but because temperature can be 270 Kelvin when it is coming from this thing right here some place might have a temperature of 270 Kelvin but no place has a temperature of zero Kelvin that's why I'm using it to display a circular progress indicator however another option could be to use another variable called Boolean is loading which is initially set to false then you come away a usage State you set is loading to true so you're basically telling hey rebuild the build function is loading is now true then here you have is loading set to false and you come down and you just have is loading if it's loading then show circular progress indicator otherwise the padding is fine now let's restart and you see we see a circular progress indicator in the left hand side and then this thing so that means our loading indicator is working however if you use temperature is equal equal to 0 as well it will work just fine let's restart you see 270 Kelvin not 270 Kelvin sorry I'll set it to 0 I'll restart loading indicator is there and then I see this thing over here so I hope that made sense to you now you can use either of those approaches it is on you but my point right now is this is quite tedious to be honest I have to set up my own loading indicators I have to set up my own error handlers for example if I just misspell in something in the API and then I start to run my function I'll see an error all right you see unhandle exception format exception blah blah blah blah and it continuously keeps loading because I haven't set up my it's loading properly in case of an error I have to set it to false even here if there's an error I have to set as loading set to false so I have to do all of this stuff on my own and it's quite tedious for me luckily flutter has something for us let's look at it also you see unhandled exception format exception all of that and if we use let's say data 3 over here and then restart you'll see unhandled exception and unexpected error occurred what we had over here so basically throw is just returning an exception for you and the error message can be whatever you have written over here so I hope that made sense to you what this throw does it basically throws an exception and whenever you have an unhandled exception you have to add a try and a catch block here and do stuff on your own however you have to put a try on catch block here let's have e over here and then you have get current weather then whatever error it gives you just print e all of that stuff you'll have to do it or just don't throw from here however my point is there's a lot of stuff to do a lot of error handling to do instead I can use something provided by flutter which will boost my performance by a lot so let's remove energy State let's remove this loading let's remove the temperature as well all the set states are not required anymore we can keep this line over here because we are going to extract the mean temperature again but not over here and what we are going to do is just return data in case of a status code of 200. now let's come over here let's remove the loading indicator for now and here again we're going to go back to the static value however you already know constants are not going to be needed anymore because we are all going to have a dynamic value so let's not use constant because the value is going to keep changing it's coming from an API all right and what I'm going to do is wrap padding widget with another widget and what is that widget future Builder this is a widget provided by flutter that eases Our Lives by a lot when dealing with Futures and if we want to display something related to our future so we're going to have a future we are going to have a builder then we are going to have context snapshot I'll explain what snapshot is and we're going to have an RO function returned from a builder so these are two required arguments of future Builder quite convenient future and Builder now I'll explain both of these things but let's resolve the error we have only future so what is this future buildup well basically you just need to pass in your future over here it can be anything future of object and object is a super class of everything so you can pass any function over here any variable that is a future and it will build according to it so if I go ahead and return my function which is the future so I'm going to have get current weather and then let's just convert this to a block all right I don't want an arrow function because I want to print something here I cannot print function does not allow it it just allows me to return one thing if I just convert it to a block I'll be able to print it so press Ctrl shift R get the refactoring option and it asks you to convert to block body so let's convert it save it it will format let's go right over here and we are going to print snapshot what exactly is this snapshot also we're going to print the runtime type of the snapshot so press command J we're going to restart and we see something like async snapshot Dynamic connection state DOT waiting async snapshot Dynamic so this is the runtime type then we have our entire value coming and E6 snapshot dynamic so what is this thing over here well snapshot is basically a class that allows you to handle States in your app a loading state a data State an error State you can handle all of that using async snapshot that's what snapshot gives us you see over here connection state DOT tweeting why did this connection state DOT weight income because you were getting data from the web so it's saying that hey we are still getting your data then we have the runtime type because we printed it and after a while it said connection state DOT done that hey we got your data it's successfully there and it printed it out to us this null null null stands for each and everything if it's if it is having data if it is having error if it is having loading what is it having so that's what null null stands for over here so anyways now that we understand this we can handle the loading State easily we know whenever there's loading State we have connection State DOT waiting so if we have if snapshot Dot now what do we use Snapshot dot hash data has error connection state right because this might be an enum or a class I don't know and this requires a connection State as well so I'm just going to have if snapshots dot connection state is equal to connection State DOT and it is an enum and it gives us values like active done none waiting when it's loading it is giving us waiting right so we can just use that and return a circular progress indicator Also let's return a constant over here perfect now if I restart I see the loading indicator and 200 Kelvin I again restart I see loading indicator 200 Kelvin now 200 Kelvin is not the correct value it's hard coded but you see we are getting the loading indicator and then our data so we don't have to handle all of the stuff on our own if there's error we can print it how we can just have if snapshot dot has error if snapshot has error then we are going to return constant text saying snapshot dot Arrow which is an object all right and this can't be a constant because snapshot dot error is a dynamic value it's coming from snapshot right it's not a static value it's not a hard-coded value or a constant value so we need to return text Dot to string because text cannot take an object it has to take in a string so we return an error all right so if snapshot has zero that means if the async snapshot has error then we just want a text to show the error on the screen and what return will do is basically just return this text from here it will not display anything from here and that's exactly what we want in case of error just display it to the user don't display wrong values that's not how our app works let's get rid of snapshot let's save this restart we have a loading indicator and there's no error so it doesn't show anything however if I just take this not take this if I spell this incorrectly let's say data 3 let's restart the app you see loading indicator and then an unexpected error occurred that's a good sign now if you want to return a different kind of message you can do that you can have data message because with every code which is not 200 we get a message as well when we had four zero one we had a message as well you see internal error shows up now that's what the error says if here I type in data at three forecast it says internal error and the code is 404 are favored not found so let's come back to our 2.5 model even here 2.5 model I think I'm going to keep an unexpected error occur that's a better message than whatever the API might give us cool so now we are able to handle the loading indicator and the error message now let's style it a little bit because the loading indicator is showing right in the left hand side corner so let's Center it to center it Ctrl shift r then wrap it with Center you all are experts in this now you can just pass in constant and now a loading indicator will be centered perfect I still have some problem with it if I restart it's showing a material design loading indicator on an iOS simulator what I want to do is show this kind of icon or this kind of loading indicator only on Android devices not on iOS devices that's why what I'm going to do is use circular progress indicator dot adaptive with adaptive it changes based on the operating system it's on so if it's on iOS it gives a iOS kind of indicator and if we open a pixel it will give us the material design progress indicator and that's really cool it just gives us a native feel now if you want to use circular progress indicator you can use it I just wanted to show this cool thing to you also this text can be centered so let's go ahead and wrap it with Center sweet now we have handled the loading State we have handled the error State and finally we are on the data state so let's go ahead and retrieve our data for our first data we have already implemented the logic for it so let's just copy that so here we're going to have final data which is equal to snapshot dot data and this data can be nullable all right so we are just going to apply here that hey the data here is never going to be nullable also I've already mentioned this to you before whenever we return future or anything like stream future always make sure that you have a generic type because future Dynamic isn't cool we've discussed this in dot course so what I want to do is return a future of some type and here I'm going to return data but what is the data well it is a map because at the end of the day we are getting an object of string so everything over here is a string in the left hand side all the keys are strings but on the right hand side sometimes it is integer sometimes it is string so we can just have future of map of string comma dynamic so here the dynamic is necessary because stuff keeps changing on the value side on the right hand side cool now if you come over here you see snapshot.data has a value of map string comma Dynamic with a nullable option first of all future Builder is correctly able to identify based on the future we provided over here and secondly this is nullable why is this nullable because it thinks that it might not have an error why does this have a nullable option because it thinks that maybe there's an error maybe there's loading state it cannot definitely have a value that's why it is nullable but now since we have handled the error State and you've handled the loading state we are quite sure that it is going to have a value otherwise you can just check it on your own if snapshot dot has data what has data does behind the scenes is just check if data is not null it's basically checking if data is not equal to null that is what snapshot.house data is and same goes for has error error is not equal to null okay you can do that but here I'm quite confident it is going to have data now I'm going to have final current weather temperature or let's just say current temperature because we are also having forecast right if there's forecast there's a possibility of having later values as well so that won't be current temperature so we have in our final current temperature and we're going to set it to data list 0 main temperature which was our main temperature or the current temperature that we want to show and finally we are going to come back here and type dollar current temperature Kelvin restart and with the loading indicator we get the right value perfect so the first part of our app is complete congrats to us now let's go ahead and change this icon and this text based on what we get so this icon over here is based on the text right if it's sunny I want to show a sun if it's rain cloud whatever I want to show a cloud icon and for that we have a value in our list which is weather Main so what I need to do is final current what do we call this current Sky because it is telling me how the sky is cloudy whatever so let's call this current sky and then we are going to have data at list at 0 same thing as before data list 0 then we're going to have weather instead of Main and then we are going to have the main cool now we can take this current sky and paste it over here so you're going to have cut and sky like this and it's going to be a string all right because main clouds this is a string so save it put it as constant come back over here and it gives us an error why because the type string is not a subtype of type int of index let's see why we get this error and the reason for this error is if you come over here weather is a list we neglected that we directly said hey data listed 0 whether is a list and what we are saying is called the main property on a list the list cannot have a main property only maps have that only objects have that so first we need to access this particular array and after that we can access main property on it so here we need to do whether at zero so we iterate or we grab the first element of the list and then we call the main method on it or the main property on it and when you come over here clouds are seen perfect now you see we are repeating stuff over here data at less zero so what I can do is shift this in another variable so I can have final current weather data is equal to data listed 0 because technically this current this consists of current weather data and now I can replace it with this now this is just an improvement so that you know you have better readability in your functions or in your classes or in your UI code and you don't have to repeat this stuff again and again data list 0. you just store it in a variable and you can use it anywhere now I'm going to take this current Sky I'm going to go down remove constant from icon and here I'm going to have if current sky is equal to either crawl cloud or current sky is equal equal to drain those are two possibilities all right and you can put or condition in a ternary operator so if it's either of them then we want to display icons.cloud otherwise icons dot sunny now if we come back over here we are seeing a sun and that's because the data we are getting is clouds not Cloud so we need to make sure this is the correct thing and you know make sure the case sensitivity is also correct clouds is not equal to Capital C clouds all right so make sure everything is correct you come back over here and you see clouds perfect so this part over here is done now let's move to additional information and after that we can get to the weather forecast so in additional information we have humidity and I've spelled that wrong even after trying to correct it let's go ahead and type it over here now let's get let's get the values of humidity and speed and pressure let's explore the API to see if that it has values and I'm just going to grab this first current weather because that should give me the wind speed the pressure all of that stuff I should not be going to the second element of this list because that contains the prediction for later on it's not the prediction as of right now you see it has a prediction of some other time this is the current prediction so to access pressure we have this thing over here which is present in main we've already done this before so let's go right at the top we are going to have final current pressure you want to type current you can type it or pressure because you have only one pressure in our entire app which is the current pressure and set that equal to well the current weather data so you can have current weather data so you're act already over here then you have to access main pressure so you have Main pressure cool now take this mean pressure go down an additional info item you see this thing over here this is this is where you can easily go from top to the bottom you don't have to scroll through stuff you can directly just jump from year to year and it just saves a lot of time for me so get used to this and it will save you a bunch of time especially in bigger code basis so we are over here now the value is going to be 91 but in our case not 91 sorry it's not humidity it's pressure in our case we need to mention a string but here it's giving us a number right all the numbers are marked in blue strings are marked and green so it's giving us a number so maybe we can have current pressure dot two string with two string we are able to only get the required pressure Also let's remove constant from here we all know it's not going to be a constant let's save it come back over here and the pressure is one zero one one perfect the next thing we require is wind speed how do I get wind speed well it's present over here in wind speed so same thing we'll go over here and Define a variable now obviously you can copy this and go down paste it over here and that will work fine for you there's no problem with it but when you have variables in one centralized place in my opinion it just gets so much easier because if you want to change anything you can change all the API related stuff in one place so let's come back to current wind speed and that is going to be wind speed because we are aware data at least is zero this thing over here then we are going to wind then speed and we're getting the value we can copy this go down then I have current wind speed.2 string again save it come over here we have 4.45 as our speed perfect and the last thing we require is humidity and humidity is also present in the same place as our pressure so let's go to current pressure now if you press command on our current pressure variable you'll be able to go where the current pressure variable is defined just like we can do with literally anything right if you want to go to sized box you can click it over here and we go to the flutter source code if you want to do that in your own source code you can do that as well so you go to current pressure now I'm going to copy this paste it again and now I'm going to have current humidity now I know I'm going a bit faster here and I'm doing that because this is all the stuff we have covered in the dot course just knowing what to use when to use I want to wait waste much time over here right so yeah main humidity we'll take this current humidity and paste it over here and again pass two string to it because it's a number come back over here and a humidity 48 is showing all good the last thing we want to do is weather forecast and that too for only five items you see in our API it gives us a list of 40 items the first one we've already used so we are not going to use it again our numbering is now going to start from 1. because 0 was used to display the current weather now everything from here is going to display the weather forecast so let's go to our weather forecast over here early forecast item let's call this early forecast instead of weather forecast all right that that makes more sense I guess now how do we handle this I want to iterate through a list which is a list get five elements and display them on the screen that's a major tough task to do here do you know how you'll do it try to do it on your own if you can and you'll be more confident if you do it but if you're not then I'll let you know you can think about using a for Loop all right when you use a for Loop let's remove a constant whenever you use a for Loop you can go from index one to index five and display it on the screen so let's try it what I'm going to do is for int I is equal to 1 because I want my list to start from one I cannot start from 0 or I can start from 0 and I is equal to 0 I is less than 5 because I only want five elements I plus plus then I'm going to have my Ali forecast item I'm going to remove the rest of the early forecast items and first of all we require a Time now where is the time mentioned in our list it's mentioned over here DT underscore txt in this format we'll get to the date format part later on we only want to get time but it's giving us date and time both but we'll get to it later on as of now let's just display the entire thing even if we get the render flow error the error that shows up in the yellow saying that the height is extended like we saw over here with our row when we are not wrapped it with single child scroll view remember that if we remove this widget you see this error this is render flow error and we will get that if we exceed the size already allotted to a particular widget so anyways um let's get access to the list so it's going to be data at least so it's going to be data at least at I not zero not one not anything but if we put I we get I is equal to 0 so that means data at least it's 0 that means you are getting the same value instead I'm going to do data at least at I plus 1 with I plus 1 I get the starting value as 1 till 5 including 5 all right so we'll get the correct stuff so we'll get elements from 1 or elements one two three four five that sounds good and once we are over here let's say we are aware perfect so first of all I'm just going to print the date time or the date and you can do two things for it DT which gives you date and let's say I think milliseconds since Epoch now what is Epoch Epoch is January 1 1970 so how many milliseconds have passed since January 1 1970 this is what the daytime is and in text this is what it represents third July 2023 12 am so you can use either of them I'm going to go ahead and use DT for now later on I'm going to use DT text so that I can format it according to the way I want and if I come over here we get type int is not a type of string because time requires string so let's convert it to a string and then pass it in and we have this thing over here and it keeps changing for everything we have one six eight eight three four to four hundred one six eight eight three five three two hundred all right so I hope you get the point then we can have the same thing over here data at least I plus 1 main temperature so we're going to have Main m come away and it says type double is not a subtype of type string basically temperature is giving us a double value temperature requires year a string value so call to string again come back and you see 289.84 287.855 and all of that stuff looks good and finally we want to display the correct icon now to display the current I can give already put a logic and we know how to evaluate if it's a good thing or not so what we need to do is go at the top have current Sky scroll back and we're just going to have if current be the weather data instead of current weather data I'm going to have data at least at I plus 1 right because current weather data is data at least at zero instead of having 0 here I'm having I plus one I hope you're following along so you have data at least I plus 1 then main then temperature mean temperature not mean temperature sorry I plus 1 whether 0 mean and if that is equal to clouds or if that exact thing is equal to rain then we are going to have icons dot Cloud otherwise I can start Sunny then we save it become aware and you see when we add a sunny weather we had Sunny icon showing up now if we come back over here just to verify we are going to go over here we'll see that the main over here is clear and in clear we want to show Cloud no sun we don't want to show clouds clouds is only there for rain and stuff okay so yeah we have been able to build the app the problem here is what if instead of showing five things I want to show 40 things exactly how much this allows or 39 because let's say 38 and let's say I want to return or have less than 39 items here then what will happen well if I restart you see we get a bunch of our icons those are all good but what's Happening Here is they are not building on demand they are all building together now we are getting our weather forecast and that all is correct that's all good that's perfect but the problem here isn't about displaying and getting the correct data it's about a performance of the app all the widgets here are building together that's a big problem when we are returning like 40 widgets together right because it's like 40 widgets are building together isn't that just insane it will affect the performance of the app very much so instead of building 40 widgets together at the same time what I want to do is build this widget just when we scroll all right so it lazily creates our widgets only the part that is scrolled will get created otherwise it won't get created so it won't affect the performance of our app I hope you understood this if not I'll repeat you can skip if you understood what I'm saying is 40 widgets are being created together now that is a Major Performance thing because just imagine like 40 components on the screen together at the same time that's just making sure that your app performs less well so what I want to do is Implement kind of like lazy loading where the widgets are being lazily loaded not the data we get the data as it is but the widgets are being created on demand as and when I scroll all right so like if I scroll like this the widget should get created not all at once so for this I'm just going to go ahead and comment out the entire single child scroll View and I'm going to create my own early forecast from scratch using a widget which is very very important and that is called list view Builder see this thing over here list view Builder there's another widget called list view which we haven't talked about and list view is basically like you know if you want a column that is scrollable and you want to mention padding from the side you can go ahead and list use list View it will help you over there we are probably going to use list View later on in a third app but as of right now we're going to use list view dot Builder it requires a named argument of item Builder and it gives us context and index also one thing I think I forgot to mention is whenever you have for Loop if conditions inside of flutter code you don't have to mention brackets I'm so sorry I forgot to mention this brackets are not required when you have flutter code you can just mention for Loop no need of bracket and if you want to return more than just One widget you can have dot dot dot and a list okay so what you're basically doing is wrapping all of them in a list and then you're destructuring the list so that everything shows up for all the 40 Widgets or 39 widgets all right so let's remove it we only want to have one widget for Loop that's why I'm just going to keep it like this also let's comment it out again and let's focus on our list view Builder now listview Builder will build on demand it accepts item Builder which requires a widget to be returned which is nullable and it gives us build context again and an index now this index is there because you need to mention something known as an item count so this list view Builder is basically telling hey we'll help you to build a list of items that are lazily loaded so it will get loaded as and when you scroll but you need to mention the item count how many items there are and the item Builder so what do you want to build and for that we are giving you the index because obviously if you mention the item count let's say the item count is five I am giving it a static value here we are not going to know what to return for example I'll return Ali car forecast item but then I have to mention time temperature icon now how do I get access to time here we had I I Plus 1. this is how I would know I'm accessing one particular element from the list how can I do it over here that's why index is present just like there are four Loops I this is the index that will help us so let's go ahead get the data so we are going to have our data Final early forecast which is equal to data at least index plus 1 again we are going to have plus one because list view Builder also starts from zero so we have our early forecast now the first thing that I want to return here is DT which is the time so let's go ahead and have DT dot to string which is just time in two string then we have temperature so we are going to have early forecast then main then temp and Dot to string and finally we are going to have our icons I'm just going to copy this line I'm not going to type it again and paste it over here Also let's uncomment this so to uncomment it I'm going to press command slash and there we go and finally I'm just going to take all of this out in one thing which is final early Sky let's call it that then we are going to have index plus 1 and then if Ali sky is equal to clouds or early sky is equal to rain then we are going to show the cloud otherwise sunny now you can shift all of these variables outside as well so you're going to have final early temperature which is equal to this thing let's paste it over here then we are going to have our date time which needs further factoring but as of right now our list view Builder is complete what we are saying is build five items and this is what you need to build build Ali forecast items five times and it will only be visible as and when we scroll press command J and we are received by errors and a UI that doesn't look quite good let's restart and still the UI is still dismantled I don't know how it's looking like this and you're getting a lot of Errors over here now I'll simply tell you the reason you can go ahead and read the errors but I'll tell you a simple reason for this list view Builder has a tendency of taking the entire screen size like you know our text field also has the tendency of taking the entire width of the screen even less view Builder has a tendency to take the entire screen and here we cannot give it the entire screen obviously because we have this thing over here then we have our additional information down below so we have to restrict the height to restrict the height we press Ctrl shift R wrap it with the sized box and give it a height of 120. if we do that we are restricting the height to one particular thing you see and now we have our list which is scrollable and it only has a height of 120. but still I wanted to be like this like we had before in the horizontal Direction we have a nice property for that in list view Builder which is scroll Direction just like we had in a single child scroll view so we are going to pass in scroll Direction access dot horizontal save it and when you come over here we are met with an arrow and this error is solely there because we have set the list view Builder's height so this list view Builder entire thing its height is 120. and it is exceeding the current height which is why we are getting this error and it's only there because this thing this text is going down below that's not good so what we can do is restrict the text to only be there in one single line so if we go to our Ali forecast item widget scroll down we have our text of time the text has a property of Max lines if you'll see here we can tell how many lines a text can take maximum and it can only take maximum of one line and you see the error is resolved however it Clips things off and there is no notification about it like hey we clip this off there's absolutely nothing told about it so we need to change that so for that text and has another property which is Overflow so whenever it overflows it will just have a certain style attached to it so we have text overflow Dot and it has clip let's see what clip looks like the same thing as we had before dot Ellipsis so this will give us dot dot dot which tells hey this is extending then we have text overflow dot fade so it will just fade in telling you hey we are cutting it off and then we have finally visible which is just completely visible I like ellipses more because it just tells you that hey there's more to it but we have dots over here anyways now that we have our stuff good our Ali focus is showing our app is now working based on our weather API we are almost done only difference is the time that we want to show I told you we are not going to show DT we are going to show DT underscore text which is not what it says it's DT underscore txt not t EXT and we come away and we see 2023 all of that stuff now what I want to do is of the entire date given I only want to access this particular thing only the line so think how will you be able to do it one possible suggestion would be to go ahead and use substring and I totally agree you can go ahead and use substring because it is in the format of yyy hyphen mm hyphen DD so it is going to have a particular set of characters after which you can extract your time and that works fine for me and maybe you want to use that but I'm going to take another approach which is to add a package to our app for this and what is the package well if you go to pub.dev and type intl Intel thank you 'll see this package and this package is published by dot team themselves saying they provide internationalization and localization facilities including message translation and whatnot but if you scroll down they also help with number formatting they also help fit date formatting and passing which is exactly what we need we have a date in a particular format and we only want to display the time based on that so we can go ahead and add Intel to our pubspect.aml file now instead of going at the top copying Intel going to pubspect.aml file scrolling down and in the dependencies adding Intel like this there's another thing you can do nvs code press command shift p then you have the property of adding dot add dependency when you search for it you'll see this and here you can just pass in the package name Intel and it will automatically add it to perspect.aml for you run flood up object runs everything and you see Intel is automatically added for us so you can use this when you want to add packages in Bunch for example I want to add let's say Intel I want to add HTTP I want to add multiple things I can separate them by comma and add everything but since I've already added I'm going to press escape to escape that dialog sweet so now that I have access to date formatting let's go ahead and use it now you can refer to the documentation that was mentioned earlier but since I've used it before date format dot dot pass I don't need reference to it but obviously if you're using it for the first time highly recommend to read the documentation that is attached over here it will help you to use the package efficiently and properly so the first thing I want to do is take this and convert it to a date time object now you remember in our DOT code I had introduced you to date time dot now like this to demonstrate to you what final variables were right final time is equal to date time dot now well exactly we are going to convert it to date time the string so the string is going to get converted to date time which we can pass using Intel package so we're going to have date time dot pass and whenever you have anything date related I always recommend to use date time in Florida because it makes your job so much easier especially when using it with the Intel it will make a lot of stuff easier for example if you're building WhatsApp and you know on your home screen or in your chat screen also in the chat bubble you see the text of the date as mentioned or the time is mentioned how's that possible how can we do that in flutter well exactly you can do it over here so let's go ahead first of all and convert it to date time so we have date time dot pass and we need to pass in a string so we have early forecast DT underscore text and then we are going to use date format which is given to us by Intel package make sure it's imported right at the top intel.dot so we are going to update format Dot and we have multiple stuff over here every month abbr month day and all of that stuff but here even down we have functions for this this is basically describing how you want to format your date time object in my case what I want to do is display it in a format like 0 0 or 3 or 6 or 9 or 12 or 15 or 18 like that so for me I can just use wire so for me I can just use date format.hm and then if I go to hm it basically just has hm provided to it hm is basically R followed by minute which will give me in the format I want are minute right so we have date format.hm dot format and then I'll pass time to it and format requires the date time which is why I converted this string to a date time object all right now if I do this come back to the app I have 12 3 6 9 and 12 showing up now you can go ahead and try a bunch of variations here like HMS and you'll see our minutes second then you'll have J let's say and you can try a bunch of things J is basically 12a and 3 AM 6 AM 9 am 12 pm whatever you prefer you can use that and that will work for you or if you want your custom made you can just update format and you can mention your own pattern here so if I mention hm your it will again come back to me like this or if I mention J like this it will let me know like this so that's the point these functions were basically doing that behind the scenes when you add dot j it was basically calling J over here so it was calling date format at J what is this this refers to the class itself this date format so you were mentioning the pattern itself so you had date format J dot format and there we go now we can save it restart the app and I'm going to go ahead with 12 am 3 am I like this better and there we go so app is looking good now the last feature that I want is whenever I click on this refresh icon it should refresh and if there's any update it should let the user know because obviously this is real time only when we call it it's not like a stream that will continuously Give us new updates and new values when I click on refresh it will refresh the screen so how do I make sure this refresh happens Also let's remove the comment from here I hope you understand why we want to use less view Builder it is a better approach overall lazy loading and all of that stuff now if become aware in our icon button what if I just put such date if I put set State what will happen is when I refresh it will rebuild the entire scaffold so that means it will rebuild this entire future Builder as well it will call the get current weather function as well that means this entire build function is going to get rebuilt however if you check out the flutter official video on future Builder now what they've done and recommended to do is store this in a variable so you'll have final weather which is equal to get current weather or maybe something like this so you have laid future map string comma dynamic weather then you have NH state and once we add init State we are just going to set a late variable whether equal to get current weather all right now I can use this weather over here instead of weather all right and now you see the app loads now you might say hey why is this not lazy loading and that's because this is having the type of future we are not resolving the future we are not using a weighted await anywhere if you're not using a weight anywhere we are just saying hey call this function store the future inside of this variable and then we are calling this variable and when I restart it doesn't give me the error now when I restart or refresh this doesn't work anymore why because we are not calling the function anymore we're calling the variable and when we call the variable it is not rebuilding again you see so earlier we had a function and whenever the build build function would rebuild this function would get called and that is why such State worked earlier when such state was called entire build function was rebuilt so future Builder was also rebuilt so this future was called the function was called and when it was called this thing re-ran and thus we got new values which were then updated however here we have already called the function over here okay and the value is present inside of weather and we are just passing the weather variable here so when such state is called build function is rebuilt this weather variable is already there with the value assigned to it by the function that was called over here so the function is not getting called again because set State doesn't call in its state again it just calls the weather variable and whether variable has the type of future map string Dynamic and future Builder is just resolving that future giving us a snapshot so that we can use the data error loading and display it on the screen that's the job of future Builder but since there was no function function was not called it was a variable and variable already has a value assigned to it it has a value of future map string Dynamic assigned to it that's why it is not getting rebuilt the function is not getting called again and thus it is not restarting and flutter always says to use it like this but in our case we can call get current weather because we want it to work that way whenever the build function is called it should rebuild or what you can do is re-initialize weather to get current weather so if we search State whether is equal to get current weather that means we are re-initializing whether so if we restart we come over here it will again rebuild for the entire thing so as of now in a simple app there's no difference between this thing over here or just calling get current weather and not having this it's the same thing but in a bigger app when we get into inherited widget which is in our third app itself and when we talk about State Management you'll see this build function will get called even when such state is not called because that's the talk about State Management even such state is a kind of state of management now I hope your understanding what state management is you know what status and we just have to manage the state so such state is also a type of State Management but it is related to one single screen just like scaffold you know scaffold is there for one single page set state is there for one single stateful widget it cannot manage the state in two to three different screens such state will only rebuild one particular screen it won't go ahead and rebuild a totally unrelated screen if some data changes that's where things like inherited widget and we're going to study about riverpod comes in place this is just a local State Management solution and the State Management we are going to talk about is global State Management but we'll get to it I hope you understood that this is local state management but yeah we are going to dive deep into it because State Management is a very important concept but anyways you can use whatever I'm going to go ahead with the weather option because if you want to expand on the app's functionalities and I hope you'll do that after you gain the knowledge of State Management as well and incorporate State Management that we learn in the third app over here this will be more beneficial all right so now let's get to the main.dot file again and here we have seen our app in dark mode Let's go ahead and use theme data dot light if you use that let's see our app looks and this looks quite good I'm not disappointed with the results we have our card we have everything showing up nicely let's switch back to theme data or dog and this looks nice if I use remove use material 3 to true you see this looks quite bad in my opinion the layout looks good the coloring is not fine you know all the borders now have rectangular or pointy edges I don't like that and if we just have dot light light doesn't look that bad I am always fond of this color the blue color but still it's not as good as compared to material 3. all right so that was the difference I wanted to show you first Theory I want to talk about is the layout Theory we've already seen the Practical usage of this layout but since we've already got a practical experience I want to give you a theoretical experience with it and after that we are going to talk about widget Tree Elementary and render objects thing that I teased about when we were starting with flutter and we're going to talk about what exactly a widget is okay but before that let's talk about layout in theory the biggest quote in flutter in terms of layout is constraints go down sizes go up parent search position what does this mean let's go over it one by one the first sentence I said was constraints go down what does this mean it means that in flutter widgets receive constraints from their parent widgets constraints basically means boundaries so widgets receive their boundaries from their parent widgets these boundaries Define the limits within which a widget can render itself each widget passes these constraints or boundaries down to its child widgets we've already seen a practical experience of it with our list view Builder and a lot more things if we had our list view Builder it was taking the entire screen size what I said over here is wrap it with a size box give it a height of 120 so that means constraints go down the parent widget size box imposed a restriction a constraint a boundary on list view Builder to take only this much height or this much space unless you build it the same it gave its child widgets early forecast item that particular constraints to strain since it couldn't stay it gave us a render flow error in the bottom you remember when the time we had DT over here instead of DT underscore txt so lets you build a passed it down to its children or child so that is what constraints go down mean second thing is sizes go up this means when a widget receives constraints from its parent it calculates its own size based on those constraints the widget tries to expand to fill the available space while respect thing while respecting any limitations imposed by the constraints this process occurs recursively up the widget tree where each widget determines its size based on its children sizes and the constraints received from its parent this thing is basically what I have just explained to you early forecast item took as much height as much width as list view Builder and size box restricted on it since there was fire right term counts it took this much space since there was access dot horizontal it took this much space however when I put access dot vertical it takes the entire screen size and it implements a scrolling view like this all right so I hope you understood what I meant over here and the last thing here is parent sets position so after determining the sizes of his children the parent widget decides where to position each child Vision within its layout the parent widget is responsible for arranging its children according to its own layout rules and constraints this is what we did with the column right I said we could wrap everything with align widget we could wrap this text with a line this text with a line this text with the line this thing with a line and that would work but what I did instead is in the column set cross access alignment so that set the position for its children and his children were everything that you can see all of these things are children of column so parent widget was responsible for arranging the children according to their own layout rules and constraints so I hope you understood this this is a theoretical aspect of it the Practical I've already shown it to you and we've implemented it in UI now you don't have to necessarily remember it unless you're going for interviews and stuff but otherwise if you're just building for yourself practical experience should be enough so now we are done with the application completely and I've also talked about layout let's get into some more theoretical Concepts which are quite interesting in my opinion so let's dive into them now let's understand how flutter Works behind the scenes to display something on the UI or to display something on the screen so to understand this first we must know that flutter doesn't really translate any of the widgets into particular native uis all right so if you have a button flutter isn't going to say hey you're an iOS platform let's convert this to an iOS native button if you're an Android product isn't going to say hey you're on Android I'm going to convert it to Android native platform and then display it on the screen no flutter doesn't translate to native code what flutter does is paint something on the canvas using its own rendering backend or rendering system the rendering system it uses behind the scenes is this Kia Graphics engine which is currently being replaced by impeller that's why if you come over here when you run your app and press command J you'll see using the impeller rendering backend because on iOS the work for transitioning from this Kia Graphics engine to impeller Graphics engine is done on the Android it's still being working on and they'll cover it soon but for iOS it is done the shift was made from skiato impeller because skia had some issues with animation and 3D stuff with impeller things will be better but anyways flutter doesn't translate to Native UI that's why if you see over here I can have an Android E look on iOS right so this allows us to create customizable UI and we can have one UI in all our platforms irrespective of whether it is on Android iOS Mac OS web Windows wherever so now let's understand how stuff works so first of all we have our widget tree the first thing that we have is the widget tree and we already know what widget tree is right so let's get it here type in widget tree and we know what widget tree is we have already created our own widget tree here we have my app material app weather screen and in weather screen we have scaffold app bar icon button future Builder progress indicator if there has to be one a text widget if there has to be one and all of that stuff if you want to take a look at the overall widget tree you can click on this search kind of Icon over here and this dialog will only show when you're running your app so this Dev tools widget inspector page will only be there only when you run your app all right and now you see widget tree so this tells you your entire widget tree you can just push this down to see the entire thing so you have root my app material app where the screen scaffold everything displaying and if you open this up a little bit you have layout Explorer so you have to select one widget and you'll get a layout Explorer for that particular thing so this is how your entire UI looks like screen a scaffold which takes a width of 430 a height of 932 then you have future Builder which takes a width of 430 then it has a height of 8 something then you have padding which takes some constraints and that's what the layout Explorer is all about you can explore your layout how your layout stuff is done then you have widget details tree where you can see the properties that you've used for every single widget be it padding column whatever one cool thing you'll notice over here is something known as render object and that's what our second or the third tree is all about so we have one more tree here so let's paste it and let's call this render object tree all right so what is this render object tree we all know what widget tree is Right widget tree will represent the structure of our UI and it is composed of multiple widgets but what exactly is a widget we know it is the block displaying it on the screen but what is it well a widget is just a configuration it is a lightweight object with final properties why are the properties final because widget is immutable right and we've already seen that whatever is immutable its state cannot change its properties or data cannot change that means widget tree is a very lightweight object that has only final properties to understand why widgets are immutable we'll have to understand that widget tree doesn't really display anything on the screen it is just there for you to compose your UI to tell flutter how your UI should look like flutter will manage all the rendering stuff behind the scenes you'll just tell how you want your stuff and it will do that behind the scenes so widget doesn't actually render anything let's just Chuck the widget tree and just focus on widget so let's close the widget inspector and we are going to just focus on one widget and understand it for all the widgets and we are going to focus on the text widget so text extends the stateless widget right just like any other widget it either extends stateless or stateful widget so what exactly does text return over here the text returns something known as Rich text if you scroll down you'll find the build function you'll find default textile all of those stuff if conditions then you have widget result is equal to Rich text then you again have if conditions and then you return result so when there are no external properties like semantics label or registrar setup in your app what you return is a rich text so it is safe to assume that in normal conditions like us Rich Text is being written Now Rich Text is also a widget and I told you that widgets are just lightweight object properties and they don't render anything so why are we returning a rich text well if we press command and go to Rich Text source code you'll see which text doesn't really extend stateless or stateful widget what it does extend is multi-child render object widget and multi-child render object widget is a widget to prove that you'll have to go into the source code see that it extends render object widget go into the source code and finally you'll see it extends a widget all right so rich text is a widget but it doesn't extend stateless or stateful it extends multi-child render object widget and that is what our tree is all about render object tree now render objects are of three types or render object widget is of three types you can see it over here the first type if you scroll down is leaf render object widget this is used for widgets that don't have any child or children then we have single child render object widget this is there for widgets that only have one child like colored box an example of leaf render object widget is error widget it doesn't have a child at all it just displays itself an example of single child render object widget is colored box and then we have multi-child render object widget which is a column because it has multiple children right so that is what render object widget does the thing that actually displays stuff on the screen or renders stuff on the screen is render object what render object does is it determines the size position and visual representation of the widgets that we created or we have and they handle tasks such as layout calculation painting pixels on the screen so render object is the thing that actually displays stuff on the screen and does that by calling methods like create render object and update render object so if you just go to the render object widget it is an abstract class right it has create render object and it has update render object so this is how it creates and updates stuff on the screen so from what we have learned how stuff happens is widget tree is there every element of the widget tree is traversed or it is iterated through or it has gone through and then a particular render object widget for it is created so it is safe to say that widget tree will tell render object tree to create something right and that's partially true but what if we call stuff like such day now if I unnecessarily call such state in my app what will happen let's say here I'm not calling weather at all I just do such date I restart and when I click on refresh nothing really happens the widget tree is the same nothing additional gets printed on why is that the case that's the case because there is one more tree in the middle which handles all of these things which is the brain of whether render object tree should rebuild or not and that is the element tree so let's go ahead and create type an element tree so this Elementary is a reflection of widget tree and is responsible for managing the life cycle of widgets elements are created during the mount phase where they encapsulate the corresponding widgets and store mutable state so basically widget tree goes and creates a particular element for it and to understand this again let's dive in the source code let's go to text dot dot where our Rich text was and actually let's just exit both of them and I'm just going to go in the definition of stateless widget so let's go over there because it's easier to understand there you see you have stateless widget and then an override of stateless element create element stateless element so every widget that is there if you go to the widgets definition you'll find here a method which is create element so every widget that is there will create an element for itself stateless widget will go ahead and create stateless element stateful widget will go ahead and create stateful element so every widget will create an element for itself and this Elementary is does a reflection of the widget tree so here if you have a stateless widget you're going to have a stateless element now if I created my app over here I basically created my app element I'm going to prove it to you by the time this section of how flutter displaced UI Ends by the end of this chapter I'll be able to explain why I'm saying my app element is going to be created but for now take my word on it every widget will create an element which will be a reflection of itself right and they're only created when you first start the app during the mount phase so when you restart you know this is where elements are created and now Elementary is going to take care of whether render object needs to create stuff or it needs to update stuff so whenever you make changes to the widget tree flutter performs a process called reconciliation or diffing to identify the differences between the new and the old trees and this process is quite easy because widgets are immutable since magic widgets are immutable all of its properties are final and since the properties are final it's easier to compare the old widget tree and the new widget tree and this reconciliation process is done so that widget tree doesn't continuously just keep on creating render object widgets if it does that it will be a lot of performance waste you know so we need to boost the performance we need to make performant apps for that the flutter framework needs to be performed and this is how flutter framework is performed by performing a process of reconciliation or diffing so it identifies the differences between the new and the old trees and whatever differences are there only those things get updated or rebuilt for example let's say my text changes when I have my 288.77 Kelvin over here and I restart let's say this thing over here gets updated and let's say this text changes over here to 289.0 Kelvin so the render object is not going to build every other widget it's just going to build the text or the rich text again this way our entire UI is not being rebuilt or let's say our entire UI is not being repainted again and because of this we are getting performant apps to give you proof of this I'm just going to go to the stateless widget again here I have stateless element right I'm going to go in there we have component element and that finally extends the element so I have element over here and you'll see down in the element that we have a function called as update child and here it checks if new widget is null or and if the child is not null then it will deactivate the child and then it checks if the child is not null then it will perform some some task so basically this function update child function is the thing that will perform the reconciliation phase after reconciliation flutter will perform the layout phase where each render object will calculate the size and position of the associated widgets and then render object will paint everything on the screen so now I hope you understand why we need the elementary elementary is an intermediary between the widget and the render object trees that allows flutter to achieve efficient updates without recreating the entire UI it will just recreate one particular UI element or one particular object and and Elementary is the reason why we have features like hot reloading where you can modify the widget tree and see instant updates in the running app for example if I you know change this to theme data dot light save it instant update happens and everything is now theme data dot light and if I again change it everything is instantly theme data.doc this Elementary allows it because stuff to update is so less that you can instantly do it and you can do it in the running app now hot reloading is a big feature because you don't have to restart your app when you restart your app the entire thing rebuilds and because of that you might lose some very much needed existing data for example let's say you were filling a login form and then you press enter and some error occurs you fix that error and then when you restart all of your credentials are gone your email password everything that you had entered is gone now you have to refill those again this is this is why hot reloading is a much needed feature because it saves so much time so to summarize the widget tree defines the UI structure Elementary will manage the widget life cycle and mutable State and render object will handle the layout and painting the elementary will act as a bridge between the widget tree and the render object by performing the reconciliation process which will optimize the updates that need to be made now since we've understand what elements are we need to understand what build context is now if you come to the build context source code you'll see abstract class build context it has a widget it has owner it has mounted all of its properties but if you also go to stateless widget stateless element component element and finally to element you'll see abstract class element extends something but it implements build context so basically element is build context or build context is an element and it makes sense right because build context helps us to locate a widget in the widget tree and what is the limit element is acting as a intermediary between widget tree and Elementary and render objectory and every widget creates an element for itself so it exactly knows the state of the widget so it also knows where in the widget tree or wherein the elementary that particular widget is and build context also knows that so build context is actually an element both of them help us to locate a particular widget in the widget tree they will help us compare the state of the widget and see if it needs a rebuild and that's why many of the properties on build context is similar to what an element might have for example if you print context Dot mounted this is a property of element widget that's a property of element and if you type in element you won't see create element method on it because build context is an element you get all of these types and these help us to find particular things in the elementary now to prove to you that an element is created a way of what I'm going to do also to prove that build context is an element I'm going to print context dot runtime type so this will tell me the type of build context when I press command J You'll see the runtime type of build context is stateless element now if I take the same thing and go to weather screen let's scroll down and paste it over here we'll have a stateful element so build context is indeed an element and that's a very neat way to handle stuff because now they're giving you the element to access stuff and if you have any thoughts about what the build context runtime type it will be the particular element it is in so it can be stateful element stateless element so I hope you understood stuff what we have covered here is the three trees widget Tree Elementary and render object tree render object is the thing that looks after everything related to painting Elementary is a in mediary which will handle if the render object needs to be repaint stuff and widget tree is what we mention over here it's just a simple configuration it is a lightweight object with final properties and it is immutable because it's so easy and it's so cheap to create them and to throw them away because the element is the manager that will control everything and element can also handle and control the widget's location in the tree because even build context can do that we have we've already seen it it also handles the life cycle of the widget updating of the render objects and everything so Elementary is a big pillar in the flood of framework and we are given access to the element in the form of build context so we have understood what build context is programmatically and the three types of trees so this is the shopping app we are going to build with flutter we are going to have four products displayed over here with their title price and the image we also have a custom font for every thing then when we click on a particular product we get directed to a product details screen where we again see the title The Shoe image the price and the sizes to select from if we don't select a size we get a pop-up From Below saying that we need to select a size then once we select the size we can add to cart and the product will be added to our card successfully then we can go back come to a cart and we'll see that particular shoe in a card I can also add more products here let's say I add Jordans let's say I add 10 I'll add to card come back and I see Jordan shoes over here now I can also delete a product from a cart let's say I want to delete this men's Nike shoes I'll click on delete I get this confirmation dialog I can either click no or I can click on yes and that will remove the product from the card so this is the app we're going to build and we're going to learn a ton about theming navigation and State Management so let's dive right into it the first thing that's required is a flutter project so we are going to go to the desktop where I'm going to create my flutter project and run the command flutter create let's call it shop underscore app underscore flutter okay I already have shop underscore app created in the desktop which is why I've named the shop app flutter then I'm going to go to the shop app flutter open it in vs code and then obvious code open I'll close this for now I'll go to lib main Dot and we have our normal file okay I'm also going to run it on the iOS simulator so that we know that the project is working well and we can confirm it in the meantime I'm going to set up my screen over here so for our own reference I have taken a screenshot of the simulator and put it here side by side so that we can have the app and the UI side by side cool so we need to make this screen like this thing over here so let's clone it so first of all we'll have to remove the counter app but one thing I want you to note is this color scheme Line This is color scheme color scheme Dot from seed seed Color colors.d Purple okay and also remember the screen because I'm going to reference this later on when we add theming to our own application now let's get done with it let's remove it then I'm going to create the stateless widget call it my app then I'm going to return a material app where the title is going to be shopping app and the whom is going to be a different widget so I'll have to create a different widget I'll go to the lib folder create home underscore page dot dot this is all the boilerplate stuff I hope you are understanding it so I'll have to import material.dot again then we'll have a stateless widget which will be called home page and we want to return a scaffold so that an empty screen appears that's it I only want to see an empty screen as of now we'll take it step by step so we have home page returned over here that is nice and now if I come over here our counter app is now replaced by a blank home page so we have the boilerplate stuff ready now the next thing I want to do is just start designing the app but when we start designing the app you'll realize that this font is a bit different and the font we generally use in Android iOS it's different from what is present over here why let's just take an example of the weather app we created you see this weather app the font wire is quite different from the font mentioned over here so what we need to do is add our own custom fonts to the app so there are two ways to do it first way is to use a package called Google underscore fonts this is provided by material.io which is the Google team themselves and we have it working on all the platforms Android iOS Linux Mac OS web windows so what this does is basically a package to use fonts from fonts.google.com and phones.google.com is like a registry of all the fonts that you can use freely in your apps you see it has a ton of fonts you can use and you can use whatever one you want but the one I am interested in using is lato so this is the style I'll be using and this is a style which is used over here as well now you can explore and find your own font but I'm going to go ahead with later now you can use this font to easily add later to your app all you need to do is mention a text widget then you have this text you'll mention the style then you'll use Google fonts which is provided by this Google fonts package that we'll add to our app dot later so when you call this later method on Google fonts you'll be able to add the later font to your app and your app will start looking different that's all that you need to do so this package has its own pros and cons the pro over here is it can be used in production to reduce the app size because you don't have to install the font to your app you don't have to install it on your system either all you need to do is just use this and Google fonts package will go fetch the font using HTTP at runtime and you'll be able to see it in the app you see even in the dependencies you have the HTTP package the one that we've already used right the con is that it uses HTTP fetching HTTP fetching as you all know can take a little bit of time and that delay can be seen when you use Google fonts in your app it is a visible difference but not too much so it depends on you if you want to use this package or not I'm not going to use it I'm going to follow the alternative method which is registering the font in pubspect.aml file so as we know we can register the Assets in pubspect.aml file but we are not going to register assets fonts is different from this thing over here when we scroll down you'll see a particular section is dedicated to the fonts tab we need to use that so you can add custom fonts to your app just using this part and you can add your images audio video all of that from here we're going to get to assets as well but for now let's focus on fonts so I'm just going to uncomment all of this all of this and make sure indentation is right that means the spacing over here is right because it matters in yaml files then here we have several things to mention first of all we have to mention the asset and its location well we don't have any assets but you can go ahead and install it from fonts.google.com you can see your style whichever one you prefer you can select that style it will add it and once you've selected all the Styles you want just click on download all and it will download it for you in your system I already have a few downloaded for me so I'll just open them I have later bold and later light which is what I'm going to use if you want to use the same font style I'll mention the link for it in the description below so now to register it I'm not going to put these font files in lib folder lip folder strictly for my DOT code it isn't going to have any assets or anything my assets is going to be present in a separate folder of its own in the root folder so I'm going to create my own folder called assets fonts here I'm creating two folders because I don't want to mention ad sets just like this in the root folder it's quite messy but I'll create my assets folder then the fonts folder because I'm going to have two types of assets images and fonts the dummy data that there is this image this is coming from our assets itself which are registered in pubspect.aml so we have to register images as well that's why I've created the fonts folder now I can just copy them also we can open fonts and finder and paste it over here as soon as we paste it in the correct folder you will be able to see later bold and later light correctly sweet now we'll just have assets slash fonts later light Dot ttf and then we are going to have assets fonts later bold.ttf you need to make sure that this path matches you are in the root folder so you'll go to assets this folder then fonts and then you'll Target one particular file and make sure you do that correctly it should match word by word letter by letter also the style here is not going to be italic it is going to be 700 with a weight you can mention this style it can be italic or anything else but I want to want to mention the weight aware because this little bold font should only get activated when my weight is 700 and weight 700 means it is bolded and also you need to mention your custom font family name aware so you can go ahead and pass in later later whatever you want to call it I'm going to call this later and make sure control s is pressed so Florida Pub get is run and then your contents of the app is there with you perfect now we'll go to home page and just to see if the fonts are loaded properly or not you can go to body text it and let's say you type in hello world save it and we have hello world over but it's in the corner so we are going to center it so I'll press Ctrl shift R the refactoring options and I'm going to wrap it with the center widget Also let's put comma for formatting and when we come where hello world is seen but there's no difference in the font why because if you again go to pubspect.aml file you'll see that there are fonts family and there are multiple types of fonts you can describe over here you can have more than one font family described over here so if there are multiple font Families how will flutter know which font family to use and that is why it asks you for the family name over here the family name for this font so to make sure you're using the right font family you need to mention it in the text so you're going to have Style textile and textile has a property of font family and it accepts a string so you need to mention the font family you mentioned in the pubspect.aml file which is later over here then save it restart your app and you'll see a different font is used now if it still doesn't work for you then again you have to check font family if it's the correct thing if the asset is correctly mentioned check your terminal debug console if there is any error or you might want to terminate the app and restart it again and you'll be able to see the difference so anyways I have font family now if I have font weight as font weight dot bowl I should be seeing the bolded textile right and we certainly do now you might say hey why have we mentioned two font assets over here why have you mentioned light and bold both of them you can't remove bold right if you just mentioned later you'll be able to use a custom font and when you use Font weight dot bold it will bold it like this for you well let's try it I'm going to remove later bold restart the app and you see a visible difference the textile and all of that is the same but still the style over here for this font changed that's because font lato bold is different from later light which is bolded in this case what was happening was later light was bolded so it was less bold however here we are using later bold which has a distinctive property of its own and thus we are using two fonts for one font family and since we've mentioned weight 700 it is able to identify when to use that kind of font okay sweet now let's go ahead and design the app when we see a wire we have multiple text we have text over here used we have text over here even here and it's scattered all over the app does that mean I'll have to use this style textile font family later every time I need to user text and use a custom textile or a custom font family no that can be quite cumbersome just imagine you have to do it over your your every single place and if your app gets bigger and bigger it will be very difficult to manage it that's why font family is generally not used for a particular text you can Define it overall in your my app in the material app by using the theme property so team will set up the overall typography in your app and that will work fine so you mentioned theme data and it has a property of font family which you can use it requires a string so mention later where and now without doing anything without mentioning any textile it still uses later it's not bolded because I removed the textile font weight dot bowl however if you bold it it will still work fine cool so now we have set the overall typography in the app now let's go ahead and set up the overall coloring in our app now remember in the counter app I told you to remember one line which was the color scheme line well that's what we want to mention what I want to do is set up the overall color for my app and I only have one main color decided which is this yellow color what I want is the rest of my colors the rest of the things used in my app should be derivative of that so I want to mention just one color and based on that one color the entire color scheme is going to be generated so we can use that so let's go ahead and pass in a color scheme and as soon as we do that there are multiple arguments we need to pass in and they are quite a lot you need to pass brightness primary on primary secondary on secondary error on error background on background surface on Surface if you don't mention that you'll face errors so definitely this is quite a cumbersome task and many people wouldn't want that they want to develop a symbol app where the key focus is building functional app not generating an entire UI so for that we have dot dark which will help you generate a dark theme then you have color scheme dot light which will help you to generate light theme but you also have color scheme Dot from seed so with this you just have to mention one thing the seed color based on the seed color the entire coloring of your app will be set up and it will work fine for you now think of terms of a tree for a tree to grow you need to pass in a seed right this is what it requires you pass in a seed and the tree grows accordingly if you pass in a watermelon seed a watermelon thing will be grown if you have a pomegranate pomegranate will be grown and so on same way we need to mention a seed color which will be the base from which all other colors will be derived all colors will be based on so Mike Seed color is going to be the yellow color which I've mentioned over here and I know the RGB o for it so we are from RGB o and then I'll mention 254 206 1 1. so this is the RGB for it and opacity is full all right now we have it over here no visible differences but we've set the overall theme of our app from from seed method we are able to generate the primary secondary surface colors you'll see over here using the seed color as a starting point a set of tonal palettes are constructed these tonal palettes are based on the material three color system and provide all the needed colors for a color scheme these colors are designed to work well together and meet contrast requirements for accessibility and if you want to know more about it you can click over here open it and read about it in the material 3 design documentation okay so now that we have set this up and I think everything is ready let's go to the home page and design our app so the first thing is we need a header now this header is a bit different all the adders we have seen in the past require something like this it should be this long and it should be present over here shoes collection and then you have a search box now this is quite big for an app bar so it's definitely not an app bar that we are going to use we have to custom create it whenever you have a header sort of thing it doesn't necessarily mean you have to use an ABBA it will be fine if you don't use an ABBA but it should match whatever design you have in mind and make it pixel to pixel so let's go ahead here in the body I'm going to pass in a column and in the column I'm going to mention children and my first child is going to be a text which will say shoes collection so shoes will be on one line and collection on another so let's go ahead and have text shoes collection save it let's put com up properly so that we have the right formatting and we have our shoes collection showing up at the top now what I want to do is put shoe collections bigger bolded and it should be right below the notch just like we have it over here The Notches over here so it's this font is mentioned over here so I want it below the notch first of all we are going to go ahead and improve the style so we have textile then we have font weight as fontway dot bold and font size is let's say 35 let's save it and we are going to have shoes collection over here nice now the problem is it's quite at the top I don't want it at the top I want everything starting below the notch so for this we have a nice widget that we haven't used till now and that is the safe area widget so we are going to wrap it so we are going to have Ctrl shift R the refactoring options and we're going to wrap it with a widget which is known as safe area what safe area widget does is it ignores the top notch it avoids the bottom Notch as well or the bottom bar over here you can see this line it avoids that as well so safe area as the name suggests is a safe area where notches are not there and even these bottom things are not there now if you see if this shoes collection automatically comes down and it looks good the next thing I want to do is put collection right below so I'm going to have shoes slash n collection I've put backslash n because as we know backslash n is used to go to a new line we have seen this in the dot course we'll save it and we have shoes collection over here perfect the next thing I want is in the same line of shoes collection I want to put a search field so for this we know what widget to use text field but what we want is both of them to be in the same line if I mention it below this let's say I call text field over here and let's say I do this I have my text field over here perfect right but the problem here is this is present right below it I want it side by side so to make it side by side I'll have to wrap text and text field in one particular widget which is a row so we are going to have row children and then we are going to have text and text field put it inside save it and now we have it but the text field isn't showing up why is that the case well that's the case because if you press command J and let's say you restart your app you have a bunch of Errors showing up and if you want you can go ahead and read this error to understand what really is happening but if you don't understand it don't worry basically I've told it to you before that text field occupies maximum width it can get it takes in as much width as a device has so here in a row it is not getting as much width as the device has because the text is present over here so it's overlapping and thinking hey why am I not getting the maximum width or you can say the device width that's why we need to constrain the text field so that it only takes as much space as it's told it doesn't go ahead and take the entire device with that's not allowed again if you didn't understand just to explain it to you the text field has a tendency of taking as much width as possible on the device that is why when we are mentioned text field in a column below it took the entire device with but here when we put it inside of a row it doesn't get the entire device with it only gets this much width which is not acceptable by it because this text is taking some space so we need to tell it that hey you need to be fine with this much space you're getting so for that we'll have to wrap text field with a widget and that is the sized box widget here we are going to mention the width let's say 50 maybe that is enough and then we can save it so we have text field showing up which is quite small 50 is quite a small width so maybe we want 250. and this is still not enough maybe 270 and you see we get an error a render flow error overflowed by one pixel so maybe we want 269 but I'm going to go ahead with 260. so here's the problem now if I mention 260 here it will be different on a pixel emulator so let's get a pixel emulator up and running and see how it looks on the pixel emulator as well and then we'll be able to decide if it works fine on all device sizes or not if it works fine on all devices then we are good with 260 otherwise they need to be made some changes so pixel emulator is now up and running and as you can see we are getting a render flow error on the pixel screen so that goes to say that the pixel size that we have mentioned over here doesn't work for this case so let's just remove the size box and think of some other solution whatever width we mention is not going to be the same for both Android and iOS or for different screen sizes in general so let's just generalize this problem what do we want we want this text field to take as much space as possible after this shoes collection has taken its peace so what we can do first of all is take this text put it in a padding widget so there's padding all around it and after that we can tell search or text field to take as much space space as available so what I'm going to do is press Ctrl shift R get the refactoring options wrap it with padding so we have constant agencies.all but it is not enough I want it to shift quite a bit so maybe I can shift it to 20 and this looks better after that in the text field I'm going to use another widget which is called as expanded what expanded does and it is generally used in either a row or a column is it just tells hey take as much space as much width as possible it doesn't say hey take the entire device with it says just take as much space and width as possible in this row or in this column wherever you're defining it and now on both this devices it takes the same space there's the padding of the text widget and after that it has its own text field right so it works on all screen sizes so that's the cool thing about using expanded you don't have to use pixels or you don't have to mention any height width Etc you can just use expand it to tell hey just take as much space as available in a row or a column cool now that we have this let's go ahead and Define or Design This search field and I'm going to keep the pixel emulator on the side as long as it's not bothering me now let's go ahead and create the search so what do we want well first of all I want this text to appear and it should just be a hint a label wouldn't look good right if you have search written over here and when you click on it the search will go on the top we won't we don't want that kind of label we do want hint text so we'll go to the text field we already know we'll pass in our decoration input decoration and the hint text is going to be what search and if we do that much and let's come over here save it we have search written over here that's nice now I want to bold this text because the text is not bold and maybe I want to reduce its height as well so for that I can do it over here in the input decoration itself but the problem here is whenever I want to create a text field I want this kind of design I don't want anything else I want this text to be bolded I want my stuff as it is for every single text field I create so that's why what I'm going to do is go to the main dot dot and in the theme I'm going to define the input decoration so every time I create a text field or I use input decoration I want a similar kind of theme so I'm going to have input decoration theme and this doesn't ask for just input decoration it asks for input decoration theme so let's go ahead and pass it in and let's mention the thing that we want an input decoration theme I want the hint style to be given a proper style so we are going to have textile and here the font weight first of all is going to be there so we are going to have font weight dot bold and then we are going to have font size which is 16. so this is now bolded and looks better in my opinion let's put it over here also let's put a const here and for the home page as well we'll put a cons that's nice the next thing we want is an icon so obviously we know what to use prefix icon because we want it in the front if you ordinated it in the back we would use suffix icon but let's go ahead with prefix icon and here we can mention our icon we already know how to use the icons class so we have icon icons Dot search and just to clarify icons dot search is icon data and this is a widget you cannot just use icons dot search aware because icons doesn't extend the widget class so we need to wrap it with icon which takes in an icon data and icons is an icon data all right let's save it come away and we have this now what I want is the color to be same so again for all my text Fields I want the icon color to remain the same so I'll come in the input decoration theme and have prefix icon color color dot from rgbo and here I'm going to mention a color which we have found out one one nine one one nine one one nine one so this color is kind of grayish and you won't see big differences but it there is a difference so for every text field I create this is going to be the theme data I can obviously override it for example if I just override the color over here let's go ahead and type in a colors.red the color is now red so you can override it but if you don't pass anything it will take the default theme from here and this will only match particular things for example input decoration hint text style can be passed over here and it will follow that if you pass in a label style only label will follow this particular property not hen Style so if you pass anything over here for example a color or anything it will follow that and if you don't pass anything the default will be what you mentioned in the theme in the theme data now the next thing is to put borders over here and to put a border it can be a bit different for every text field we create for example in the home screen I want I don't want a text field like this because here the text field is like this it goes straight then there's a curve on the left and then it again goes straight so I don't want this kind of text field border for every text field we create that's why I'm not going to mention it in the theme data I'm going to mention it right over here so yeah I'm gonna go ahead and add border in the decoration I need to add sorry border and that will include border like this but this is an abstract class you already know so we can use outline input border or you can use an underline border I want an outline input border because I want a clear background or clear border like this then I'm going to have Border Side where Border Side is Border Side like this the color will be there and color will be color dot from rgbo 225 225 225 and one this is another color I found out from the figma design so we can paste it away and don't worry about the warnings as of now if we just put one constant over here the errors are gone but we can't be sure about it yet because text field requires a controller and controller cannot be a constant so I'm not putting it as of now so there we go we have our Border Side ready as well now if we come over here we are able to see stuff now what I want is the Border radius to be present so let's go ahead and pass the Border radius so we are going to have bought a radius border radius Dot horizontal you can also use water radius dot circular but that will be for everywhere I only want it from the left that's why I'm going to use border radius Dot horizontal of course you can also use only but then you'll have to set top left and bottom left both because you want a curve from your and a curve from here but I know I want it from the horizontal totally so I can just mention left here and let's say I pass in a radius dot circular of 50. cool now we can save it we come over here and we have our border radius looking good only from the left hand side not from the right hand side if we add right as well let's try it out we have something looking like this and this might be good for other text fields that we create not for this so we are going to have a simple left like this nice this looks nice now the problem is the color isn't exactly what I mentioned so I've mentioned the Border over here but this color is quite different from what is over here it is taking the default color so what I'm going to do is push this border out and I'm going to have final border which is equal to border just like we did in the currency converter app as well remember and we're going to put a constant here because this is a constant then we can pass border over here then we can have enabled border pass the Border same way and now you see the design changes enable border is this border and focus border is the border that we see right now so Focus border has a predefined color and it has a predefined color because of this seed color when we passed in color scheme Dot from seed it generated a design theme of its own using which it is giving us this color it thinks this is a nice color with seed color as yellow so let's just remove it and see you see as soon as I remove seed color it's now blue the default theme that's why I've mentioned seed color over so that it can generate on its own but I still don't like this border color over here so what I can do is pass in focused border and pass the border to it as well so when it's in focus we get the same overall theme let's restart and that restarts it only for iOS not for Android so let's go ahead and restart it for Android as well now we have restarted and everything looks great so this is nice we are creating uis that will fit everywhere that's nice the next thing I need is is this chip or you can say these filters so there are two options we can take here first one is creating a list of filters then using list view Builder that we have already seen on the weather screen and displaying it over here that sounds nice right so let's do it we'll go to our code and for now let's just wrap everything in a const after we start building stuff the text field might need a controller so we can put it then so what I'm going to do is Define a list so I'm going to have final list of string filters of companies and then I'm going to have a list but as soon as I create this I can't Define a constant Constructor because the field filters is initialized as a non-constant value so I can put Constable here and that fixes everything because list like this is a constant but I have what I want is the company names to be present in the filters so first of all I'll mention it I'll have all then I can have added us then I can have Nike and then I can have Bata cool now have all of those filters now I can use a list view Builder to display them on the screen so let's have a list view Builder this will take in a context and an index then we can have an item count and as you can see as soon as we put a list view Builder we get errors all over the place and that's because listview Builder is not a constant so let's go ahead remove it and add constant for every single widget that looks nice now in item count what is our item count well whatever or how many filters are present over here my filters here are filters dot length and this crosses my mind that yeah you could use a row here to display these widgets but again if you have more categories or more filters in the future for your application not just four things maybe you have a fifth brand Puma or something as well you want to add it you can do that by just mentioning the value over here and everything else will take care of itself you only have to update the value over here you don't have to go like hey since I added one value I'll have to add one more widget no filters.length will take care of it because you are specifying the value as let's say this is 4 so it will build four times if you add a Fifth Element it will build five times and it will build according to the data we pass and the data I want to pass in over here is these name of the companies only so let's go ahead now how do I create this kind of UI right this looks quite interesting so to create this kind of UI there is a widget you can obviously go ahead and use the container to create this kind of layout and that's totally possible but flutter makes our life easier by providing us widget for it and that is the chip widget when you return a chip you just have to provide one label and it will create a chip out of it chip is this thing only of course you can create a container and make it do your work but there's a widget for it and there are so many widgets that I won't be able to cover all of them in this course so you need to constantly look up for yourself if you have a doubt you can ask it on Google or on our Discord server and you'll be getting help for it but if there is no specific widget for it you can create your own combination of widget and get it working anyways coming back to the label what is our label well it's these texts only so I want filters at index whatever we're building for so we are going to have final filter is equal to filters at index then I'm going to have the label which requires a widget so I'm going to pass in a text which will be a filter save it we come over here and we see nothing why let's open the diva console and we again have an error and this error is quite similar to what we had before when we laid out a text feed the problem is the same list view Builder wants to take the entire height of the screen and you're not giving it that now if I remove this thing also I think I've made a mistake here I should not be passing in a row I should be passing it out of the column now this is a mistake you need to understand this I had passed in a row okay so it consisted of these two things it consisted of these two things in a row now what I want is an element over here so I need to pass it in a column which I've already created right I have a column over here so I need to mention my chip or my list view Builder out of this widget of row okay so I can come down over here I've put the list view Builder but the problem Still Remains the Same it wants the entire height of the screen and it's not getting the entire height of the screen so now we want to restrict the height so for this we have already seen we can use size box now if I use expanded over here and save it yeah I do see stuff but what's happening is it's taking the entire width of the screen I don't want it to take the entire height of the screen in any case I only wanted to take as much height as I tell it to take so what I'm going to do is wrap it with the sized box instead and then I'm going to mention a height of let's say 120 then save it and I have this now you see I have a scrollable list of filters now I'm going to go here and pass in a scroll Direction which will be access dot horizontal so everything is horizontal now but we need a padding like a margin sort of thing that we have here between every chip so let's add that we are going to wrap chip with a padding widget and if I do constant Edge and such dot all it will be from all the sites I only want it from the horizontal side I don't want it from the vertical side right so I'm going to have dot symmetric I can use dot only left 8 and write it but does the same as doing Dot symmetric horizontal 8. I hope you're getting it we've already discussed about this but I'm still clarifying in case you didn't understand it then and here we have our widgets showing up perfect now I only want to increase their height now to increase their height what should I do does Chip have a height property let's see it doesn't have anything height or size related so what I need to use is a padding to increase the height of the chip I'm just going to increase the padding around it so it increases the padding and this will become bigger so to I've already passed in a padding over here right and it looked at the outside it didn't look at the inside of the chip widget and that's why chip also has a padding property of its own you can pass that in so you have padding Edge and sets Dot then you can pass in all or symmetric whatever you want if I pass an edge and such dot all 15. this looks good not bad but the problem I have with it is it's not looking as good as I want it to look so what I'm going to do is I'm going to increase its padding from the horizontal side and make it different for the vertical side so that will give me a better feel of it so what I'm going to do is Edge in such dot symmetric then I'm going to have horizontal as 20 and vertical as 15. save it also put Constable here and there we go this looks much better and is as similar as this right but yeah the text is quite small so let's make the label style bigger you have label here so we can either pass in a style over here or a label style for it so we have label style and then we can have textile font size 16. then also put a const around it save it and we come over here and this looks better it is scrollable over here it might be extending this part and that is why we are not getting an error if we wrapped it with a row we would get an error and then we would have to wrap it with a single child scroll view what we've seen in the weather app before but anyways coming back to this this looks nice the last problem or the second last problem is the color so let's change the color and for every chip that I create I want a particular color to be present so I can change the chip color from here I'll pass in the background color and the background color can be constant color dot from rgbo and then you mentioned the rgbo which will be 245 247 249 and 1. then we save it you come over here and we see the similar coloring now obviously this looks a bit different from this one but if you take a screenshot save it over here and get it side by side both of them will look similar just to make this look more prominent what I'm going to do is add a border as well so here chip also allows us to pass in something known as a side and we already know what Border Side does it will help us to create a border of a particular color so I can pass in a border side which will have a color of the same thing as this one so I'm going to have constant color as this also let's put a constier save it become aware and this does look more prominent okay and the last thing I want to do here is make the Border radius more curved so I want this to be more curved just like this one so I can decrease the Border radius so for that we also have another property which is the shape that will allow us to do that so we have rounded rectangular border where you can mention border radius and that will be border radius dot circular 30. it's all tried and tested values all right when I was building the app for the first time I tried values like 10 15 20 30 and whichever one I liked I kept it and I like 30 so here it is and this looks exactly like this one all right now the next thing I want to do is the selection of this chip so whenever I select a particular chip I want that particular chip to have a yellowish color so for this my plan is very simple I obviously need to know what filter is selected so that I can filter accordingly so I need to know that yeah all is selected so I want to show all the products I want to know added also selected so that I can filter all the Adidas products and so on so I definitely need to know that what filter was selected so I need to store the name of this filter so I'll be using a string to store my state after that you know whatever is clicked on I can just use gesture detector to know which one was tap and then save it in my state so for that I'll have to convert this from a stateless to a stateful widget let's do that then I'm going to create another variable which is string selected filter and that will be equal to filters at zero but when I try to do this it says the instance member filters can't be accessed in an initializer it basically means that hey you've created the list of filters over here and now you're saying you want to use filters at zero you can't use an initialized value again in to initialize something else so what you can do instead is use late string selected filter and then use NH State because this is the first thing that calls before the build function and then we can set selected filter equal to filters at zero and that will work fine okay all right now what I'm going to do is take selected filter and whenever I tap on the chip so let's see if tab has Chip Hazard on top property and it doesn't so we'll have to wrap the chip with a gesture detector widget now here's the question should I wrap the gesture detector property with chip or should I wrap padding with gesture detector meaning gesture detector should be used like this like wrap with Widget gesture detector should be used like this let's see if I use on tap and let's say I just print hi if I do this press command J let's restart the entire app and we'll do the same for iPhone as well we'll come away and let's say we select added as high gets printed that's correct but if I print outside of Adidas let's say over here it still prints why because you've wrapped it around a padding widget what padding does is it's saying that this particular thing this part is One widget this part is One widget it is not just including this particular widget it is also including stuff on the side because that's what padding does padding creates a spacing an empty spacing from the left and the right hand side so that's what padding is doing and in closing it with a gesture detector you're saying that whenever I click over here I want a particular filter to be selected and that's not how my app is going to work my app is going to work only when the chip is clicked on so I'm going to remove the gesture detector from your I'll press command Z then I'll wrap the chip widget with a gesture detector and then I'm going to have on tap print let's say hi then I come over here I click on added as it prints but when I click outside of added auth it is not printing cool so it was a very minor thing but it definitely helps to improve the logic yo so coming back to what I wanted to do selected filter should be equal to the filter we have over here right so you have selected filter which is equal to filter save it and yeah we've just made sure selected filter is changed now I want the background color to change according to what the selected filter is so if selected filter is equal to filter so if selected filter what we have selected is equal to the filter that we are on so if added off is there and it's clicked on the selected filter and the filter is the same thing so I want the yellow color to be there so if selected filter is equal to filter then I want the yellow color and whenever you find yourself repeating many colors what you can do is set up the theme for it now I want to access the seed color so what I can do is theme dot of context Dot color scheme dot seed color but there's nothing like seed color given by color scheme then what should I use that's the point of seed color scheme Dot from seed is basically like hey give me a seed and I'll build everything based on it there's no seed color in color scheme class in this class of color scheme there's nothing like seed color so we cannot use it what can we use well we can try to use primary right and when we come aware the primary is quite different from what I wanted my primary to be my primary was supposed to be yellow but it's not yellow because we have built from seed so when we've built from seed HRS it has predefined some colors that will look good and it thinks this is a good color for a chip and I disagree I wanted something else so what I can do here is override the existing color so I'll just say the primary color should also be this and when I do this and let's say I restart my app you see yellow color is there and it looks good I'll restart it on Pixel emulator as well and you see it looks nice so again to explain what happened over here we generated from seed seed color is just there so that it can build stuff for you it can build colors for you and automatically assign them so it created the primary color also for you but I didn't like the primary color generated so what I did was replaced it with my own primary color and here is my primary color rest of the things like secondary color or surface color all of that can be defined by this color scheme only I only want the primary color here to change and then to access it what I've done is theme.off context dot color scheme dot primary to understand how this works behind the scenes I'm going to demonstrate or create a diagram for you and once we understand theme dot off context dot color scheme dot primary like how is this actually fetching this primary color we'll understand the basics of State Management the basic principles of State Management in flutter so this is how it works let's say you have a root widget and the root of your widget is this all right and here I'm going to have root written so this is the root of our widget and let's put the root widget here this looks good and the root widget is followed by our widget tree so we have one widget over here and let's say there are multiple other widgets and then every widget has its own sub widgets as well like column it has multiple children so you can have those as well let's say this is our entire widget tree a very simple demonstration all right and let's say this is our material app so after root we directly have our material app in the material app we have set up the theme and all of that stuff so we have all the stuff related to theming all right now material lab behind the scenes configures all of the theme related stuff and sets it up globally for your entire app so it does that behind the scenes so it has all the theme related data over here so let's call this theme data now in some descending widget let's say in this widget what I've done is called our theme dot off context right this is the main part theme dot off context by calling theme dot off context you're triggering something known as inherited widget so if we just come over here to the home page go to theme we see a stateless widget but when we go to theme dot off context we have inherited theme and if we go to inherited theme it extends a narrated theme and inherited theme extends inherited widget so we are using something known as the narrated widget which we've talked about a lot whenever we talked about widgets so there are three types of widgets stateless stateful and inherited but we never got the opportunity to say that where do we use an edited wizard this is where you use a narrated widget inherited widget is used for State Management by the flood of framework whenever it wants to talk to the parent widget as of now we've seen that whenever we want some data to be passed to the child how we do that is by Constructor so if material wants to give something to our home page it will pass it through the Constructor if home page wants to give something to some other widget it will pass it through the Constructor again if it wants to pass something to the Constructor it can do that but how will we do it in reverse for that State Management is there and another problem here is what if my material app doesn't want to keep passing everything to the build function or through the Constructor right every time it has to go through the Constructor that is quite cumbersome when you have a large widget set right now we only have four so it doesn't matter for you but later on when we have bigger widget tree you'll say hey this is such a bigger budget tree do I have to pass it through the Constructor every single time and this is where inherited widget will help you inherited widget will just say hey you want me to pass some data down to the widget tree you can pass it to any widget like this so it will just skip it it will skip all the Constructor part and it will directly have the data given to it so this is what team dot off context does it will just tell the parent widget whenever it sees the theme widget it is just going to go there and grab the data from it to repeat what I said how theme dot off context works is it goes up the widget tree and starts finding the nearest theme widget as soon as it finds a nearest theme widget it will grab the properties of it and use whatever is necessary so if team data was mentioned over here let's say theme data was also present over here and theme data was also present over here both the places so theme dot off context is directly going to go to this theme data it won't go to this theme data it won't go because it will find the nearest theme data widget for it that is how theme dot off context works so basically what theme dot off context does is find its nearest widget its nearest ancestor widget of the same type since this is team it will also find theme later on we'll see stuff life now like Navigator dot off context even then what it does is find the nearest Navigator widget and use that to display its routes or you know do its navigation stuff but we'll get to it but this is how team.off context works and this is how inherited widgets work we are not going to write code in inherited widget if you want to do that I'll mention a resource below which is created by the flutter team themselves and that will provide you with a clear description however what I'm going to do is just explain how theme data works so if you've understood you can skip it and if you've not understood I'm going to explain it again how this works is whenever you call theme dot off context this off context goes ahead and Finds Its nearest ancestor widget so it will go and search for any theme widget that is nearest to it and once it finds it we get theme data it will use the properties mentioned over there suppose if theme data is not mentioned over here it will go to the root widget to find the theme data and even if it's not mentioned in the theme data root it will still have it because material lab behind the scenes does create a theme data if you want to mention it and change it you can change it but if you don't mention and change it then it will use the default theme the blue color theme or the pink color theme it has already created all right so I hope you understood this explanation this is what it does this is inherited widget and this is how State management in general works with flutter we are going to take a look at a similar thing in Navigator as well I'm going to explain it then so if you didn't understand it now an opportunity will be later on however I would still recommend you to understand it right now so coming back to this we have selected filter is equal to filter and when we have this it will have a color scheme dot primary so it goes and finds its nearest theme data widget it found it and then it will access its color scheme primary which perfect now if I try to change it it doesn't change why well that's because the selected filter is equal to filter but you've not called set state when we have not called such State however widget rebuild that's why we need to wrap it with a set state so that the build function rebuilds and then we can properly select a particular widget perfect now that we have this done as well let's just get rid of the warnings by protecting a const over here now the next thing after the list view Builder and the size box in the column is displaying these cards our data so let's save it let's close all the save files I'm going to go in the lib folder and create a new variable or a new file called Global variables.dot and this contains my Global variables and file and my Global variable is the dummy data that I want so my dummy data is going to be a list of maps string comma Dynamic so it is going to contain a list of products and my products are going to be mentioned in the form of a map so we are going to have a final list of map string comma Dynamic why dynamic because we also have a price to mention let me give you an example let's have a final products which is equal to a list and this list is going to have a map first of all there's going to be a title of the product so let's say the title is men and then I want apostrophe s but if I do that it will give me an error so I'll put a backslash so it will ignore this single inverted comma and act as if this is a normal single inverted comma all right then yeah men's Nike shoes we save it now you won't be able to see anything on the screen obviously we have not displayed anything the next thing we need is a price so we'll go ahead and set the price let's say 44.52 now all to all the shoes Enthusiast if the value is incorrect forgive me for it then you're going to have sizes this is a list of sizes from which the user can select and this is shown on the product details screen so we have 8 comma 5 9 comma 10 comma 11. so I hope you are understanding why this is a list of map string comma object or dynamic then I want the image URL and this image URL right now is going to be an asset later on it's going to be coming from the web itself because when the user uploads the image from the device it is going to be stored in the database and then we are going to get the URL from the database to display it on the web now if you don't understand it don't worry don't worry at all just know that this image URL is the URL we are going to have in the assets so let's go ahead and create an images tab and import all the images now you can find anything from web which is a shoe and you can paste it for yourself but I already have it with me if you want the same images as me you can find it in the description again below Also let's open this images and finder let's paste it come over here we have all the images you can view it in vs code itself that's nice now I can go to the pubspect.aml file scroll up we have assets images I can just uncomment everything and mention the path to my images just like we did for font so I'm going to have assets slash Images slash shoes underscore one dot PNG and you need to do that for all them choose one two three four so let's go ahead and type it out now yeah it depends on you if you want to do it for all the images you can do it one by one or you can just exclude everything and just have assets slash images slash you need to put the slash here if you don't put a slash and you put it like this it will think images is some sort of file and if you put a slash over here it will think Images slash is a folder so we need to import everything in this folder so if you do this it will import all the images to your perspect.yaml in your flutter project now you can use anything inside of your app now a disadvantage of doing Images slash is suppose you add some other image which is not related to your app but just to test it out let's say I add shoes underscore file and I never use it in my app but I've still registered it that will add unnecessary weight or unnecessary size to my application and we want to reduce it as much as possible so yeah always try to reduce the application size great now we can close this and we can mention the image URL we have assets slash Images slash shoes underscore one dot PNG now you can copy paste this again and again so that you have appropriate stuff so I'm going to paste it four times now if you don't want to write all of this by yourself what you can do instead is check the description of the video there you'll find a link and you can copy all of the product data from there which is what I'm going to do so I can select everything paste it over here and I have products I did miss one thing which was or two things ID and Company so what company is this or what brand is this shoe off this will help us to figure out how to filter things and then an ID for every product and then we have the correct image URL for everything we also have another thing over here which is the cart I hope you copied that as well and that is a dummy data for the stuff to be shown in the cart later on when we add State Management it is going to be dynamic but just when we are creating the UI we want it simple right so we will just have our card as a dummy data perfect now let's close this go to the home page and just before the column ends because I still want it in a column right we have our first element of the column a row then the second element as a list view Builder and the third element well what is this going to be this is going to be a list view Builder as well right this is going to be a list view Builder because I want to build all the products that I can see products.length and I want to display a product card for it every single time I have that so we are going to use a list view Builder as well so I'll type out list view Builder like this and then we are going to get a context index and that's it we also need to specify the item count we've used lets you Builder quite a few times so we know what to use but now we need access to the global variable products so we can just type in products like this dot length and make sure that you import the global variables package from Shop app fillet which is our own package all right so now we have access to the products and now we can extract one particular product using products at particular index so now we have access to each of the product here and now we want to design how the product card should look like it should look like this and I'm not going to go ahead and return let's say a container over here because this can get quite big so what I'm going to do is extract this out in a separate widget of its own and call this product underscore card dot dot then I'll import material.dot then I'm going to have a stateless widget and I'm going to call this product card all right I'm also going to return a container and let's go ahead and make this card now here you have two options to use you can either use a card widget or a container which one will you use here well you can use both of them and style it according to the way you want but I'm going to go ahead with container because card will give me an elevation it gives me it will give me a shadow effect behind and I don't want any of that effect I just want a simple box to be there with color in it so I can just use a container for that task and then I'm just going to go ahead and put in a child and in the child a column and the column will have children why because we have three different things here we have the title we have the price and then we have the products image URL okay so let's go ahead and do this so the first thing is the text so we need the title and the title is going to vary for everything so we can take it from The Constructor just like we did with the weather app right so we can have final string title then we are going to require this through the named argument and then I'm going to have title passed it over here great also since it is giving us this warning and I want to get rid of this warning I'm going to put a color over here and the color of the container is going to be this particular color so what is this particular color well it can be color dot from rgbo 216 240 253 comma 1 okay so our value is 216 G is 240 253 is blue and opacity is one and if I save this I see nothing because I haven't returned the product card so let's go ahead and return it over here I'll return product card and the title is let's say hi okay I'll save it and nothing shows up on the screen why we are expecting a list view Builder right but if we open the debug console I see these errors why is this error well again the same thing unless you build it wants to take the entire width or our entire height but it's not getting the entire height so we need to give it the amount of height we want to give it and what should the height be here well it should be the entire remaining screen right we cannot give it like size box 400 because then on certain screens it will only take a level this long and on certain screens it will take the entire height so for this reason I am going to wrap it with a widget of expanded so it will take the all amount of possible space and here we see high perfect and we have I guess four products returned and even in a global variables we have four products so that means we are doing the correct thing nice now I'm going to go ahead and put a size box of height 5 and after that I'm going to put a price so the price is going to be dollar something and that something is going to come from the Constructor again so I'm going to have final string or final double price and then we're going to require this price so we have required this dot price and then we can have dollar dollar price but now we have two dollars and it thinks we are using the dollar to half string interpolation So to avoid that we are going to put slash before the first dollar sign so it knows that we are talking about the real actual dollar and then it can use string interpolation for dollar price perfect now I can save this much I come away I see nothing because in the home page I need to provide a price so the price right now can be a static value of 25.2 come over here and we see dollar 25.2 that's great and the final thing I need is my images to show up so again I'll leave a size box of height 5. now how do we show images in flutter apps that's not what we have seen so to do that we have the image widget right we have this image which you can use to display stuff and then this requires an image property which requires image provider so we can pass an image provider here and you see it's an abstract class so again we need to use a subtype of image provider and whenever there is abstract class abstract class is only created in such cases because there are multiple types you can pass to it for example this image can be from assets what we have mentioned in our app it can be from Network that means it's coming from the web and you want to display it so there can be multiple types that's why the abstract classes are created that's why we can just search for asset image and you can pass it over here and this asset image requires an asset name so our asset name is going to come from here again so you're going to have final string image required this dot image now I can take this image put it in asset image and we're done now we can come here path in an image and for image we'll have to use this product so we can go ahead and use product image URL as string all right we need to use as string over here because in global variables products is defined as list of map of string comma object it thinks it's an object not a particular value or not dynamic so that's why we need to tell it that yeah we are sure that this is a string and we can do the same things over here since we've already done it product price as double and product title as string right now we can come over here and we see our images are showing up nicely and it is scrollable so that's good now first thing we need to do is make sure the height is constrained it's not whatever it wants to be so let's go ahead and use it so an asset image we cannot specify the height but an image we do have a property of height so we can go ahead and pass the height as let's say 175 if we do that it will only take as much height as we tell it to all right great now instead of using image like this a smaller option can be image dot asset then you directly mention the asset and you can also specify the height over here and you're done so this is just a shorter option of doing the same thing you can use it because it's the same image widget that we are using but now it has dot asset to it attached so it is a Constructor thing and it just simplifies a task if we want it to and you'll see no difference over here perfect now we do have a white patch over here and that white batch is visible over here as well and that's simply because of the image we've chosen the image is like this that's why we are getting the white patch okay great now that we have image.asset in place the next thing I want to do is increase the height of all of these things so I want a particular textile for this thing so what I'm going to do is generalize it in main.dot for text theme right so I'll come over here and add text theme this allows me to pass in typography or theming of text all right now I can pass in the text themes I want to use and I'm doing this because I want to reuse my titles everywhere I use all right so if I am using a text title over here I want that particular theme to be used in some other text theme as well that is why I'm mentioning it over here you'll see it later on as we reuse these text teams the main point of me doing all of this and setting up the text theme over here is just reusability I can change the text theme from one particular place and it will reflect all over the app that's what I want so anyways I'll go ahead and mention title medium which is what I'm going to specify for this thing over your title medium so the textile here is going to be font weight font weight dot bold because I want it bolded and the fonts size I want to use the size so the font size will be 20. quite small because our main title this title over here is 35. so I want it smaller than that and much smaller than that and now if I do that there's no visible changes over here because this text is on its own it doesn't inherit the properties I've defined over here so I want to make sure that it inherits those properties or you know just starts taking those properties not inherits but starts taking those properties so I am going to put style and that will be theme dot off context so you see the context is helping us over here to find the particular widget in the widget tree that's what we had discussed right context will always help us to locate a particular widget that's why we are passing the context over here and even if we go to the function definition you'll find inherited theme is equal to context it uses the context to find the particular inherited widget of that type so it uses context to find another widget of the same type this is where context can help so here I'm going to do theme dot of context dot text theme Dot and here what is the style admission title medium so I'm going to mention title medium yeah perfect and when I do that it looks good perfect now what I want to do is set the style for this dollar 44.52 as well so let's go ahead and the main.dot file and here I'm going to mention either title small or body small you can use whatever and please note that these font sizes like title medium body small these are used by certain widgets when they want to set up text for example Abba Abba uses one of the properties from your like title Lodge to display text on the screen so text theme has a bunch of values already there you can see it over here if we don't don't mention anything they have a style of their own but if we do mention it it will override those existing stuff and app bar like widgets so for example if I put app bar text text uses this text themes property like title Lodge to display stuff on the screen I'm going to share it to you when we go to the product details screen you'll see that okay so we come over here set up body small now you can set anything but I'm setting it body small because I want the body to be small everywhere so I can have textile and font weight can be font weight dot bold again and font size can be 16. so it's smaller than the title medium but it's still small now I can come over here I'll copy the style I'll paste it for the price but instead of title medium I'm going to have body small okay now if I come over here dollar 44.52 this is nice great so we have all of this set up but still there are problems if you compare it with your there are many problems so the first problem I want to fix is the alignment issue so everything is in the center I want everything to be in the left hand side so in the column I'm going to set the cross access alignment obviously I want it in the start and it's a column style of cross access alignment dot start we'll save it and everything shifts over here but I still want padding to be present so what will I do I'll wrap this column in a padding widget I hope you're getting the hang of it whatever you can think of this is what I want to do you can display it on the screen so I just thought that I wanted this to be a little bit away from everything from the left from the top so I just use the padding widget it should come intuitively to you now instead of all I can have agencies.all 16 and this looks better now the problem here is the image isn't centered I want it to be in the center I don't want it in the left hand side just after the padding is done no so what I'm going to do here is wrap the image in a center you can use align property you can use some other thing you can think of but I'm going to go ahead and Center it and yeah that's easy the next thing I want to do is make sure that I leave some space from here you see there is space between every card and there is space from the device with as well so again we'll have to use the margin property of the container since we are in a container we don't have to wrap anything so I can just do that so I'll have margin agent sets Dot all 20. also I can put conster wire save it and there we go perfect now you might think hey since you already have a container why are we using a padding over here why can't we just take this padding and push it over here and then you can remove the widget you can remove the widget by doing so save it and yeah things are still the same if you thought this way then congrats you're becoming a better flutter developer you have your Basics nailed down since we already have a container there's margin property and there's also padding and I've already explained the difference between the margin and padding to you so we don't need the extra padding widget now if you put it there's no harm but why do you want multiple widgets when one widget can do it for you sweet the next thing I want is the border to be curved and that should make my entire app better so how do I make this curved does container have a property for that not really there's no order related property but we do have something known as decoration and this requires decoration which is again an abstract class so you can't instantiate it however you can use box decoration which is generally used with flutter so you can use that over here and box decoration will allow you to pass in a color which you've already done but you'll see why we need a color over here then we have an image that we can pass in yep we can pass a container image then border border radius border radius is what we want we want to put that nice curves so we can put that and now we can have border radius dot circular 20. again tried and tested values you can just keep using it and now we see an error as soon as we provide border radius it is giving me an error why so let's try to remove water radius and C if I remove water radius I still have this error so this has something to do with box decoration if I remove box decoration and save the errors go away now this error is there because you have defined a color over here and then you've also defined decoration now if decoration is mentioned then you have to shift the color from outside to inside and then the error goes away however if you have no box decoration or decoration mentioned you only want a color then that's fine too but both can't be there decoration and color in a container cannot be passed the color has to be moved inside the Box decoration for it to work now you might ask why does container have a color property if box decoration also has a color property and that's because box decoration isn't just used for container it is used for literally every decoration property so if some other widget requires decoration property and a decoration class you can pass box decoration to it and then you can also specify the color also since it requires decoration something that extends decoration can be path stair so it's not necessarily box decoration Maybe you want something else some other decoration type and you can see that over here some other decoration can be known over here like shape decoration all right that's why color was mentioned over here so yeah the point is if color is defined in container you cannot use decoration and if you want to use decoration Define both of them inside it's also written in box decoration over here if you scroll down if color is null this decoration does not paint the background color if images null this decoration does not paint a background image and it does so on and on okay so let's restart and become aware and our app is looking similar not the same why is it not looking the same well that's because the colors are different the first card is this exact color but the second card is a different color and this color if you notice this color is quite similar to this color so we need to use this exact color and we need the background color to change how should it change well if I just open the app for you the first one is blue second one is white third one is blue again fourth one is white so this is the pattern we want how can we have this so to generalize on even stuff we want blue color otherwise we want white color on even stuff as in the index should be even so this was zero so it was considered even so we could mention blue color but as soon as it became indexed as one it became odd that's why it has a background color of white so we are going to ask for the product card color here so we are going to have final color background color and this will be required through the Constructor now we can take this background color pass it to The Container color save it come to the home page you have background color pass to it then you'll have product but product does not have any background color how do you how will you make sure that product has a background color so this is the reason why we have to do something like this so we need to check if index is even so if index is even that means it is 0 2 4 6 8 10. then what do we want to do so if index is even I want to give it a particular color if index is odd then I want to give it the white color so that's what I want to do so I can just have if index is even then I'm going to have constant color dot from rgbo then I'm going to have 216 240 253 1. otherwise index is not even then I'm going to have constant color dot from RGB again but this will be 245 247 249. 1 what we've used before all right this is the same color we use for the chip earlier you can see it over here so anyways we have this setup and now you can see the clear difference now our app is looking much better perfect so this looks great the next thing we need is this Bottom bar and we can add that later on but first what I want to focus on is whenever I click on this product the product Details page should appear so to show your real demo if I select this one I click over here the title appears the image appears then some different colored box appears with the price the available sizes and the add to cart button so I want to design this so let's go ahead and design it so we are going to go ahead in the lib folder and create product underscore details underscore page dot dot now I'm going to right click over here and close others so it will close all the other files over here so I have only one file to focus on then I'll import material.dot again then I will create a state less switcher and I'm going to call this product details page then again we are going to return a scaffold and now I want to test how this looks all right so how can I test it well for that I can just take this product details I can go to the main dot dot and replace home page with product Details page to see the thing right so yeah we do see an empty screen also it is continuously showing performing hot reload for iPhone so I'm just going to exit that process and I'm going to select iOS here again and then going to run it so that should hopefully work and while that is happening let's go ahead and design the product Details page so the first thing we need is an app bar which just says details so we are going to go and have an app bar title constant text which says details save it and we see details over here with the yellow background and that yellow background is there because we have set primary color to this yellow color So to avoid that yellow color what I can do is go to the main dot dot and you have set up the global theme for my app bar my app bar should look the same on every screen so I'm going to set up the app bar theme over here which I can obviously change from here as well but I'm going to do it here because I want it for every app bar so I'm going to have an ABBA theme which is going to have first of all a title textile so the textile is going to be font size 20 so I want it a little bit bigger and the color should be colors dot black okay because this is white as of now and doing this much the color changes the next thing I want is it for it to be transparent and in my opinion it is not transparent because we have not set use material 3 to true so we want to make sure that it is set to true and you see everything changes also if we come back to the home page over here let's put home as home page and we come over here nothing really changes over here things are still the same what has changed is the app bar is now so first of all let's just change it again product Details page app bar is now white in color perfect then we want the title men's Nike shoes or whatever so for that we'll have to get access to the product so we are going to take it from The Constructor and have final string object which is Prada and then I'm going to require it through the Constructor so I've required this dot product then I'm going to have a body the body is going to have a column column is going to have children and the first child is going to be text which says product at particular title which is going to be treated as a string cool now if we come to the mean or dot you see we have to pass in a Constructor here and the Constructor is a product so let's go ahead and pass in we are going to import products from the Global variables.dot file and then I'm going to access the zeroth element now it says invalid constant value because this isn't a constant this is a global variable that can change so we can have a constant removed and there we go so we have men's Nike shoes written over here now don't be concerned about products at zero we're just passing product Details page over so that we can take a look at how to design the page and after that I'll tell you how to navigate from one page to another okay so let's go to the product Details page here now what I want to do is set the style for this men's Nike shoes thing and if you notice that this font size and this font style the font weight and the font size both are very similar to what we had in the shoes collection both are of equal height both have the equal font weight so both of them are quite the same so what I'm going to do and what's going on in my mind is what if I go in the home page I copy this textile I go to the main dot dot and then I'm going to have a title Lodge and I'm going to paste this as a textile so the font weight is bold the font size is 35 now I can come to the home page and I'm going to have theme dot of context dot text theme Dot title Lodge so with this I'll have to remove constant I'll have to set constant for this part for this part but the text style is no longer constant because it is theme dot off context great now why have I done this I've moved this to the global theme and set it to title lodge because that's what I want for title Lodge and now I can reuse this component easily by just copying this thing so this textile can be applied to any text I want to apply it to this text I'll just pass in the style as this thing over here save it and there we go men's Nike shoes shows up and it's looking really good the next thing I want is the image but before that I want spacing to be present and the thing about spacing and the tricky part about spacing is this if I come back to the normal app if I have this kind of thing the spacing should decrease but if I have this kind of shoe the spacing should increase so it's relative spacing right I can't give a fixed value over here otherwise I'll get render flow error because this shoe is quite big so if I put let's say a size box of height 50 and your I put a size box of height 50 again that will work but if I put a size box of height 50 over here this shoe will go on the top then I'll have size box of height 50 again and this container will come right over there so it's not consistent UI basically and our spacing wire requires relative spacing so for that particular reason there's another widget that will help us to space stuff out and that is the spacer widget so if I pass constant spacer like this the spacer requires something known as a flex so anytime you use spacer it will create a flex of one on your screen and it will relatively lay it out so to show it in a diagram form let's say this is my screen let's say I have my text widget over here then I want to leave some space so I can just leave some space here this will create a flex of one then I have suppose my image so my image is showing up like this then I'll again have a spacer so spacer will be like this this will also create a flex of one and this will be relative positioning meaning the spacing will be carried out like this by performing the calculation that there are total flexes on the screen is equal to 2. so each Flex is going to take a size of 1 by 2 on the entire screen since the number of flexes on the screen is 2 this space is going to be 1 by 2 and this space is going to be 1 by 2. so they equally divide themselves if I add one more let's say Flex let's add one more Flex over here the total Flex will be 3 and each Flex will take 1 by 3. now a weird thought comes in what if I want one of my spacing to take double the space of another what if I don't want second space and this Flex should be bigger all right it should be twice the height of how much this Flex is taking so what will happen I can specify a flex property to it you see we have Flex so this can be flexors too this will be Flex as one so the total Flex is 3 but this will take one third of the available space and this will take two third of the available space that's how flexes work if you don't understand this I'm going to demonstrate a practical example to you but that was just a diagram so now I've created a flex of one now I'm going to use image.asset to display my image again and that will be product at image URL and we are going to take this as a string save it and we come over here our image is showing up and this is the previous app we'll get to this app and our image is showing right at the bottom not bad because what has happened over here is the total Flex is one since the total Flex over here is 1 it says hey I'll take one out of one space so it takes all the available space however if I add another spacer what happens is there are two flexors on the screen this thing right here and this thing right here so this takes one by two and this also takes one by two so both of them take 50 50 of the available screen space but that is not cool because it's simple this should be one this should be two because this image should go more up so your will pass and flex as to save it come over here this looks good enough the next thing I want to do is wrap this image with a padding so I can do that I can wrap this with a padding widget and then I'm going to have agencies.tall 16. and this looks better I'm not going to specify any height width Etc after this what I want is a container if you can see over here What's Happening Here is there's a container which has its own background color you can see it over here then it has its own text with the price then the available spy sizes you can select from and then an add to cart button so we need these three components in this color so what will you use here and how will you lay it out well we can use it in a column first of all that's a good thing to clear off so let's go ahead and create a container down below so we're going to have container decoration box decoration then I'll mention a color so the color is going to be constant color dot from rgbo and it's going to be the same color that we had used earlier for the chip for the second box that was odd I mean the box that had even or odd index so we're going to have 245 247 249 and 1. after mentioning the color what I'm going to do is mention the width as well so the width over here let's say is 250 I'll save it and I see nothing on the screen why because I mentioned the width the containers with doesn't really matter here the height matters because the container is getting the maximum width because column is taking the maximum width now because it is in the scaffold's body so I can set the height as 250 and you see a container has risen above where and that looks solid perfect then I want to make this curved if you see a wire this is also curved so I want this container to be curved as well so that's why I had set up box decoration so I can use your border radius and the Border radius will be border radius dot circular 20 let's say come over here and it's hard to see but the Border radius isn't quite enough so I'll set it to 40. and I think this is quite like it so I like it this way that's good now after the containers decoration has been done we can go to the child again column I hope you're becoming experts in UI it is so intuitive in my opinion you know I want everything vertically I can use a column if I want everything horizontally I can use a row if I want to put items in a list I can use a list view Builder if I want to display a text I can use text for an image image.asset so I hope you're understanding and getting the hang of things then I'm going to mention texture and the text is going to be well slash dollar dollar then I'll have to mention product price like this cool so we have dollar 44.52 showing up but this now takes only this much space I want to take the entire width so for that particular reason I can have double dot infinity or even if you don't mention the width it's fine because we have a list of sizes to display when we have a list of dial sizes to display we will be using list view Builder because we don't know how many items we are going to have it's not one particular value it can be 9 10 11 12 for one product it can be eight nine ten for one product it can be six nine twelve for one product so the sizes can vary and number of items can vary that's why I'm using a list view Builder when the number of items is not known you can use list view Builder when the number of items are known then you might want to use list view we've not taken a look at list view but let's do the same as listview Builder instead of passing an item count item Builder you just have to pass in children just like a column and just mention stuff in it so anyways we have product price what I want to do is make sure this text is big enough and if you notice this text is as big enough as this one so we are just going to have a style of theme dot of context Dot text theme Dot title launch if I save this dollar 44.52 shows up and now in my column the next thing I'll do is leave a height I'm not using spacer over here notice that I'm using a size box because this isn't relative height it doesn't really matter if my height is relatively spaced or not in terms of images it did matter because I wanted consistent UI so anyways we have a size box here that looks good so we'll have a height of 10 and after that we are going to have a list view Builder that will tell us all the available sizes so we are going to have listview Builder with an item Builder context and index then you are going to have item count and the item count is going to be product sizes dot length now if we go to Global variables product sizes so we are doing the correct thing but we are calling dot length property on an object so obviously we need to treat this as a list of double but if we use it as list of double then it will give us an error like this why because you're saying list of double dot length you're not saying product sizes as list double dot length Okay so you need to wrap it with the apparent thesis and then you're done okay now you can extract one particular size so you have final size which is equal to product at sizes at particular index and here it's saying you cannot invoke this thing this index unconditionally because it thinks that product sizes can be an object which is nullable so what I'm going to do here is tell them that yeah this can never be null and then access the index property on it but then also I cannot access index property because there is nothing like add index on an object so we need to again treat this as something so we're going to have as double then I'm going to take this as a whole also this will be list of double and then you'll have access to index so what I've done here is the same thing product at sizes as list double and then I'm calling at index to get one particular size and now I want to return it so I'm going to return chip and then the label which will be text size dot to string perfect now we'll save this become aware and we get an error the error is there because it is saying that list of integer is not a subtype of list of double so it considers these sizes to be all integer and that is true as of now everything is integer but so let's go ahead and use that particular thing so we are going to have as list of integer list of integer since everything over here size is 9 10 12 9 10 12 it cannot have a decimal value right that's why it is an integer now you can just have list of end and you see our UI is not distorted the error goes away but it is all distorted and it's again thanks to the list view Builder again list view Builder wants to take the entire screen size it's not getting that so it's just distorting our UI and giving us a bunch of Errors again wrap this in either expanded or sized box I'm going to wrap it in size box why very simple size box will give at a particular height of 50 so it is constraints in that particular height all right and it can't grow bigger than that Also let's set the scroll direction as access dot horizontal and everything is and horizontal Direction after that I'm just going to wrap my chip widget with padding widget and I'm going to have Edge and such dot all 8 and everything is evenly spaced out that looks cool after this we finally need add to cart button and we are done also I think this dollar 44.52 is right up we have to center it but we can do that after we add a button so again let's go ahead and leave a size box of height 10 then I'm going to have elevated button very simple I'm not going to use text button and the child is going to be text which says add to cart save it also we are going to put constant come aware we have add to cart button but now we need to style it first we need a background color then we need to set the size for it and after that we might have to change the color of the text because the color of the text inside of it is yellow we want to change it to Black so let's go ahead we are going to have style which will be elevated button dot style from then we want to set the background color we've already taken a look at the button so much it's just a revisit for you I hope so now the background color should be yellow and it's yellow because the overall theme of my app is yellow so now I just want to set it to theme dot off context dot color scheme dot primary color so with this it has a primary color of what we have defined yellow now I want the minimum size to be there the minimum size of this button should be this much and otherwise it can take whatever it wants so it will be double dot infinity and height will be 50. then we can save it come over here and here is a button add to cart button has disappeared and that's because that was already yellow so let's change it back to black so we are going to set the style over here which will be textile color will be colors dot black and font size will be 18. let's just make the font size a little bit bigger this looks good now we need some spacing from your right so obviously we need padding I hope that stuck your mind you know this is a way to know that you're progressing then you have Edge and such dot all let's say 10 not enough let's try 20 good enough but the width or the height between both of them has increased and it has increased because we have a size box of height 10 over here then we have agencies.all 20 so that means the spacing from here till here is 20 plus 10 which is 30. and from all the other sides it's 20. that's why what I'm going to do is remove the size box height so from all the places it is 20 and it looks better and final thing for the UI here is I want everything to be in the center so I'll just access the main column and set it to main access alignment Dot Center and there we go this looks awesome the next thing in this screen what I want to do is whenever I select a product I can select a size for it and we've already done this with the chip widget the same thing I want to do over here as well with the sizing so I recommend you to try this on your own and make sure that your logic is correct and what you're doing is correct so that you have more confidence in yourself so pause the video and try it for yourself I hope you were able to do it for yourself now let's try it together what I'm going to do first of all is convert the stateless to a stateful widget then I'm going to have end selected size is equal to 0 let's say so the selected size is 0 at first then I take the selected size so I have end selected size equal to 0 then I'll scroll down here where did it go the chip yep yeah I'm going to have a background color of selected size is equal equal to size so if it really does match my size then I'm going to select one thing so let's say if it is selected then the color is theme dot off context dot color scheme dot primary color otherwise it is all going to be null okay that's nice if the background color is null that means it takes the default color that is already given to it and we get this kind of error now so let's just restart and there we go error is fixed to fix it on Android emulator we'll click over here restart and it will start okay cool now if I select anything still nothing happens because we have not updated the value of selected size so what we need to do is wrap the chip widget with a gesture detector we are not going to wrap the padding widget with gesture detector and I've already mentioned the reason to you now uh in the on top I'm going to have set State don't forget that and selected size should be equal to size the size we have extracted over here and now if I select anything it is selected perfect now what I want to do is come back to the main dot dot I'll mention home page over here and this should be a constant I'll come at the top and remove product details and Global variables from here now what I want to do actually is whenever the user clicks on one particular product I want to navigate them from one screen to another how will I do that well that opens up to a New Concept and flutter which is Navigator let's talk about it and how it works so let's dive in the code for it we are going to close all the files here and I'm going to go to one particular page which is the home page where I have just one thing if I scroll down the product card so I want the product card to be wrapped with the gesture detector and whenever I click on that product card I want to get navigated from one screen to another so first of all let's go ahead and wrap it with gesture detector then we are going to have on tap you see there are lots of options gesture detector provides as well but we're going to go ahead with on tap and then on tap what do we want to do well we want to navigate from home page to product Details page now since we have that much Clarity it's easier for us why we just have to do Navigator dot off again or Navigator dot off also uses inherited widget behind the scenes and context is used to find ancestor State ancestor State again so context is helping us find the nearest Navigator and using that Navigator I can navigate from one page to another then after doing navigator.off I get a bunch of properties over here Focus node overlay but that's not what I'm interested in what I'm interested in is methods like pop push pop and push name so let's go over them one by one so first one is pop pop is basically popping off the screen now to understand this you'll have to understand how Navigator really works let's remove this diagram and draw a diagram for navigator think of Navigator as a stack all right what is the stack well let's just think of it as a pile of books on a desk all right so let's just consider this is a desk and then you have a bunch of books on top of it so there is one book all right then there is another book on top of it and then another book on top of it okay this is how Navigator works it works on the concept of Stack this is a stack anything that's above one another is a stack and just as a general information stack is also a widget in flutter that will help you to build uis so it has children pass to it so you can pass one particular widget which will be the background and after that the next widget you pass in will be above it so if you have text hi then you have text hello that will just make sure that there is kind of this thing so let's just have this CC hi is there you won't be able to see it but you see H is kind of bolded that's because hi and hello are there so H is overlapping so basically high is below hello so it is stacking up so in this case hi is this thing hello is this thing and the eyes are over here this is your eyes right if these are your eyes and you're looking from your to bottom what will you see you'll first see Hello then you'll see hi right and that's why stack is there so this is the general concept of stack stack is also a data structure so basically this is the concept on which Navigator works whenever you call things like pop it just pops off and removes off the topmost screen it will just pop off and remove off the topmost screen well how do you add screens on the top that would be the biggest question well for that you use Navigator dot off context dot push so what push does is it has one widget it will just stack it above another again you push something from One widget to another it will just put it on top of another widget so this is our push walks and pop just removes off a particular widget just think in terms of our array right it also works on the concept of Stack right if you use two and then you use add function to add the number three it will add it to the last then you use push to add four so you will be adding 4 to our array and then when you want to remove something or pop something it will remove it from the last unless you specify what kind of page you want to or what kind of number you want to remove so it's kind of like a list but in general it is called stack okay so now I want to call Push because I want to push it now here's another important concept which is of this thing push replacement so what push replacement does is if you call navigator.ofcontext Dot push replacement from this screen it will replace this entire screen with a different screen altogether so this is out of the picture now now if you call Pop after that it will pop this screen and will give you the screen back so replace push replacement just replaces the entire thing entirely it just removes it from the stack with itself and then when you call pop it will just pop this thing so I hope you understood that now we have Push replacement here not push replacement I want Push and what push requires here is something known as route and generally what we pass over here is material page route or a Cupertino page route or something that basically extends mati uh just a page route all right so you have page route Builder that you can pass over here or anything that has or extends page routing why do we have to do this well it's boilerplate code but we have to do material page route because what you're doing is trying to add a platform adaptive transition here so moving from one screen to another looks different on different devices and those are transitions the way they do it on iOS it might be different from for iOS it might be different that's why so you need to mention material page routing and here you can mention more settings but I hardly ever use any of them then it requires Builder that requires a context or that gives the context which you can use so we have this and here what do we have to pass well we have to return a widget from here what Widget the widget you want to transition to you want to move to so I want to move to the product details screen so I'm going to return it from here and I'm also going to pass in the product that I have extracted here perfect now if I save it I'll restart my app and when I click over here I go to the particular product if I click over here I go to Adidas shoes if I click over here I go to Bata women's shoes now I know the images are incorrect but forgive me for that this is just about learning all the images and illustrations used here are incorrect I know so we can close this and yeah this works well now just to demonstrate what I was talking if I use replace surveyor not replace push replacement then what will happen is when I click over here I won't be able to go back when I try to go back I won't be able to on Android emulator to go back I have to click this when I try to do that I won't be able to do obviously only when I click over here when I try to go back I just exit the app again when I try to open the app you know I just go back that is how replacement works I won't be able to go back from the screen so obviously push replacement is needed and stuff like let's say Authentication so when you have logged in you don't want the user to go back to the login screen that's why you use push replacement that time not push but in scenarios like this push is very much needed and you also notice the difference over here all right let's have iPhone simulator hot restart when I click over here and when there's push I get the back button however when the push button is not there it's push replacement then I don't get any back button so I hope that was clear and I hope you understand what the code for navigator is it's Navigator dot off context then you either want to push push replacement pop and there are a bunch of other things like push and remove until there's push named which is related to named routes but we'll get to it when we start building stuff for the entire web all right when we make our layout good enough for all the screen sizes so we have push here then we have Push pop and push restorable push all of that stuff but the most commonly used is push push replacement and Pop I don't think you're going to need anything other than those 90 of the times obviously so now that we have understood this I just want to clear how Navigator works so in flutter the Navigator is actually responsible for managing the navigation stack and handling the transitions between different screens or routes in an application we passed in a material page route and that handles the navigation you see when I click over here I get a transition which goes from right to left but on Android it goes from bottom to top you see not even bottom to top it's kind of like a fade animation so it is platform adaptive based on what platform it is on it will perform that navigation or that transition and whenever we call Navigator dot off context we're basically using inherited widget it Returns the nearest Navigator widget in the widget tree that contains the build context exactly like theme Right In theme also it would go up the widget tree finding theme class and it would inherit or take properties from it same thing is happening for navigator it is going up the widget tree trying to find Navigator now you might say hey everyone we have never created any Navigator stuff away and that's true you've never done it but material app has material app behind the scenes creates a navigator class which you can find when you just try to look over here all right you'll be able to find stuff so material app does it for you now behind the scenes Navigator maintains a stack of Route objects which I told you about which represent the different screens or routes in your application I'm saying different screens or routes because sometimes you might not want to return a screen when you go to a particular or when you use Navigator what you want to show is let's say a half screen dialog something like an alert dialog box something like that so even then Navigator can help you and those settings over here which are present for navigator in the material page route can help you like full screen dialogue maintain State all of that so those are different routes but usually you'll be encountering different screens because to create a dialogue a pop-up you have several other things now when you navigate to a new screen you push a new route onto the stack so if you want one particular screen so let's say I have my home page over here that's the home screen now I want to pass product details so I'm going to pass it at the top over here so I push it on top of the stack and this is what happens when you navigate back for example when I click over here and when I go back when I click on this back button Navigator dot pop is called all right and then you navigate back from year to year so behind the scenes navigator.off context Dot pop is called so it goes back to whatever screen it came from so just to summarize if you've understood you can skip this part whenever you call Navigator dot off context it looks for the nearest Navigator widget in the given tree and this is typically provided by material or Cupertino app right at the top of the widget a hierarchy our root widget once it finds the Navigator widget it returns an instance of the Navigator state now this Navigator state is the thing that allows us to manipulate the navigation stack so if you go to navigator.off context you'll see static Navigator state so this Navigator state is the thing that does most of our work and it allows us to manipulate the navigation stack so with the navigate a state object now you can perform various navigation operations like we saw whenever we call Navigator dot off context it gives us the Navigator State now with this Navigator State we can call push pop push replacement all of those stuff when you push a new route the Navigator animates or transitions from the previous route to the new route using transition animation which are already predefined for platforms on Android it is like a fade in transition and for iOS it is a sliding transition transitions are there so that it provides a smooth visual effect it doesn't go like hey you suddenly change the screen and you get to know that these are two different screens it just is a smooth process and when you pop it out from the stack the Navigator reverses the animation bringing back the previous route so when you click over here you see we have right to left and when we click back it is left to right so it just reverses the transition so I hope you understood how Navigator works and this is how anything that has dot off context will work because they are using inherited widget and that is the biggest concept in State Management once you understand that you'll be understanding Navigator scaffold messenger that we'll take a look at and many State Management tools as well and I hope you're also understanding the importance of build context Bill context is making sure behind the scenes that you can find the correct Navigator State widget because just think about it even in the flutter source code the flutter source code is so big and if you want to access from One widget to another there might be some way of communication right you can't just keep going through the Constructor and keep passing everything for stuff like these product Details page Constructor is fine because it's just one product that you want to display and storing it in a state management tool is just stupid however in stuff like add to cart using State Management is required for example if I have a bottom navigation barrier and when I click over there I should see the card page so that means I go to the product Details page I click on add to cart and it should add it to my cart page think of it in form of a widget tree if it's hard to visualize just draw it out and see or I can do it for you you have your root widget then you have your material app then after the material app you have the home page then after the home page there's another widget you could take which is the cart page right home page and card page are shown differently as of now so if you click one item like the cart button in the bottom bar for example over here when you click the cart item you should be seeing card products so there are two options you can take now in the home page if you click on something you can go to the product Details page now my card or my add to cart button is mentioned inside of this particular widget which is the product Details page so what I want to do is whatever I click over here should be added to a list and that list should be accessible in a separate widget as well how do we do that how can I make sure that stuff passes from Child widget to parent widget from parent widget to its parent widget and then it can pass it to its sibling this is quite a cumbersome process you can do it in flutter but it's quite cumbersome so instead of doing that what I'm going to do is introduce State Management which usually does something like this you shift everything down then the State Management tool will create a storehouse for itself right at the top of the widget tree and here you store all the data and this is what state management is you store all the data over here so what you do is add to cart from your to your the changes are made over and then you continuously listen from the card screen to this particular screen or this particular storehouse so just to summarize if you didn't understand whenever I click on add to cart button in my app over here it should be displayed over here so what I'm going to do is whenever add to cart button is clicked on I'm going to update and store all the data in one particular State Management tool which will be the head of everything and whenever I want to read data I'm going to read everything from this State Management tool or the storehouse itself so if I make changes over here I can read it instantly if I make deletions updating any stuff it will automatically be received over here this particular tool will do that so this is what we are going to do in State Management I hope you understood the concept because I'm not going to explain it again I've already explained that now we'll see it in the form of code but before that we still have to get done with the UI and what I want to create is a bottom bar over here which tells you hey do you want to access cart you can access card from here so let's go ahead and do that so let's go ahead and add bottom navigation bar to both of these things so let's just close all the save files from here go to the home page and here we are going to set up our bottom navigation bar because whenever we return a scaffold we get body we get the Abba property and we also get a footer kind of thing which is the bottom navigation bar this bottom navigation bar accepts a widget so you can pass anything over here but there is a special widget for bottom navigation bar which is modern navigation bar itself here there's a required argument of items that you need to pass in and it should be a list of bottom navigation bar item so we're going to copy this put it in the list and then we're going to use that so we're going to have bottom navigation bar item and here we're going to pass in an icon and that's pretty much all there there is so the item we want over here or the icon we want at first is icons dot home so I want the home icon to be there and the second item that I require is bottom navigation bar item which is shopping bag or shopping cart whatever you want to use I'll go ahead and use shopping cart then you can save it also put a constable because both of these items are constant so the list becomes a constant and when you come over here you still see this error and this error is basically saying that item dot label is not equal to null so that means the label property should be added somewhere where in bottom navigation bar item even though this is nullable it does require a label to be passed in but what if I don't want to pass any label it should be nothing so I'll just pass in an empty label here in both of these things and the error goes away I see my bottom navigation bar great now what I want to do is whenever I click any of them I want to navigate to that particular screen so for that reason I am going to create a function or let's not create a function I am just going to create a variable that will keep track of the current page so we have the current page at zero now I can copy this current page and here in the bottom navigation bar we require two things on tap and current index so we can pass in the current index which will be current page so this is the correct index so this is the item that we have selected also here you'll have to pass an i in current page is equal to 1 and then when you restart the app you see this thing is active now and the home is the zeroth element or the zeroth page so yeah just restart the app and you'll see the difference so now whenever this item is being tapped on we want to change the current page so that will reflect those changes right so for that we can use the ontap property given by bottom navigation bar or alternative option was to wrap this bottom navigation bar item with the gesture detector but that isn't allowed because this wants a list of bottom navigation bar items you cannot put a gesture detector here because gesture detector is a widget not particularly bottom navigation bar item only so let's go ahead and pass the on tap here and the on Tab will have a value we are going to set State and we are going to set the state of current page equal to the value this will give us and then what I'm going to do is Click over here you see there is a smooth change over here so we are able to change the item in the app but still we are not able to figure out how to change the screen how do I show this particular cart page for this particular home screen or how do I show the home page on the home screen or when the home screen is active and how do I show card page when this is active so to do that I'll have to do one thing I'll have to extract the entire body out in a separate widget of its own so let's copy this entire widget and let's call this product list so we are going to have in the lib folder a file product underscore list dot dot then we are going to import material.dot and then we are going to create a stateless widget which will be product list and here I'm going to return this entire widget I'll make sure you understand the purpose but as of now just follow along also this requires a border to be passed in and this is the Border we are basically taking a widget out from here and putting it in its separate own Widget the reason for that I'll mention in just a minute also we want filters so we'll have to convert this product list to a stateful widget because all the chip and filter stuff is inside of it and then we can take this final string filters out put it in a list come back over here then you're going to have a selected filter then we are going to have our init State and then I'm just going to pass in my product list like this okay so I've successfully extracted out the product list widget into a separate widget of its own also I'll copy or cut all of these import lines and put it inside of the product list so now all the errors from product lists are also gone because things like Global variables so this thing over here requires Global variables where is it the products yep then product card and product Details page everything is required and now if I restart you won't see any visible differences on the app it will still feel the same way what has changed however is we have access to this product list now changing from one screen to another becomes easier how well I'll show it to you what I'm going to do is create a list of widget which will be pages and that will be equal to an empty list with product list passed to it and a cart page so we have to go ahead and create card underscore page dot dot import material dot for it then we are going to create a stateless widget call it cart page then we are going to return a scaffold a body with a centered text and we are going to name it cart page so as of now this is what the card page looks like however we are going to fill that in we're going to create that UI really soon so let's copy this card page and have it over here let's paste it sweet so we are going to have const like this perfect so we have a list of pages now and that Pages includes product list and card page so this is the page that we want to show and how do we want to show it well if we are on zeroth page we want to show the product list if we are on first page I want to show the cart page so we can have that if condition over here right I can just have if current page is equal to 0 then I'm going to have product list otherwise I'm going to have cart page and that should work right so if we just restart you see card page is showing up if I go to home page home page is showing up and it does that correctly however one small Improvement here could be if we just do Pages at current page pause the video and give yourself a time to understand what I've done if you don't understand watch the next part so what I've done over here is I have Pages product list and card so if current page is zero then I'll access the product list which is pages are zero if current page is one then I'll access Pages at 1 which is cart page so I'm basically performing the same task but really smartly if I add more pages further in the app I can quickly change it so this is the thing I don't have to use the ternary operator anymore and this feels better however one problem here is that whenever I scroll and go to another page then come back everything starts from scratch you know it just starts from everything I want that scroll position to be maintained if I come away or come back the scroll position should be maintained so for that we have a widget called index stack what index stack does is it stores everything in a stack and by Stack I mean it will just keep on piling stuff so the state doesn't really go the state is still persisted in indexed stack so it requires children and the children here are the pages so we can just pass pages over here because children requires list of widget and pages is a list of widgets so we can pass that in and now the next thing we want is index so that it knows what page it is on and the index for us is current page now if you do that restart come back over here scroll and come back the scroll position is maintained you see if I leave a tat added us like this come here come back added our scroll position is still maintained so index stack allows us to do this and I hope you understood why I extracted out the product list it was just so that we could toggle between this part let me highlight it out this part of the app and it will keep on changing based on whether we select one bottom navigation bar item or another the next thing I want to do is make sure that the icons over here are bigger so for that we can set some properties for our bottom navigation bar what we can do here is set an eigen size and the icon size here can be 35 save it and this looks bigger and I like it the next thing over here is that this app bar is quite big or the bottom navigation bar is quite big even on Android and that's there because the label occupies some space for example if I pass in home the home is displayed over here you see and the home is displayed that means label is taking up the space even when it's empty so what I want to do is make sure that the selected font size is 0 and unselected font size is also zero if both of them are zero it will take lesser space you see and now it works fine it works well and it looks good in my opinion perfect now let's go ahead and design the cart page how do we want the cart page to look like so let's close all the save file we're going to go to the lib folder and create or we already have the card page created we'll just go there and start designing so in our scaffold the first thing that is required is an app bar just saying that hey we are using the cart page so we'll have a title of app Carter now you'll notice in home page that I have a scaffold body index stack and in the body I have again mentioned a scaffold so there's a scaffold inside of a scaffold and that works fine as long as you don't have an app bar now if you create an app bar here let's just create it for now if you have an app but over here it will look quite weird because you have one app bar and then a second app bar so definitely you can put a scaffold inside of a scaffold but it can look weird so anyways now we have the given constraints in which we have to put a scaffold but our constraint is very clear the entire screen except this part you know the bottom navigation bar so our constraint is this entire thing you can say okay so we'll come over here and let's start displaying stuff so to display this uh stuff we can just use a list view Builder directly nothing else just a list you build up because we don't have anything else to mention and here we'll also mention the item count which will be got dot length and this card is coming from Global variables here if you've copied stuff from the link mentioned in the description below you might have also copied this card and this card contains just one item which is the Jordan shoes all right now you can use that Also let's put context index inside of an item Builder now if you're wondering and I didn't answer this before why is there a context we understand why there is an index why is there a context and context is basically available in all Builder related stuff for example if you add future Builder you could have a context there if you just have a builder widget which is a builder it's which is a widget of itself you'll get a context there as well so basically whenever you have Builder you will have a context and if you're wondering what the Builder widget does I'm not talking about listview Builder the Builder widget only it basically just provides a context to you which you can use and it does have a significance of its own it will provide you with the build context that is not same as this context now in the item year what I want is final cart item which will be equal to cart at particular index now what do we return here well it's a very simple choice I just want to return a tile that has one heading one subheading an image of the thing we have in cart and a delete button if I want to remove it from the card so for that particular reason what I'm going to return from here is a widget that you've never seen before and that is the list tile widget so usually whenever you have list view Builder list style goes well because well it has all the necessary properties you might need to return so it has a title that will help you to display a title stuff so let's have a text widget here this accepts a widget and the text can be cart item at title dot to string so we have a title that is good then it also has a subtitle and here also we can pass it a text which will be telling us the size so what number size should the user select so let's say the user selected a size of 8. remember this is just dummy data when we add State Management to the app which is the next step we will be able to dive more into it so we can just have cart item at size that just looks good now if you come over here you'll see Jordan shoes size 8. perfect the only problem I have is the title is not bolded so let's go ahead and bold it out so I'm going to use style property here but I'm not going to mention the normal style I'll go to the main dot dot file and I'm going to copy this body small title that looks good to me so I'll just have theme dot off context Dot text theme dot body small then I'll save it and this is now bolded and it has the same size as 16. no visible difference there after this I want to add an image in the start showing that this is the shoe you've selected so I just want to show that so for that we also have another widget which is or another property which is leading so what leading does is put whatever widget you have in the start so you can use the leading widget here and pass in a circle Avatar and then you pass in the background image which is a property to use on Circle Avatar what Circle Avatar basically does is it gives you a rounded border where you can describe your background color background image foreground image radius minimum radius all of that stuff so here you can pass in a background image and this requires image provider what is our image well it's coming from asset so you can pass in an asset image here you cannot pass in image dot asset because this is a widget image.asset is a widget however asset image isn't a widget asset image is a network or is a image provider if you see here asset image and go into the definition of the source code you'll see asset image extends asset buttonal image provider and it extends an image provider so it's an image provider it's not a widget image dot asset is a widget see here it requires image providers you can pass an asset image and if you're getting stuff from Network or from web you can use Network image so let's go ahead and use asset image and pass in the asset my asset is cart item will go to Global variables and we have image URL so we'll pass in image URL and we'll treat it as a string perfect we save it and we have our shoes showing up now what if I want to increase the size of this Circle that we have Circle Avatar has properties for that as well you can also set the radius property that will help you to change the size of it so let's say the radius is 45 so this is quite big and there you go but I don't want it this big I want it 30 let's say that's fine and if you want to change the background color over here you can change it the yellow color is there just because of the theming we have set in the overall app and the last thing I required here is a delete icon now there are two things you can do away for the delete icon either you can add a button over here that says hey you can remove this item from the card or you can have a swiping gesture saying if you swipe this you can delete the item in the cart or you just long press on it and you can delete it what I'm going to do is add an icon over here that says you can delete stuff this is helpful because the user doesn't have to swipe through or if the user doesn't know that they have to swipe to remove from the cart it's helpful so now you can have a trailing widget here which will be an icon button and on press is required so what should happen if it is removed for now nothing and then icons dot delete okay save it you come over here and you have the delete icon now the delete icon isn't in its original fashion in its original fashion it should be in the red color so let's get it red so we're going to have a const icon icons dot delete and we're also going to press or pass the color which is colors dot red and I'm not setting the theme away I'm generally typing colors.red because no matter what the theme of our app is the delete button has to be red color and we have a delete button cool so we have our cart layout set up as well now the next thing we need to add in our app is State Management so how do we manage the global state in our app we already do that with set state so we are the local state management but what should happen if I click on add to cart and it should show up in the card here I've already explained all the stuff related to State Management and inherited widget which is what flutter uses behind the scenes to have State Management but we are going to take a look at an abstraction over inherited widget why because inherited widget can be a bit cumbersome to write every single time it is quite a big source code to write and yeah if you want to know more about it link is mentioned in the description you should definitely check out the video by the flutter team themselves so now let's dive into the State Management world and we are going to manage a state using provider so for State Management we are going to take help of an external dependency and for that I can go to pub.dev and the package we'll be using is provider this provider package is a wrap around inherited Widget the widget that I explained to you but we did not write and it is a wrapper around inherited widget to make them easier to use and it is more reusable by using provider instead of manually writing inherited widget you get all of these features all right and it's a good thing there are other State Management options you can use as well there's riverpod which is my personal favorite and you can find that in the video I'll mentioned in the description below you can check out my separate tutorial on it and after that I would recommend you to follow with the project of Reddit clone so that you get a proper practical understanding of using riverpod in your apps and another famous library that people like to use is block and there's another package that people like to use in the flutter Community which is get X but I personally do not like it and it is the most liked package on pub.dev so it's the most like package in flutter but I personally do not like using it and you can find my video on why I don't like using it in the description as well so we are not going to take a look at get at all and even block but riverpod you can find in the video description let's go ahead and use provider now how should we use provider so the documentation or usage for it can be found in the yeah but I'm going to tell you how to use it because that's what the aim is right now we can copy this go to pubspect.aml and add it to the dependencies and then save it now I will get rid of it and we'll start all our apps from scratch now provider runs on every machine so it can work on all the platforms you can see it over here so that's fine and at the end of the day it is just a wrapper around inherited widget which basically means like it is built on inherited widget with a slight wrapper which allows you to use it very easily and it is a flood of favorite package so flutter recommends using this however the creator of this package is not the Google team it is the team or it is the person that created the riverpod package as well and he recommends using this package over provider however we are going to use provider because that will give us a clearer insight into inherited widget River pod doesn't do that anyways let's just focus on provider and remove Revo pod out of the picture now here let's add provider so the first thing to do in provider and I told you about this in inherited widget explanation as well that how inherited widget works is it creates a storehouse at the top of a widget or at the top of the widget tree so we can do the same we can go to the main dot dot and we can wrap our material app with something known as a provider widget okay this provide a widget is coming from the provider package and it extends inherited provider inherited provider extends single child stateless widget this extends a stateless widget so this is a widget that you can use and the task of this provider is to store this data and you store this data using the create option wire send create you pass any value it accepts Dynamic value which is basically like hey you can pass anything you want it can be your own custom class you could can be a string so let's go ahead and return a string from here with just saves hello world all right I'm just showing you how to use provider in your apps so you can build or provide value from one place to another so what you've done is at the top of the widget tree you said hey we have a provider and the descending widgets can use this value so whatever value we're returning the descending widgets can use it and if you hover over this it is automatically getting a type of Provider string so whatever value you type over here will be the type of this provider cool now we can go to the cart page let's say now the thing we have to concentrate on is how do I get this value how do I get the value hello world in my cart page well you can do that by printing provider dot of context and here we have to mention a generic type now you already know provider.off context syntax right it is the inherited widget syntax exactly but this also requires a generic type if you mention a generic type it will be able to find the provider so if we have string here and then let's just say we printed you see hello world is written if I restart the app hello world is written how does this work how are we getting the value in my app in the cart Page by not even giving arguments and that is the beauty of provider and inherited widget we mentioned hello world over here so this was a provider of type string then we called provider dot off context so it went up the widget tree trying to find the nearest ancestor to provider dot off string so it searched the type of Provider string all right it went up the widget tree and tried to find a provider which was like this provider string and then when it finally founded it returned the value now what if I have two providers instead of one so I have one provider at the root of the widget tree and let's say I have another which is wrapping the home page all right I have a provider here which wraps the home page and let's say we say hello also this requires a function so let's pass in a function all right cool now if we restart we see Hello written over here hello world is gone now only Hello is returned and that's because provider dot off context is trying to find the nearest widget to it or the nearest widget in the widget tree and the nearest widget is this part over here that's why we get hello we don't get hello and hello world both because once it finds the particular provider it will stop looking for any more providers it's done so it doesn't look any further it will give the value given by this hello perfect so now that we have used provider I want to tell you that there are multiple types of providers there are providers like provider we've already seen this then we have changed Notifier provider then we have a future provider and then we have a stream provider so these are the four main types of providers that you can use in your app provider we have already seen is a read-only value so you can just provide one value and it will only read it will do nothing else then there's change nodifier provider with this provider you can change the values and notify the widgets that are listening to it about those changes this is the provider we want in our shopping app then we have future provider so future provider is there so that it can listen to Futures subscribe to them and show the changes and stream provider is basically providing a stream future and stream providers are useful because provider helps in lazy loading right so it can help over there and that is a good thing however we'll be only focusing on change Notifier Provider from now so instead of returning a provider which is a read-only value we don't need that anymore we're going to return a change nodifier provider but if I just do change Notifier provider it's not enough we need to provide a generic type of air and a generic type as let's say string but string doesn't conform to the boundary of change node file basically whenever you have change Notifier provider and you have a create function you cannot pass in a string or anything you need to pass in something known as a change in node of fire okay and what is this change Notifier it is a simple class in the flutter SDK which we can use so it's coming from flutter not from provider and what this does is provides change notification to whatever is listening to it so if any updates are made or anything is done it will notify the widgets listening to it and will rebuild those changes but now we cannot just use change Notifier like this we have to use it a little bit differently what we need to do is create our own separate class so let's call our provider as cart provider.dot then we are going to have class card provider I always like to have anything related to provider using cart provider so it's clear for me to know if it's a provider or not then we have to extend this with change node F5 all right as soon as you extend change Notifier you can take this class and return it over here so you can return card provider over here now this card provider is accessible throughout your entire app so whatever you define over here can be used outside of this class in the home page in the cart page anywhere in your app and that's a plus right so this just tells us that if I click on add to cart and I store it in cart provider then I'll be able to see it in the card screen if I use the same card provider and that's exactly what we are going to do this card provider is a storehouse right at the top so here I'm going to create a variable called this final map string comma Dynamic cart and that is equal to an empty list but here a value of type less Dynamic cannot be assigned to a variable of type map string dynamic it's basically saying that hey your card is a map of string comma Dynamic how are you assigning to this to a list and that's true my card cannot be just a map if it's just a map I'll be able to store one single product I want to store multiple products so I need to have a list okay now that I have a list I can create two functions add product and remove product so I'm going to have remove product so two functions are present in cart provider which we can use so in add product we are going to get one product which we need to add to our cart so I can have map string comma Dynamic product then I'm going to do cart dot add product simple now the same thing is going to happen in the remove product as well I'm going to get a product here and then I'm going to do cart dot remove product so this way my card provider is up and ready as simple as that since the instance of this class is accessible throughout our entire app I can go to one particular page and where I want to go to is product Details page I hope you understood what happened in card provider I created a class extended it using change Notifier so that I could use it in main.dot in the card provider over here and then what I did is ADD product added it to the cart list remove product those are just functions and now whenever this add to card button is clicked on I'm going to call this particular function okay so let's go ahead and do it so I'm going to go to the product Details page then I'm going to go to the elevated button on pressed and here I'm going to have provider dot of context and here I need to mention the type what is the type of my provider now if you want to take a look at it you can come over here and the type of provider is cart provider you can use that so you'll have provider.off cart provider Dot and you have the option to add a product now I'm just going to click on ADD product and then I will mention my map what is my map well it's this thing product but you see I can't access product over here and I can't access it because I'm in a stateful widget whenever I'm in a stateful widget I am unable to access this product then how did we do it earlier widget.parada but we didn't write widget dot product right flutter did it for ourselves so when we add stateless to stateful widget conversion we wrote widget it automatically converted product to widget dot product because we are in a separate class of ourselves right how do we access element of this class we cannot do that that's why state has created a widget property or a widget getter for us which we can use to access Constructor arguments or whatever we want to do and that's how we get access to widget dot product so I can add the product like this and now just to see if it is working I'll press command J I'll restart my entire app and I'm getting an error I am getting an error saying the following provider not found exception was thrown building card page so the error is in card page and the error here is that provider.off string context was called and there's no provider which returns a string for us in the entire widget tree we had it but we removed it and replaced it with cart provider so this no longer exists that's why we get provider not found exception so when a provider doesn't exist in your direct widget tree that's when you get provider not found exception so let's remove or not remove Provider from here we are going to print provider dot off context cart provider Dot card so we're going to print this thing out and now I'm going to restart my app I see an empty list I come over here I click on add to cart and I get an arrow the error says that I tried to listen to a value exposed with Provider from outside of the widget tree now this error basically occurred and you can see the reason below this is likely caused by an event handler like a buttons on press that called provider dot off without passing listen false basically whenever you use provider dot off context you always have to listen to stuff you're just saying that hey I'm subscribed to cart provider now any changes made to cart providers any of the services I want to subscribe to them I want to listen to all of those changes that's what change Notifier also does when you extend to a change Notifier it will notify all the widgets that are listening to it about its state change yeah what happened is you're saying provider.off card provider context so you're basically saying that hey I want to listen to card provider but then you're calling add product function on it so you're not really listening you're just calling a function so whenever you're calling a function beside the context you also need to provide one thing which is listen and set it to false by default listen is set to true in our cart page the listen is set to true all right but here you're saying listen is false and then add product and listen should be false every time you use this function out of the build function all right whenever you use provider dot off card provider context out of the build function listen should be set to false and if you're in on pressed it is basically out of the build function because you can take this on pressed and put it like this void on tap like this right so you're now out of the build function and then you can pass on Tab so now you're out of the build function and it still works fine now you might raise a question hey how are we using build context when we are out of the build function build context is there only over here how can you use it over here I can use it over here thanks to the state class that we are extending this date class also gives us access to the build context and this build context that the state provides and this build context is the exact same thing it is the exact same element so you can use it wherever you want but yeah in a stateless Widget the context is not given because this context is given by the state class it is not given by state full widget so stateless widget cannot give that only state can and obviously in a stateless widget we do not extend state great so now that we are in a function outside of the build function we are using listen false and anytime you want to call a function from card provider you have to set listen to false if you said listen to true you're basically saying that hey I'm in the widget tree I want to continuously listen to the changes and that's definitely not the case over here anyways now that we have understood this we'll restart the app we'll come over here we'll add to cart let's open the terminal nothing shows up and there's still an empty list if I add to cart again still nothing works if I go back come here let's say add to cart still nothing works so why is this not working well this is not working because whenever you use change Notifier or extend change Notifier it doesn't do anything automatically it only notifies the widgets listening to it when you call a particular function which is notify listeners and this function is given by change Notifier itself so you extend change Notifier and you see it is a mixing class so you can also do card provider with change notify or extends to notify same thing and as soon as you do notify listeners and restart your entire app come to men's Nike shoes add to cart command J and now you see automatically you have access to the changes made over here and this data is coming from the cart page so you update it one place and the data is stored in some other place that's the cool thing right now in the card provider we are going to do the same thing for notify listeners of a remove product so when you remove a product you can have notify listeners like this so notify listeners just notifies all the things that are listening to this card provider sweet now the problem I have right now is I cannot display the data that is coming from this cart that's because sizes is giving me a list and it's just giving me a product what I want is something like this I want ID title price image URL company all written over here but I also want size since I want size over here I'll have to modify this widget.product a little bit so how are we going to do this well we can have something like this so what I'm going to do is copy this this is the layout in which I want my product or my cart product then I can have it like this then I mentioned the ID so the ID is widget dot product at ID and the same thing for literally every single thing we have widget dot product title widget dot product then we have price then we have widget dot product image URL and do that for everything all right so you have image URL here and finally widget product for the company sweet and the size here is going to be the selected size also you can add an if condition over here what if the user does not select a size what do we want to do in that case well first of all I don't want to update my cart otherwise it will come like selected size is 0. and that's a wrong thing because a shoe cannot have a size of zero so I'll just have if selected size is equal to 0 then I want to do something else so I'll just have a reverse condition if selected size is not equal to 0 then I'm just going to paste it over here so if selected size is not zero it is something else and that has to be from some selected size we have decided then we can go ahead so now we restart come over here let's say I add to cart nothing gets added to the cart and this is kind of like a bad user feedback you can say because what's happening here is you add to cart the user doesn't really know that they have to select a size maybe they forgot to do that so you have to tell the users that hey you need to select a size so here in the else condition you can tell the users that and here I want to basically show a thing popping up from below saying that hey you need to select a size so for that we have something known as scaffold messenger not scaffold scaffoldmessenger dot off context again this is using inherited widget behind the scenes and I'll explain why Dot and this has multiple things like show material Banner remove current snack bar all of that what we want is show snack bar and this requires something known as snack bar so let's pass it in then snack bar requires content so let's pass the content which will be a text because content requires a widget and then you say please select a size okay and then we are going to put a cons for the snack bar and once we come over here let's go back come over here add to cart you see please select a size so this is our scaffold messenger showing up why does this use a narrated widget because it wants to show the snack bar on one particular screen and here it is just contacting the messenger of a scaffold all right earlier this was known as scaffold.off context but then it caused some problems with build context and cause problems like build context not found that's why this was renamed to scaffold messenger so what happens is it's it Finds Its nearest scaffold now it Finds Its nearest scaffold messenger and shows a snack bar on that particular scaffold and what is the snack bar snack bar is a thing that shows up from the billow giving us an impression that hey you need to do something okay so now if I select a size add to cart it will be added to card but I still have no clue that it was added to my cart so what I can add here is again a scaffold messenger and a snack bar saying product added successfully save it then you again select some other product let's say this then you have product added successfully you go back come over here and you won't be able to see the changes because our card does not depend on it but the changes are reflected over here now let's go ahead and make the changes over here in our cart page now whenever you want to continuously listen to something in relation to a provider we have to do that in the build context otherwise lesson will be set to false and we won't be able to listen to anything so let's save our final card is this thing over here then we'll remove Global variables and as thing is done so the item count is card dot length cart item is cart at index and now it's safe to say that we can remove cart from our app the dummy data still needs to be there now we can close all the save files we are going to restart our app all the data is now gone because the provider doesn't store data permanently in our storage it only stores it temporarily as long as the app is running after you restart or reset the app it is all gone so let's go ahead and select 11 size then we'll go to Adidas shoes We'll add a 10 size then we'll add a Jordan shoes and add eight size then we come to the cart and we see three things men's Nike shoes size 11 10 8 and all the proper images are showing up perfect the last thing I want to work on is this delete product so whenever I delete something from your it should remove it from my card but even before doing that I want a confirmation I want my app to ask them are you sure you want to remove this product if you're sure only then we'll remove it for you we already have the remove product function ready all we need to do is put up a dialog box what we want is whenever we click on this particular button it should show up a dialog box right in the center saying delete choose or delete from delete product are you sure you want to remove products from cart and then you have two options no yes so this is what you want to do let's go ahead and do that really quickly so in card page Whenever there is on pressed you can have something known as show dialog this show dialog is a function given by flutter that will allow you to display UI it will allow you to show a dialogue on the screen and then it has a builder so you get a context and you can use that context to display stuff now this Builder requires you to return a widget from this function of build context that it's giving now what do we want to return well I just want to return a dialogue let's say if I have a dialog will that work well let's go ahead and try it out you see when I click over here the screen does get blurred that's because of our dialogue now I'll pass a child here and the child is let's say text and we say are you sure then become aware we select we see a dialogue saying are you sure so you can set it up for yourself you know you can design dialogues on your own I have that much faith in you at the end of the day we are returning a widget so you can use container padding column all of your creativity to return a particular dialogue but if you don't want to do all of this there is a built-in widget called alert dialog which you can use and I like to use it for this kind of stuff this basically tells you to show an alert dialogue that hey you're doing something that is a bit risky not exactly risky in this case you're just removing a product from your cart but it just verifies that hey you're doing this so let's go ahead and set it up it requires a title which is exactly what we want so we are going to have delete product as the title now when we click over here delete product is the title and you see that this is quite big I don't want it this big and the reason it's big is because the title has a style it is inheriting from we can override that by having theme dot off context Dot text theme Dot let's say body medium save it the app delete product this doesn't look very good so I'm going to go with something large which is title large let's say now if I click over here this is quite big maybe we want title medium and this looks good enough so we have delete product as the main title after that we need something like a subtitle and there's nothing like a subtitle but we do have content so what is our content well very simply it is a text saying are you sure you want to remove the product from your cart okay this is my content this is my text widget just asking it are you sure you want to do this because this is an alert dialogue it just asks for your confirmation now if I click over here we see this this is looking good the last thing I want here is a no and a yes button so that the users can select accordingly and for that we have something given by alert dialog which is actions actions is the same thing that is available on the app bar as well which you can use to add action related stuff things that you want to mention over here and the same thing is here as well if you want to mention something so I want two things over here two text buttons basically the first vertex button is going to be a text saying no also this will be a constant text no and then there's going to be another text button which is going to be yes all right now if we click over here we don't see the buttons but they are there no and yes now we just have to change their design so for this we'll have to set up the style and everything so let's go ahead and pass the style as text button or actually we don't need to do this we can just mention the style over here for the text textile now what is the color of no going to be well I just want it to be colors.blue because no is a safer option and the other option Also let's put fontway dot boldier and the other option which I'm going to copy paste is yes and that is going to be colors.red now if you click over here yes is there no is there you can select either of them you can set more properties on this show dialog basically like if you want to disallow the user from clicking outside right now if I click outside of the dialog I can still exit but if you want to make sure the users can avoid that you can set barrier dismissable to false once you do that the users won't be allowed to click outside and exited like this I can't exert it even though I'm clicking but anyways I like this better so I'm going to keep it and now I can't exit it so I'm just going to restart my app then add some shoes come over here and we have men's Nike shoes size 11 and size 12 properly there now in the know what I want to do is whenever the user clicks on no I just want this dialog to go away and do nothing just this dialogue should go away so to make this dialogue go away I can use Navigator dot off context dot pop once I do this and click on no it just removes the dialogue nothing else because what this dialog does is it Stacks it it Stacks it at the top of the screen so navigator.off context dot pop will just remove it after this we have yes in yes what do we have to do well I just want to call provider dot of context then again I have to access cart provider then lesson should be set to false don't forget that dot remove product and what is the product I want to remove the product is mentioned over here it is the cart item so you can just mention the cart item and done now if you want to remove Adidas shoes you can click on yes and Adidas shoes gets removed but the dialogue isn't popped off we still have to call navigator.off context dot pop to remove this thing so let's click on know now we have delete button yes and it will clear off the card for us now we can go ahead and set things up let's say 10 9 and now if I come over here yeah size 10 size 9 and I can remove anything I want and it works fine so this was what I wanted to talk about State Management with provider provider has its flaws for sure but this is very close to inherited widget which is why I wanted to take this up now there are some things you can modify here first of all this is a big line to ride isn't it so what you can do is final card is equal to context dot watch as soon as you do context.watch provider gets triggered then you have to use the cart provider and there you go you now have an instance of cart provider with you now you just have to call the cart and it will work just as intended so we have context dot watch here instead of provider.off card provider context Dot card so this is a shorthand Syntax for the same thing it will work just as expected you can try it for yourself and here whenever we have a function called what we need to do is context dot read you can't use context.watch because lesson Falls means read it isn't watch watch is basically like your continuously seeing read is you just read it once and leave it so again you need to mention cart provider over here and then you can have dot remove product and pass in the particular card either and you can make these changes everywhere in your app it is just a shorthand Syntax for it it is a function which basically does provide a DOT off context this listen false and I think this is an extension yeah this is an extension on build context provided by flutter so yeah you can you do this to simplify your life and that works great looks great perfect now you can make these changes all around your app and this is how it is done so yeah we are done with State Management with provider in our shopping app one last thing I'd like to mention before closing the State Management chapter with provider if you want to return multiple providers in a bigger application what you can do and I'm going to remove this comment is return multi-provider with multi-provider you can return a list of providers and there you can mention your change Notifier provider where you pass in a context and return card provider as simple as that so if you have multiple providers you can pass it in multi-provider otherwise change Notifier provider or just provider is fine but most of the times in bigger apps you will be using multi-provider only because you will have multiple providers there's a lot less boilerplate code to write when using provider as it is a wrapper around inherited widget a widget provided by flutter itself to pass data between other widgets using provider we can separate business logic from UI making our code much easier to test and maintain in this tutorial we will go through different type of providers and understand when to use what type of Provider first one is provider itself as the name suggests provider provides data to visits below it in the widget tree to demonstrate this I'll wrap the root of my widget tree with provider this acts like a storehouse for data wait a minute which data whatever we pass in the create argument it can be string Boolean and even instance of a class to read this data in a widget we can use provider dot off then the type of the data we return followed by context what happens behind the scenes is it goes up the widget Tree finds the provider widget closest with the type we return and spits out the data that's stored we can see the data correctly when we display it on the screen as well if you find the syntax really long you can use context.watch followed by the type of provider and it will work the same way provider is a read-only widget which means it cannot modify the value initially passed to it so how do we modify the values with the help of change nodifier provider instead of Provider we will pass in chain Notifier provider and in the create argument pass in a data model to create a data model we will create a Class instantiate A Private variable create a getter and a function that increments the variable's value by 1. to make this work properly with change nodifier provider extend the class with chain Notifier which provides us with notify listeners function whenever this function is called it notifies chain nodifier provider and widgets listening to it are rebuilt if you don't use notify listeners the UI of the app won't get affected even though the data in our case counter variables value changes also note that more functions like decrement and reset can be added in the model class itself getting data is same for all providers we just need to specify the type of Provider properly since we have counter return in chain Notifier provider we will replace string with counter but as you can see this returns instance of the counter class so we will use counter getter we created in this class to see the count now to implement the increment function we can use this line why let's break it down provider dot off counter context will return to us the instance of the counter class on this instance we are calling increment function inside of which we call notify listeners and this will rebuild this widget since we are listening to it but what if I don't want to listen meaning I don't want the widget to rebuild so I can set listen to false for a shorter syntax we can use context dot read it's worth noting that context.read cannot be called inside build function on the other hand context.watch cannot be called outside of build function another thing to note is context.watch should generally be used when every part of the widget needs that value because it makes the entire widget rebuilt for example when I click on the increment button only the counter needs to rebuild but in reality even the text and floating action button rebuilt this might not seem like a big difference but what if you're building Twitter like app I and to update the number of likes you're rebuilding the whole postcard to prevent this unnecessary widget rebuild wrap the counter text with consumer widget which will make only the widget returning from it rebuild give consumer the return data type and to get the data we can use instance of return data type provided to us don't forget to remove your context.watch calls otherwise it will still rebuild the entire widget next type of provider is stream Provider from the name itself we know that it will help us manage stream data it is like stream Builder but with lesser boilerplate instead of chain Notifier wrap my app with stream provider in the create argument pass in a stream like this in our case it will output 0 to 9 with a gap of 1 second after each number initial data argument is also required it is the data to be displayed until the above stream gives us a value to read this go down to the consumer replace counter within which is the data type we are returning from stream provider and remove dot counter it works proper only if you restart the app equivalent of consumer in this case will be the following future provider is similar to stream provider it too accepts initial data and create arguments and works the same way so I'm not going to rewrite the whole thing but basic difference is future provider returns a value after the future is completed now we know about most of the essential providers but here comes a problem what if I want to use both stream provider and change Notifier provided together in the application we can do something like this right wrap my app with provider pass data and create and in the child change Notifier provider likewise we can do for hundreds of providers in a vast app right no why use this nesting hell when only a single provider can help us which is multi-provider it accepts list of providers in the argument and that's it that's how easy it is to add multiple providers in our application now the last provider we're going to look at is proxy provider when one of our provider depends on value returned from another provider we use proxy provider to demonstrate this I'll create another class in our code called second class and accept instance of Firebase odds from Constructor here we can create any method that we want I'll just keep it empty now I want to provide this class so I'll go into the multi-provider where Firebase auth is already provided to access this Firebase auth instance I will use proxy provider the syntax is like this proxy provider and unlike other providers we pass two types independent class and the dependent class then we need to pass update argument which gives us context followed by instance of the independent and dependent classes we will return the class from this function passing auth as the argument this will make a provider work but what if the class doesn't need one but two three even four instances we will use proxy provider 2 3 4 and so on for it and that's pretty much it the next thing I want to do is focus on responsive UI by responsive UI I mean the device or our app should look good on all screen sizes and that includes Chrome Mac OS Apple Android all of them it should look good on all the screen sizes so right now our app looks good on IOS and Android and that's cool but now I'm going to switch to Chrome and I'm going to run it on Chrome to see how it looks on a bigger screen size all right so let's launch it and while that is happening I also want to restructure the folder structure now you see there are many components in our lib folder so obviously we need to segregate things we need to put all the pages in one particular page we want to put providers in one provider and we need to do all of those tasks so let's go ahead and do it in the lab we are going to go ahead and create a Pages folder then I'm going to take cart page drag it in pages then I'll may let extension dot make the changes and save those changes then I'll put home page as well then we are done with that let's save it after that we need another folder and we are going to name it widgets this is going to contain small widgets not exactly pages but smaller widgets so we'll pass in the product card let's move it in and let's save the changes and one thing I forgot to do was put product Details page in pages so let's put it there save it and then the last thing is I think provide a product list and product list also goes in the pages so we have widgets and pages so this is good for a smaller application then in the lib folder I'm also going to create providers and as our app skills we are going to have more providers right so we are going to create a separate providers where all the providers are going to stay like cart provider also save those changes if you don't save it it will give error in your app so we have Pages provider widgets and Global variables can stay here or you can create a utils folder and save it in utility but I don't like to do that utility includes some other things not exactly Global variables Global variables can be constants or something else all right so we have a cleaner folder structure here the purpose of a clean folder structure is that you can just have your apps layout very nicely and more Engineers working on it will be a better thing all right and even the Chrome is now set up so if you come over here and expand the app there is Chrome and this looks decent enough not bad not good if we come to the product list over here we are getting an error and this error is there because it wasn't able to find something we just need to restart because this happened when we were changing the folders right now if you come over here the error is gone perfect so what are the changes we need to make well the first change as you can see in the details men's Nike shoes this shoe image is quite big I want to reduce the shoe image size and that's not just for one shoe even this shoe is quite big so let's go to the product Details page and scroll down we'll find our image.asset and as you can see this error is there because we haven't set a particular height for it and what should the height be well let's go ahead and see it the height should be 250 let's say if we do that come over here this shows up nicely and if we go to the iOS device over here and we click on it we have 250 showing up this looks cool it works on both the screen sizes let's click over here and yeah this looks cool I'm fine with it also if you right click on Chrome click on inspect you'll be clicking on this icon over here to toggle device toolbar and now you can check for the responsive design from here itself right and as you can see when we increase the font size the maximum height it takes is what we've mentioned over here 250 and when we shrink the size the image height keeps on decreasing so that's a good thing for us right even for our button if you see that's the case the button keeps on increasing and it takes the entire width of the screen with the padding there now I don't want this what I want is the button to only be there only this much just like our shoe all right so it shouldn't be this big because it looks kind of weird doesn't it so we can scroll down to our button and here you see we have set up the minimum size how this works is it the minimum size it can take is double dot infinity and then we've wrapped it with padding so they're spacing over here however what we can see here is maximum size can be this much then when we click you see this is quite small because the maximum size it can take is this so we have set up a constraint over here that maximum size is this much minimum size can be whatever you have the child as how much ever size the child requires and same happens over here although I'm pleased with the result this is not what we want so we are going to use fixed size over here because maximum size gives us a very small result minimum size gives us a very big result fixed size will give us exactly what we want so instead of passing in double dot Infinity I'll pass 250 this is good enough and if I pass 350 Come Away you see this looks good enough the problem then comes on the pixel emulator all right if we just open it and take a look if it looks good enough let's run it without debugging if it works well on the pixel emulator then we're fine with that it all looks good but if it doesn't then something needs to change and we have the pixel emulator if I click on a product add to cart is there and it's similar to this thing over here perfect I like it this way so this works well on the screens on all the screens in fact so we are done with the product details screen the selecting part is still the same we can add to cart we can go back come to the shopping cart and we'll see our product and here if I click on delete delete product everything looks good it's all good in my opinion you know the dialog takes only this much space which is what I want then this is the size that I want I only wanted this much so everything looks good over here but the problem I have right now is this card over here this card takes in a lot of width and this width is fine over here this width is completely perfect but over here it's taking in a lot of width what I want to do instead is if we exceed a certain screen size or screen width let's inspect the tab and come over here so if I reach let's say this much height let's say this much height then I automatically want to show double cards so I want two cards to be displaying on the single screen and when we are less than that particular dimension I want only one card to display so it depends on what the screen size is again just to tell you if I expand this I want two cards but when I have it minimized like it's in a phone mode I want it this long I only want one card to be present otherwise two cards so how can I make this happen that's where we have another widget in place frada gives it to us what is that if we just come to the home page and in the home page we have to go to the product list in the list view Builder now this list view Builder this list view Builder is for filters and filters look great this is the thing I'm worried about this list view Builder over here now instead of returning one list over here I'm going to have grids and it depends on the screen size right so how do I calculate the device width so for that particular reason we have final size which is equal to Media query this media query gives us a lot of things it will give us what platform we are on what is our screen height what is our screen size what is our screen width what mode are we on so like if the phone is in a straight mode or if it is in a horizontal mode like this it will give us all of that data so it's pretty helpful for us yes you can click over here to change the mode of the app or the mode of the phone if it's portrait mode or horizontal mode whatever so media query gives us access to all of that so what I want is mediaquery dot off context dot size you can see over here it gives us a lot many more things like view padding View and such platform brightness and you can look at all the things it gives us but what I want is size why because size will give me the perfect size and then it will give me the size of the media and logical pixels example the size of the screen that's what I want and also you'll see over media query dot off context and if you see over here for the media query itself it extends something known as inherited model not inherited widget a narrated model is kind of like inherited widget but there is a slight difference we are going to talk about let me just tell you how this works how we can make two cards appear on a bigger screen and only one card on a smaller screen and then we can talk about the difference between inherited model and inherited widget and how it affects us so we'll scroll down and here where our list view Builder is there expanded is there in the child so first of all let me make it clear that whenever we want to display two items in kind of like a grid what we use is grid view Builder so just like list view Builder there's grid view Builder and obviously there is grid view as well which you can use but great view Builder is used when you don't know the number of items the grid is going to have in our case products dot length is the number of items in Grid View and list view both as of right now we know what the products length is but if we make database connections and we dynamically get it from the database we won't know how many products are there just think of Amazon does Amazon know how many products there are they are like billion products they can't possibly know how many exact items or products are there that's why there is item Builder and grid view Builder widgets so we are going to use grid view Builder and just to give you a demonstration I'm going to comment this out I'm only going to have expanded again because this behaves similar to listview Builder it will take in the entire height of the screen but it doesn't have the entire height so we have to wrap it with expanded then we are going to have grid view Builder this requires grid delegate and then it requires sliver grid delegate this grid delegate controls the layout of the children so this will tell it how many items we want in a row how many items should have how much spacing so all of that configurations can be made with sliver grid delegate so let's type it out sliver grid delegate but then it is an abstract class abstract classes are made so that we can use their subtypes which follows a particular attribute for example get layout and should lay a relay out should be followed by every class that extends or implements sliver grid delegate that's why abstract classes are made and your abstract classes are allowed here I can pass in anything sliver grid delegate related for example sliver grid delegate with fixed cross access count sliver grid delegate with fixed with Max cross access counts level Grid delegate with fixed cross access so all of that is present aware what we want is sliver grid delegate with fixed cross access car here we get an error but this error is not because this is an abstract class this isn't this is a normal class but it requires a named argument but before jumping into that let's format it and understand what this means sliver grid delegate with fixed cross access count we know what sliver grid delegate is it's this thing that it requires to control the layout of our children in the grid view Builder obviously with fixed cross access count basically means how many items you want in one row in the product list or in the grid view Builder and how many do we want to display in one particular row I want to display let's say two widgets at the most so here we have to pass in a required argument of cross access count which will be 2. now consider grid view as a column right all the widgets are going to be one below another so consider it a column by passing in Cross access you're basically mentioning everything in a row format that's what column does right when you pass in Cross access alignment you pass in the alignment in horizontal Direction that's what we are doing here so let's put Constable here then we are going to have context index just like we had with list View and then we want the exact same thing that we had over here so let's go ahead and uncomment this we can copy this gesture detector and return it over here then again we can comment the list view Builder I only uncommented because I wanted to copy stuff now it requires product what is the product well first of all we have to mention the item count even grid view Builder has the same thing item count so let's go ahead pass in products dot length and product is going to be final product is equal to products at index grade all the errors are now gone the warning is up there over here and it's there because of the size variable that we've never used we're going to use it in just a moment after we understand how grid view Builder works now let's restart become aware and we see two products displaying in a grid format perfect now if you come over here we have the same thing displaying but this error here is Justified because it just looks so awful on a mobile screen however this looks cool enough over here right two products and this looks better however we have a problem over here we are going to fix that problem but first of all we just want to configure the layout such that on smaller screen sizes we use a list view Builder otherwise a grid view Builder so it's very simple we just want to get the device size and that device size should not exceed 600 or 650 which is what the normal devices size is and then accordingly we can display a grid view Builder so basically we want to check if the device width is greater than 650 if it is greater than 6 with 50 that means we want a grid view Builder because it's a bigger screen size however if we are less than 650 screen width then we want to display a list view Builder because it's a smaller screen size so we can take the size then we can uncomment this line and then have our if condition laid out what is the rift condition it's a ternary operator we are just going to have size dot width so with size dot width I get access to the device width this is not the width of any widget or any constraints it doesn't follow any constraints of padding or whatever it just gives us the entire device width so here I'm just checking if size dot width is greater than 650 then I want list view Builder or grid view Builder sorry so I'll copy grid viewbuilder cut it also remove expanded from here because expanded is already there at the top and then we are going to have grid view Builder like this otherwise we are going to display a list view Builder so if size dot width is greater than 650 we show a grid view Builder otherwise a list view Builder works so a grid view Builder is still shown here however a list view Builder is shown here that's perfect exactly what I wanted so this is where media query can help us media query can also help us to size the widgets according to what we want if we want this widget size to be bigger it can be bigger if we want it to be smaller it can be smaller now let's come over here and try to fix this device height why are we getting such a big device height over here so why is this thing over here exceeding to understand that we must first analyze on a smaller screen on a smaller screen this looks good it's perfect exactly the way I wanted it so there's definitely no issue in the product card otherwise you might think hey product card is taking too much height no we have not explicitly set any height for our product card for our container and that's how it should be first you should never mention the height you should always try to use flexible expanded all of those widgets whenever you're using you shouldn't specifically go ahead and type hey I want to use this height when things become uncontrollable by expanded double dot Infinity all of those stuff then you need to explicitly mention a height just like we did with the add to cart button I'll summarize this at the end but as of right now no we are not going to change the height in the product card because it's all good it is taking as much height as it should on a list view Builder but it's not doing the same on grid view Builder so there's a problem with grid view Builder and what is the problem you can Google it but if I have to tell you the problem is this child aspect ratio over here the child aspect ratio is the ratio of may cross axis extend to mean access extent and that is one meaning cross access extent is this big then main access extent should also be this big they should have a ratio of one so cross axis extend divided by main axis extent should be one that means both should be the same value and that's why it's exceeding but in our case we don't want that if both have the same height and width that means it is a square and clearly we don't have a square over here it's a rectangle so we can edit the value here and set child aspect ratio to let's say 1.5 save it and you see it becomes shorter but still not enough I still want it shorter so maybe I can go till 1.75 and you might be satisfied with it but I'm not I can say child aspect ratio to True 2 and this looks good in my opinion it looks brilliant so I hope you understood it we made it such that the main such that the cross access extent is double the size or extent of main access extent just think about it child aspect ratio is equal to cross axis upon main axis if cross axis is 100 then 100 divided by 50 will give us 2. so cross axis is double the extent of main axis so on Cross access you see it's this big it's this big it's double the extent of this mean axis all right so we have fixed the error wire and this looks much better and it does feel like a web app which is perfectly laid out so yeah we have this and everything about it looks good so I'm satisfied with what we have over here in terms of responsive design so this was about the media query and the power of media query media query should always be used whenever you want to get the size of the screen the device with or device height of the screen and to talk about the difference between inherited model and inherited widget by extending inherited model you can listen to one particular property all right so in inherited widget let's say media query dot off context is called and let's say the value of device pixel ratio changed let's just assume okay the value of device pixel ratio changed but in our app we are using mediaquery.off context dot size so in reality the value of device pixel ratio changed but this will still get called the build function will still rebuild because that's what inherited model or inherited widget do whenever there's a change they will rebuild the entire build build function and if they do that unnecessarily my widgets are getting called so this is what happens in inherited widget you can't listen to one particular property in inherited widget your in general listening to any changes in media dot media query dot off context and then you're just saying that give me the size it's fine but if device pixel ratio changes this build function will get rebuilt for no reason at all because the size didn't change the pixel device ratio changed so this is just an example I'm not saying pixel device ratio will change and that will happen no nothing like that will happen but I'm just telling you and if condition or an edge case that can happen and this happens in inherited widget with inherited model what you can do is Media query dot size of context or you can do media query Dot device pixel ratio of context with this what you've done is you're just listening to one particular property you're just listening to the size changes of the device you're not listening to anything else at all you're not listening to the changes in device pixel ratio you're not changing you're not listening to changes in some other property in media query you're just listening to the changes in size so this is what inherited model does inherited model will help you select one feature to listen to or one property to listen to inherited widget listens to everything entire class all right so that was the difference and here I am using size of context because I only want to listen to the size cool now if I restart it will look the same thing so now that we've talked about media query I also want to cover One widget which is very helpful and I use it all the time when I want to make my layouts and that is the layout Builder widget so I'll remove media query from here because it's different from media query but in this case it is going to replace media query so let's comment this thing out okay and what is this layout Builder widget so first I'm just going to type the code out then I'll explain what this layout Builder widget does so for layout Builder widget I'm just going to have layout Builder like this Builder which will give me context and something known as box constraints all right now we'll figure out what this box constraints is what this box constraints is is it gives us a bunch of constraints which we need to follow to lay out our app so if I just print stuff constraints Dot and let's say Max height which is the main thing then we have Max width then we have minimum height and minimum width all right and then we are going to return a text from here let's say and that just says hello so nothing to fancy here and we see a hello nothing else a very simple text is returned and you might think there is no purpose of layout Builder but when you open the terminal you'll see constraints dot Max height over here is infinity constraints dot Max height again I don't know why we haven't changed it we want maximum width then minimum height and minimum width all right now we can restart again and we see over here Max height is infinity Max width is 1440 and minimum height and minimum width is zero what is this giving us well layout Builder gives us the constraints in which it is for example a certain widget might impose some constraint on us right let's say layout Builder is wrapped with a widget which is size box and has a height of 100 width of 200 let's save it we restart the app here you see the constraints have changed now the max height is 100 Max width is 200 minimum height is 100 and minimum width is 200 meaning minimum and maximum width is 200 what we have specified over here and maximum and minimum height is 100 what we have specified over here so what layout Builder does is it gets its constraints from the parent widgets so whatever which constrains the parent widgets give it it has those in its mind and it will tell us about those constraints that's why earlier when we didn't have any constraint at all it gave us Infinity because it can take how much ever space it requires then we add maximum width the maximum width would be the width of this device and it is one four four zero you can check it for M1 Max and then the minimum I hit and minimum width can be zero so you can make sure that your widget returned from your can be of heightened with zero or it can be any height or a width till 1440 so it gives you certain set of constraints According to which you need to follow so that's what layout Builder does it cares about what restrictions are put on it what constraints the container size box padding widget give to it so here we are just going to take this constraints to know what is the height and the width all right so we are just going to have if constraints dot maximum width is greater than 650 so since it is a builder it is a function at the end of the day we want to return a widget but I'm putting an if condition over here and since this is a function I can put an if condition like this if we were in UI I would put if condition like this and there would be no braces all right but we are not in UI we are in a build of function and in function I have to put a curly bracket because that's what dot requires anyways if the constraints.max width is greater than 650 then I want to show a grid view Builder so let's return grid view Builder make sure to return it and as you can see when I save it it doesn't format it automatically the code formatting doesn't work because there's an error and this error is there because we have one if condition in place so if constraints.max width is greater than 650 then we return a grid view Builder okay but what if it is not greater than 650 like our iPhone what should we do in that case then we will have an else condition and there we are going to return a list view Builder so let's copy this then we are going to return a list view Builder sweet Also let's Pro remove one pattern thesis make sure everything is correct over here let's restart the apps on iPhone Chrome and everything and we see an error over here and the same error over here that error is there because render viewport and we have some boxing related problems so basically what we need to do is remove the expanded from grid view Builder and we've already removed the expanded from list view Builder then we are going to wrap the widget with expanded right now if we save it everything shows up correctly and even here everything shows up correctly so expanded says take as much space and width as you require so here if we try to print constraints dot Max height and if we try to print constraints dot Max width we should be seeing a value let's restart we see 535 and 430 for iPhone and when we go to Chrome and restart we see 570. now the max height instead of infinity it is 570 because that's how much space it is getting because that's what expanded does right I hope you got a better understanding of it through layout Builder and as the name suggests it helps you to build layouts and the max width doesn't change because there is no constraint or there's nothing over here however Max height did change so yeah we just need to wrap expanded to layout Builder then we return a grid view Builder without expanded because expanded is there for our layout Builder we are getting the constraints properly now and the same goes for listview build up you're getting our constraints properly set up so this is layout Builder now you might ask what is the difference between media query and layout Builder the difference is Media query takes the entire device with and the entire device size no matter what the restrictions on the widget are but layout Builder takes width and height based on the restrictions imposed by the parent widgets on it and that's why I'll likely out build a better because you always want to build your widgets based on what the parent gives you whatever sizing the parent will give you you need to follow that if media query doesn't obey that then it's a problem but if layout Builder is telling you some constraints it it's because of the parent constraints and we need to follow that for example if I come over here add to cart button let's say has some restrictions imposed by its parent widget I shouldn't be using media query dot size of context or mediaquery.off context dot size because then I'll be taking the entire width of the screen I only want to take as much width and as much height as my parent allows me to do that's why layout Builder is used more often in my code I don't use media query that often in certain cases yes you do want the screen width but in this case layout Builder works fine so we are using layout Builder I also hope you understood the Box constraints here it gives you the constraints you can have for your widgets that you want to return and you can check based on that also when you print stuff here like Max height and Max with press command J restart we get 517 and 1440 then I'll click on inspect and then you see the layout changed the height is still the same but the width decreased so this is what I wanted to show to you and then we are getting an error over here saying that hey this is not enough so maybe we do need to set the child aspect ratio at 1.75 and then it will work on all the screen sizes I think it works till 1080 so we can push it till 1080 so if constraints dot Max width is greater than 1080 width so if you have this we have two cards showing up otherwise just one card okay so this works better I guess and as you can see when I increase this card also increases right if you just come over here a little bit over here you see the device or the card is shrinking in its height and width but when I increase the width of the device it increases as well so this is the beauty of child aspect ratio you can configure it the way you want it to work I think greater than 1080 is fine because all laptops have a width greater than 1080 at least I'm hoping that so yeah this was about layout Builder and this is how it's different from media query now you can play around with it and make the weather app responsive as well I didn't make it responsive for this particular reason I wanted to teach over here where we would have better examples and then I would ask you to do it for weather app and send me the code if you want me to review it I'll review it for you so this was all about responsive UI that I wanted to share so to sum it up for you try not to size your widgets because most widgets don't need an explicit size given to it they don't need sizes like 350 300 250 given to it they can take up the space they need if you have a widget like list view Builder which needs the entire device height then you can use widgets like expanded to give it all the available space and expanded is generally used in a column widget or a row widget if your widget does need a size however then give it a height of let's say 40 100 150 200 whatever because this height is in logical pixels and logical pixels basically promise that your widget will have the same physical size on all devices so this means if your widget has a size of your thumb on one of your device then it will have the size of your thumb on all devices and the third option is to use a layout Builder or media query and I've already explained the difference between both of them to you so this marks the end of the flutter beginners course we've covered a lot in this course but there's a lot more to learn I wasn't able to cover all the widgets as there are more than 200 to 300 widgets in flutter the point isn't to know about all the widgets it's about understanding how widgets should be laid out how State Management and the flutter framework work if you've understood that you're ready to build apps on your own if you want to know more about databases you can watch Instagram or Reddit clone tutorials present on this channel so I hope you've mastered the basics in flutter and you found some value in this tutorial thank you so much for watching and I'll see you in the next video