Python Invoice Generator tutorial for beginners - Python GUI Automation project [resume project]

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hello everyone welcome back to my channel now in today's video we're going to create a python project which is an invoice generator so you can think of this project as both a python GUI project by creating this interface with teakinter as well as a python automation project because we will be automating the creation of different word documents so the way this is going to work is that we have this template right here so this is a template for our invoice you can see that it has different information that you need to fill in of course I'll walk you through it later on and I'll explain exactly what all these different words mean and what is actually going on here now the way the interface will work is that you will come here you will fill in the info so let's say John Smith and let's say his mobile number is zero and then let's give it a quantity let's say he bought eight different pens and then we're going to give it this value so if you press add item you can see now that we're still building John's invoice and you can see these are his items so the quantity is eight the total is four so let's say he also bought one notebook and then the notebook itself was maybe five dollars and let's add the item so now you can see we have we are slowly building his invoice now if I press on generate invoice and I get this pop-up saying invoice complete and I go to my file explorer you can see that this file was just created so the file is called new invoice John Smith 2022 10 October 8 and with all the information so let me open it up as you can see you have the exact same template that we had before so this is the template but the information has been filled in so you can see the invoice is to John Smith this is his phone and then this is all the stuff that he bought as well as the total the tax and the final total so you have the subtotal and the final total now of course the app's still running by the way so let's go ahead and now let's do one for Jane Doe so let's say I'm a business owner and people are coming in and out of my business all the time this is a very useful app for me because I can create these invoices all the time in a very quick and easy way so let's say her phone number is a bunch of fives and let's say she bought one bag and let's give it a price of 20. um let's say she bought one pen as well let's say the price is maybe let's change the quantity and then let's say one book and the book is about 12. let's add the item all right so now we have all of our information you can see it's being updated inside the table each time now if I press on generate invoice it says invoice complete and as you can see here you have a brand new word file for Jane and if you open it up as you can see all the information is here all her information they total the subtotal the tax everything is here okay so we're going to create this step by step using python tikenter as well as a separate library for automating Microsoft Word with python now this tutorial is completely beginner friendly you don't need to know how to use any of the tools except some python experience of course you can be totally new to tick enter I will be showing you exactly how to do everything step by step the only thing I ask of you is to make sure you have it installed I have a separate video for that very short three four minutes just go ahead watch that install decanter then you can come back here it will be linked in the description of course and yeah so without further Ado let's get started part one I will cover how this whole template thing works how to automate the word stuff part two I will cover how to create the interface and in part three we're going to put it all together the source code as always will be in the description as well as the word template as well so in part one we're going to focus on how we can take these document templates that we have in word use Python to fill in the information and then generate a new document so this is for part one in part two of the video I will show you how you can create the interface with teak enter and put everything together so for now we want to focus on the type of library that we're using the library is called docs TPL this stands for docs template and this is what will allow us to actually use these templates from Microsoft Word to install it simply open up a terminal the way I have here again I'm using vs code you can use any text editor that you like and you can use the regular command prompt you don't need to use the integrated terminal I'm just using this for convenience sake so all I have to do is PIP install Docs TPL so this is the name of the library that we're using and this is what will enable us to use these templates of course in my case it says requirement are they satisfied this is because I've previously downloaded it but in your case just wait a minute and you will have it all right now that we have it downloaded you can see I have a python file called docgen.pi and I'm simply importing it so I'm importing docs template from docs TPL and inside my folder you can see I have two files I have the docsgen.pi and I have the invoice template.docs this thing here this is only because I have the actual document open so you're going to see this temporary file however if I close it this will go away so I only have two different files in my folder so this invoice template dot docs let's take a look at it this is how it looks like so I actually took a simple template from the official Microsoft Word templates that you have when you open up word you have these options but I modified it extensively just to have this very simple document this will be included inside the GitHub link so you can find the template there so you can use it for your own project all right so this is what it looks like you have the title invoice you have two so who is the person purchasing from you as well as their phone number then a table and this is where all the information about the different products that this person purchased will be so I didn't fill anything on the table because it's slightly more complicated and we'll get to it in just a second but as you can see there is a special kind of syntax that I'm putting here here here and here so in five different places let me actually zoom in so you can see this better all right so you can see that these curly braces around the word name this special syntax will enable me to use Python and actually write the name of the person here using my python code so this is how I do it in an automated way and I don't have to manually type it in word myself so this is what we're going to do we're going to use this special syntax that we have in our template access the template from Python and then put some information here now let me show you a quick demo of how this is going to work so again this is the curly braces you can see here it says name now you can write anything here it's up to you think of it it's very similar to a variable when you program so here this is like a variable called name and we're going to fill in this name value so let's go back to python so how do we do this we already imported docs template what I want to do is I want to load my template into python I do this using this line of code so I create a variable called doc then simply I just create an instance of the docs template class and what I do is I says say the name of my file so I say invoice underscore template dot docs this is the name of my file I'm saying load this into my python code once you do that this now you have it and you're able to render it and make changes to it using your code so when you're done rendering you want to save so I say doc.save this is will be the name of the new file generated so I just called it new invoice.docs so I have my old file and then I'm generating a new file as I said before to actually make any changes you need to render so this is the line of code you will need you have to say Doc dot render then you're going to pass some stuff here that we're going to talk about in just a second so by doing so you're actually able to create a new file let's actually try it out without changing any information in the template let's run it now that we run it it's done I have a new invoice.docs you can see it right here inside my folder if I open up the folder you can see it was just created right now at 1 11 pm which is the exact time in which I'm filming this so let's actually open it and when I open it you can see that the values here are blank you don't have these weird syntaxi variable names so here you have name phone subtotal tax total things like that here you don't have anything you they're totally blank this is because when we rendered we didn't pass any values so they were null by default so they are completely blank so this is our new invoice and this is what it looks like let's close it and let's now actually try to put a name here so ideally here we want to put a name and we want to do so using python so if I close it I'm back in Python what I want to do is simply I say name and I just give it John so this is a python dictionary and then inside it what you need to do is you specify the name of the variable that you have here inside your template and the value which you want to give it so this is key value so the the key here is name and I want to give it the value John now if I run it again you can see new invoice now here you can't see it but here you can see it was modified at 1 12 pm so it gets overwritten using my code and now let's open it up again and you can see now we have John here so magically through the python code we were able to take the name John and put it in this specific spot on the document without specifying anything other than the key which is name so we said in place of this variable name so if I go back to the template in place of this name here go ahead and put John and that's exactly what python did so this is really cool because now you have John here and then we can fill in all the other information so filling in the rest phone subtotal tax and total is pretty straightforward so it's a very like it's the exact same thing that we just did for John however filling in the table is a bit more complicated so I'm just going to close the new invoice and start showing you how we're going to fill in this table so here we need to specify a few more things because it's a table and we can't predict how many rows it's going to be so I can go ahead and say this will be called quantity one quantity 2 quantity 3 and then description 1 description 2 description three but that's just for three lines however if I had a hundred rows and if someone was just shopping a lot and they bought tons of things you're going to need a very very large table with multiple rows and you will have to fill all of that manually so obviously we don't want to do that we want to benefit from the idea of a for Loop that we already have in Python so what we're going to do is I will just add these here and I will explain them to you step by step so so here you have this syntax so again we have the curly braces now this time you can see a percent TR and then we're ending with percent here TR stands for table row so we're saying these table rows will have four item in invoice list so this is very similar to standard python syntax so four item in invoice list here we're going to have these item objects which will have all the information that we need and in the final row I say the percentage TR and then end four so here I'm saying once the for Loop is done just end this whole table row thing and now here I'm using the item that I got here to actually get all the information within it so item Sub 0 means get me the first thing in item item sub 1 get the second one item sub 2 3rd and item sub 3 fourth so this might be still confusing when you see an example it will be much more clear but essentially what we're doing is We're looping over this invoice list getting each specific item and assigning each item to one row and then ending the for Loop here and then inside each row we we split the item so we split the different quantity description price total into separate cells and we do so using this indexing mechanism here so let me show you an example just to make it a bit more clear so now before I showed you how you were able to render name as John now you can add another render like this as invoice list so you can see invoiceless and it will be assigned to a variable in Python which is invoice list now let's create this variable first it's going to be an empty list we said that this is a python list but each row itself is also a list so it's going to be a list of lists so as you can see you have two nested lists here and if you look at it right now you can see you have two pen and the price is 0.5 so the total is one so here I have my invoice list currently it has only one row and this row contains this information so let's verify that this is working and then we'll compare this list with the one that we added in our template let's run so now that it's done let's actually open up the new invoice and I open it and as you can see name is drawn still here and then here inside the table we have one row because our list itself only had one row and we have the quantity to the description pen the price is 0.5 and then the total is one which is exactly what we told it to put so again what we did is we started this for Loop for this invoice list so this invoice list and each for Loop We Set four item and invoice list so each item will be equal to one of these it's going to be a list itself now we said item Sub 0 which is this one so here item Sub-Zero so the very first item in this list which is this number two so item sub 1 is the pen and we put all of these in their corresponding cells which gave us this output so this is how you're able to actually process this python list and convert it to this table in Microsoft Word now let's go ahead and try it out with multiple different rows so I'm going to add these as you can see this person bought other items so they bought one of the paper pack two of The Notebook and they have these quantities prices and the totals now I have hard coded the totals here although I could do some multiplication we'll do that when we do the full application with tikenter so let's run it now that it's done let's go ahead and then open this again and as you can see our table was filled with all the information that we needed so it's pretty straightforward once you understand the basic syntax that comes with creating your template and then importing it using this docs TPL Library it's very simple to render the information and fill everything in like I just showed you let's go ahead and just fill in the rest of the information just for the sake of example so we add the phone and let's add the subtotal sales tax and total again here I'm hard coding it but when we do the full application these will actually be this will be a summation of all the totals this will be a multiplication with the percentage so don't worry about that I'll show you how we do it but for now this is just an example let's run it again so we have an utter open permission denied this is because the new invoice is open so let me actually close it and now this should work so be careful when you actually run it and the file is open the python won't be able to write to this file so now that this is done let's open it up again and as you can see all the information is here including the totals the tax and all the information in the table so this is how we were able to use Python to automate the creation of the invoice through the code and filling in all the information in this template so next what we're going to do in part two of this video we're going to create the interface using tikenter and finally we will put everything together to have this invoice generator okay so in part two we're going to create the ticketer interface so in this section we're not going to look at the documents we're not going to look at the template the invoices all of that simply we're just going to create the interface now for reference I have a screenshot right here of what the interface should look like this is going to be our final result once we're done with this creation all right so let me walk you through it step by step and see how we're going to create this interface so here I have some starter code nothing too complicated so first of all I have some imports I'm importing tikenter and then I'm importing ttk from ticketer now ttk is the themed widgets module for Tekken 3 so these are basically widgets that you can style some of the widgets are actually different and they come with different features some of them only exist in ttk and not in tkinter some of them exist in tikenter and not in ttk so you'll see why we need the ttk module later on in the video once I actually use it but for now just know that you need to import it and import take inter as well now here what I have is window is equal to tikenter.tk basically here I'm creating my root widget which is my window itself so when I create this here I'm basically creating this part so the actual window not the widgets within it just the window itself this is the parent or the root window now I I also set the title so I say window.title is equal to invoice generator form this is my title and as you can see this will show up here so this will be the title of the window then finally I say window.main Loop now this main Loop basically it's just an infinite Loop that will run it's the event Loop for tkinter so as long as your tkinter application is running this main Loop is B is running and it's receiving events in case you interact with the application or something happens when you close the app this main Loop terminates and the python app can terminate alright so this is what our starter code looks like now how are we going to start first things first we're going to create something called a frame now a frame is going to be another container within our larger window container and it will hold everything else in the application so here you can see this is the root window inside it now an invisible second container is something here so I'm just going to draw on the image but basically there's another Square here and this is okay excuse my drawing skills but this is basically another container within my larger container which is the window you don't really see it it's invisible but this is going to help me keep the application responsive and look nice as I resize my window so more on that later because as I show you and as we build the application you'll see why we use the frame exactly but just for now think of it like this it's another container within your larger window which is your root widget so it's a big container then within it you have the frame which is a smaller container and within it you have other things such as these widgets that you see right here so the buttons the labels the text entries things like that all right so I've created the frame I use tikenter.frame to create it and then I pass window as its parent so for every widget that you create antique enter you have to say who the parent is by parent we mean where does this widget exist within which container so I'm saying the frame exists within the window alright so this is how our hierarchy is looking now finally I say frame dot pack in t Contour every time you want to add a widget to your screen you need to do two things first you need to create it using its class so you can say take into dot frame or tick enter dot button or tick enter dot label so this is up to you then finally you have to position it on your screen using a tick inter geometry manager or a layout manager these are called pack place and grid there's three different methods each of them does a certain specific thing I have a video talking about them in depth but for now for this video we're going to pack the frame now pack what it does is it poses positions your widget in the middle of the screen with as much space as it requires and then as you resize the window it stays in the middle of the screen and you'll see what I mean as I show you more and then you understand why we use frame why we use pack and all those things but most importantly remember you need to create your widget and then you need to pack place or grid we'll also use grid later on in this video so you'll see that in just a second so we've created our frame we have the starter code we also added the frame now if I run the app this is what it looks like it's a totally blank app you can see that it's pretty small when we run it it's actually very tiny almost invisible this is because we don't have anything the frame gets resized according to the widgets in it and since the widgets themselves are nothing there's no widgets it's going to be totally zero totally invisible alright we have the frame what we want to do next is ADD our labels buttons and things like that so we want to add all of these guys that you see right right here inside our frame I'm going to start by adding this first name here so this is what we call a label I'm going to add it in the code so the label I'm going to add it like this I use tikenter.label and I'm saving this inside a variable called first name label so tikenter.label I say the parent this time is frame so notice how before the parent of frame was window and the parent of the label is the frame so you have the big box which is window then a smaller box inside it which is a frame and then a smaller box a very small box which is the label so this is how this hierarchy looks like and I specify the text so the text is basically what I'll see when I run my application and what the label will display now if I actually run it you can see the app is still blank this is because again I haven't positioned the label on my screen I told you you need two things anytime you want to put it on your screen you need two things two steps create the widget and then you have to pack place or grid and in this case we're using grid now here I'm saying first name label dot grid row equals zero and then column equals zero what the grid means I'll show you in just a second but for now let's run it and as you can see we can see the first name and now if I resize it stays in the center which is what makes it responsive and resizable so this is why we needed to use the frame the frame actually allows us to keep it here and keep it in the center as we resize it so this is why we have the frame the frame and we use back with it and this is what pack does so pack allows us to keep everything in the center then grid allows us to organize them and place them so I put the first name here this is the label and I did it using this line of code which you saw right now so grid then I said row equals zero column equals zero grids basically let's go back to the image so I'm going to just clear my drawing grid is exactly what it sounds like it's a grid it's a table a matrix things like that so if I just draw this you can see this is what my grid is going to look like and then you can see that we have these columns and then different rows so if I lengthen this so this is really bad I and so on so anyways but you can see that we have an actual grid right here so this is row zero and then also column zero now on this hand this would be row 0 because it's still the first row but it would be column one and now this is row 0 but it's column two so this is what the grid looks like it's basically a table and the indexes start with zero usually in programming most things do now here this is the second column so it's going to be sorry the second row so it's going to be Row one but still the column is zero in this case and this is one one and so on so this is what this whole thing looks like and this is what we're trying to emulate with our code so we started we added the first name label and we said that this is going to be zero zero done we already put that now for now we see it in the screen we don't see a table sorry so we don't see a table this is because we don't have anything else and the way grids work is in in Python and in tikenter especially is that for example let's say I put row 70 this is still going to be here because each row or each column takes up as much space as the widgets in it so because the other rows and columns are empty they will not show up and they will be almost invisible so they will have no size so we added the first name label the next thing we're going to do we're going to add the last name label so to do so same thing you say take inter dot label then what I'm going to do is say the parent is the frame so of course it belongs to our frame we already explained the hierarchy and the widgets how they work and then I say the text is going to be last name now according to the grid the one we drew here last name exists inside row 0 but column one and we do exactly that so we say grid row equals 0 and then column equals one so now if we run it as you can see we have two labels first name and last name the first name comes first because it's in column 0 and then this one is in column one and of course if I resize it you can see it's resizable and they're still in the center this is due to the use of the frame now let's close it so now that we've added these two labels let's go ahead and actually add the entries for the first name and the last name so the entries are these guys right here this is where you would enter text input so let's go ahead and do this so you see these four lines of code here I say first name entry is equal to taken through dot entry so same thing as before the way we set ticketer.label we specify the parent is frame of course because it belongs to the frame then same thing for the last name entry taken through dot entry frame and of course I need to add them to my grid so I do so I say row equal one column equals 0 for the first name entry and this is exactly why so we said here this is the entry rows one column zero then here this is Row one column one and I specify just that so I do this using these two lines of code now let's run it and as you can see they are in fact in the right position each is under the respective label so if we resize it you can see this is row 0 column 0 row 0 column one row one column zero and then Row one column one as you can see right here all right so we've added these two let's go ahead now and add the phone label and entry so here we're saving the phone number we have a label for it and we have another entry so let's go ahead now you can see we said taken2.label frame same thing as before this label exists inside this Frame then we say the text is equal to phone because this is what we want to display we add it to the grid using row 0 column two because it's the third column so this column will be two again you see it right here so this is 0 2 and then of course what this one's going to be is Row one and also column two because it's in the same column so I'm going to do the same thing here and of course phone entry is equal to tikenter.entry it also belongs to the frame so I'm kind of speeding through these because we're essentially doing the same thing every time we're creating a label and then we're creating an entry with this label and we're organizing them inside this grid and as you can see now we have all three of them you have three labels three entries and this is what they look like if I resize it they remain in the center because they are inside the frame so the frame itself is being packed each time and it's placed in the center alright so we've created these three guys now we have another set of three so let me just clear this just so that we can actually see so because here we filled out the first two rows now here you have row two and now you have Row three because we said this is row zero and this is Row one so now we have to fill out row two and Row three so I'm going to do the very same thing that I just did before now the only difference is here we're not actually using an entry you'll see what we're using in just a second so I go ahead I create the quantity label again taken to that label it's inside frame and this is the text that's supposed to display then I put it in the grid so this is Row 2 column zero just like I told you before this is now row two now what I want to do next is I want to create this thing right here this is what we call antique inter a spin box it lets you calculate and lets you change the numbers so you can actually get a numerical output and not just a string so let's see so again I say take into Dot spinbox and it's inside the frame so this is where it belongs then I put it in the grid Row 3 column 0. let's actually run it and check it out so as you can see it gets placed in this column it doesn't go over and expand to the other columns so you have the label the quantity and then this spin box so this is supposed to hold a numerical values let's say one and then as you change it of course this is hypothetical as you change it this should increase and decrease while you press these buttons a spinbox in tikenter is essentially just an entry just with some buttons so how are we going to make this work you actually need to specify a few things when you create your spin box so here you have to specify from and two so in my case I set from 1 because the minimum you can buy of any item is one not zero obviously and then I specified 100 however you can give this any upper bound you like you can even give it Infinity if that's what you want but in my case I set from 1 to 100 so if I run it now you can see the default or the starter value is 1 and if I press on the arrows I am able to manipulate the numbers using using the arrow buttons this is really good because now it enables me to actually set my quantity in a numerical way without having to type it out each time so we added the spin box we place it in the grid now let's do the same for the others so we have also the description now the description is not a spin box it's in fact just a regular entry just like the other guys before so let's go ahead and add that pretty straightforward we have a label this time the label displays description of course it's inside frame then we put it in the Grid in Row 2 and column one then I do the same thing with entry so tick inter dot entry frame and then I put it in Row 3 column one now I am speeding through these this is because majority of this code is pretty similar we're always doing the same two steps defining the label then putting it in the Grid or defining the entry and putting it in the grid now if you want to test yourself and see if you're learning this as you go along you can pause this video and try to add the final one which is this label and the spin box so we already added a spin box before just try it out try to see if you can add this write the code from memory see if you're actually learning it and you're retaining it as we go so that was just a like little test now we can continue and do the same thing here so let's see you have price label and then again same thing we added the label and then here we added a spin box again now in this case I'm actually going to use increments of 0.5 so let me show you how this will look like before I explain the code so you can see right here the price itself is not just zero it's 0.0 so if I increase now it increases with increments of 0.5 so 3.54 4.55 5.5 this is because of this guy right here so I set the starter value is 0.0 then it will go up to 100 500 sorry and then the increment is 0.5 so this is how you tell the spin box not to increase by one each time but to in fact increase by a certain value so we've created all of these guys the first four rows in the application one thing I want to fix you see here how there is this sort of space at the edge of the application making it look like it has more breathing room like if I run it here let's just compare you see everything is kind of squished and it's pretty tight and you can see there's very little Borders or space here around the stuff so just to fix this quickly in the back of the frame so because we said frame dot pack I just give it a little padding so I say padding X is 20 and padding Y is it is done so by doing so let me show you what difference it makes you can see now there is this little space here around the application around all the stuff this is because of the padding so I said padding 20 on the X so horizontally there will be like 20 here and 20 here and then Paddington on y so here and here this gives the application a bit more breathing room and as you can see it looks better because the app doesn't end just out outside the boundaries of the widgets so this is just a stylistic decision you don't have to do it if you don't want to but it helps and it makes the application look better alright so now we've added all of these and we fixed the padding let's go ahead and add this button right here so we have this small button which is the add item button so let's do it very simple straightforward same process as before we say tick enter dot button we put it inside the frame and then we say the text is equal to add item now I save this inside a variable called add item button then this add item button I say dot grid and I'm going to put it in row number four column number two with padding five just so that it has some padding around it so why Row 4 because this is the fourth row we already have zero one two three this is row number four and I specifically chose column number two so this is column number two we have column zero column one column two and I put it here in column number two now you can put it in any of them I just chose to for aesthetic reasons but this is totally up to you so now let's run it and see if it works as you can see the button is here now of course if I click it nothing happens because we haven't programmed it to do anything so that's totally fine let's just close it all right so the next thing we're going to add is a bit different now this one doesn't really fit within the grid we'll figure out how we're going to place it in just a second but essentially what this is is a way for us to display tabular data or data in the form of a table using teakinter this is something called H3 view I'll show you how we're going to use it and create it in just a second but I just wanted you to note that this is a bit different from all the other widgets that we created and it's going to take up much more space in the application this is where we're going to list all the items that we create in our invoice so let's see how we're going to do it as I told you it's called A3 view to actually use it you need this ttk module you don't use the tikenter you use ttk so this is why we imported it just so that we can use the tree view treeview doesn't exist within the original TK enter module now to create it I say ttk.treview then I put it inside the frame so this is the same as before I'm saying put this inside the parent frame columns headings I'll explain all of that in just a second so columns you have to specifically give it a set of columns so the columns here in this case will be these four you can see we have four columns quantity description price and total so I put these inside this python Tuple you can see it right here so it's called columns and basically I'm saying the columns property of this tree view is going to be the columns here all right let's run it of course it's not here yet because we haven't added it using packplace or grid let's use grid and as you can see I have row equal 5 column equals zero column span and some padding so I'll explain everything but let's first take a look at it as you can see this is the tree view so this is the table we have four columns now they don't have names yet we'll do that in just a second but this is how it looks like and it's taking up space over three columns this is because I specify this column span 3. now if I clear it and I run it again you can see it tries to put this whole thing inside the First Column and it severely distorts the application so you can see this is now column zero this is column one and this is column two and it looks very wrong so this column span property what it did is it's basically telling it is that okay start at column zero but then take up space inside three different columns so span three different columns and this is why it looks much better so now it's inside three different columns and it looks good so you have column zero column one and column two and this is taking up space inside all three and now it looks much more presentable also I specified some padding this is just for stylistic reasons again just to make things space out a little so you can remove it if you want so if I remove it like this and you run it it's the same thing it's just a bit more tight here like it's close to the edges and it's close to this button you can remove or keep it it's totally up to you but I'm going to choose to keep it all right so I added the tree now I want to add the headings so I want to add the titles of the columns so because you say you see here it says a quantity description price and total so let's do that to do that it's pretty simple so you say three dot heading and then you'd say the column name so this name right here because we already gave it a list of columns so for the column quantity give it the text quantity so this is how we specify the heading and I'm going to go ahead and do that for all four of them so for the for the column description so this one desk give it the text description for the column price give a tax unit price for column total give it the tax total so this is how we set the headings now let's run it as you can see the headings are now here it looks way better of course we don't have any info yet we'll get to that soon enough but for now this is what it looks like all right so we've added the tree view now the last thing I want to add is these two buttons right here and we're actually almost done with the interface so these two buttons they also span three different columns you can see they take up the whole space and we're going to add them so let's see let's add them using the grid so we go ahead and do this so we have the save invoice button it's a tkinter DOT button it exists inside the frame and the text is going to be generate invoice so this is the first one now the second one it's going to be called new invoice so you can see here and it says text new invoice now when I add them to this grid here are how here's how I'm going to do it so you have row six column zero this makes sense because before we set this as row four and now of course this is row five and then this makes sense this is row six and this is row seven we put it inside column 0 in both cases and then the column span is going to be equal to three again the reason is because by doing so we're saying take up space in three columns now why do I say sticky equal news this is very weird I'm going to explain this by showing you what happens when I remove this line and I run it so as you can see the generate invoice button is now very tight and small and it's not as big as the new invoice so the new invoice takes up the whole Space just like the tree view before it so this is sticking equal news is basically telling it where should I expand the sticky attribute decides where I expand now why news this stands for north east west and south so by doing so I'm saying expand in these areas if I just keep it as e so here I'm saying East you can see it just moves to the east so this is why it looks weird it looks different so when we say news this means that do it in the north east west and south so this is what it means and as you can see now it takes up the whole space I do the same thing for the other button now I'm not going to show you because it's the exact same thing and I also added some padding for stylistic reasons so now we have officially created the interface so we built it using the code we built it using teakinter it looks nice it looks the exact same as this one so now we have the interface that we wanted now what do we want to do next we want to add some functionality to these buttons first things first I want this add item when I fill in some info so let's say Quantity 4 and then description pen and then the price is zero or is one I press add item what I ideally want is I want the item to show up here in this table indicating that my invoice now has an additional item it has a new item on the invoice so let's do that using the code first things first anytime you want to link a button to a specific line of code you're going to use this command property so inside my add item button where I specify taken to that button and frame the text everything I also specify command and in this case command is going to be equal to add item now add item should be a function that I write myself that should get executed when this button is pressed so basically when add item button is pressed go ahead and execute add item function now where is that item function let's go and create it so here at the top of my code I create a new function called add item so as you can see it's called add item and this is what's going to be executed when this command when this command happens so when this button is clicked so I'll show you what I mean in just a second let's try to actually print hi okay so I'm just going to print something just to show you that this function is getting executed so if I run it and I press on add item you can see hi gets printed here let's do it again and again and again so if I scroll up you can see hi is being printed each time so what's happening in the code is that when the button is getting clicked this command guy is telling us go to add item and execute this this is basically how it's working all right so I don't want this what I want to do is to actually get the information from my different here so from these different entries so I want to get the quantity get the description and get the price so let's do that first things first I save in a variable called quantity the quantityspinbox.get so this function dot get will get me the value of the spin box which is in this case one or two or three or four or whatever and I convert it to an integer because I want it as an INT I don't want it as a string it it genuinely just returns a string at first all right now I do the same thing with the description so I say description entry dot get and in this case this is just a string so here I'm getting the value of the description finally I get the price now this one I convert to a float because it can have the value of 0.5 and different increments so I say float price spinbox dot get as you can see here all right now I want to extract the total price so to do so I just have to multiply the quantity by the price so this is just a case of multiplication so if one pen costs one dollar and the person bought two pens this is going to be a total of two dollars so now I extracted all this info what I want to do is I will save them inside a list so this is my list and it's going to be called invoice item and then this invoice item will have all this information inside of it what I want to do next is I want to Simply add this to the tree view to the table where I was saving all my information so I want to add this to this table right here to do so one line of code you say three dot insert and then you say this so you don't have an identifier for it this is just for this sake of the identifier zero and then you say values invoice items so here you're saying this is added at the start of the row so let's see if I run it and now you can see here let's put a quantity of four let's say pen and then each pen costs 50 cents let's press on add item you can see the information was added here now let's actually change this let's go with eight and maybe here we're going to say eight uh paper and then also let's go with one these are just hypothetical but as you can see the information is being saved here and it's being added to the table so this is really cool now we have this functioning and we're able to add our different items to our tree view now what is one problem that we have here we ideally want these values to be cleared each time we finished adding an item so ideally I don't want to have to erase this and write something new I want it to get cleared on its own so let me show you how we're going to do that through the code at the end of our ad item after we've inserted everything into our tree we're going to actually go ahead and clear item so here I'm adding this function and I'm going to explain it to you just step by step just a second we're adding this function just so that we can clear the items in the tree View and then of course inside that item I have to call it so I say clear item let me show you how it works in action and then I'll explain the code so if I run it let's say Quantity five pen and then 0.5 and if I press on add item you can see it was added here and also these guys return to their default values and this one was cleared as well this is really helpful because it doesn't mean I have to keep erasing and keep modifying and it reduces the likelihood of others so now if I go here and I press on paper and give it some random price and press add item you can see again it gets cleared okay perfect now that we have this let me just explain how the code is working basically for the quantity spin box I say dot delete from 0 till end zero means delete from the start of the spin box to the very end tick enter.n means the very end of the spin box then I insert it into the spin box the default values which in this case is one now on the other hand uh the description entry I delete 0 and then I also delete to the tick enter and then same thing so here I cleared the description entry here I do the same thing for the spin box I delete from 0 to tick enter and and I insert the value 0.0 so let me run it and just change the values here add item and as you can see it gets cleared so this is how what I already showed you all right so now we have the clear item and we have the add item working the next thing that we want to actually work is this new invoice guy right here so new invoice does something pretty similar except this time we want to clear everything so we want to clear the first name the last name the phone things like that so before I wasn't really showing you the first name and last name but basically let's say I'm putting in for John Smith and then he gives me his phone number which is a bunch of zeros and then this is where I'm changing the quantity so pen and then this is going to be uh 2.5 okay so when I added item it cleared these guys but this one stayed the same this is because we're working within one single invoice so this invoice is still for John Smith now if he goes ahead and buys a notebook and then um this is priced in some certain way we add the item these are all still for John Smith well we want to export the word document which has the invoice this is going to be for John Smith as well so we're not clearing his first name last name and phone however let's say I don't want to do his invoice anymore I want a new invoice so this is what the new invoice button should do it should clear everything it should clear his name his phone and it should also clear his two items it should clear everything he's done so far and we start fresh from a blank slate so let's code that now again you need to actually specify the command so for the new invoice button every time it's clicked go ahead and execute the new invoice function so this function we're going to Define it here now what it's going to look like is as follows we have the first name entry dot delete from 0 to the end last name entry same thing and phone entry same thing so we're clearing these three different entries from zero till n so we're clearing the whole thing now another thing we want to do is we want to clear item this is because the clear item here it already clears the other three so it clears these guys we don't want to copy paste the same code we just call it again and this way we cleared up everything now let's try it out let's see if it works so again I'm going to say John Smith and the phone's going to be a bunch of zeros and this is going to be six different pens and it's going to be 1.5 so as you can see this was added here and let's say he got a notebook as well and it was a certain number let's add it okay so now if I press on new invoice you can see everything here was cleared except the tree view so this is the very last step that we're going to do here we have to clear everything inside the tree View this is one line of code very straightforward so back in new invoice we say three dot delete and then we use this operator basically we're saying delete each one inside they get children delete each child inside get children and this should delete everything so let's run it and go with John doe and then his phone then a bunch of information here so I'm doing the same examples but anyway so notebook this is going to be let's say six so now if I press on new invoice everything was cleared all his information as well as all the items we had previously logged into the tree so this is the end of part two so part two what we did is we created the interface from scratch using tikenter we programmed these two buttons the add item and the new invoice button now in the final part we will program the generate invoice what this will do is it will produce the word document just as I showed you at the start of the video it will produce it and generate it from the template that we have so now we've come to the final part we want to link everything together we want to use DUI we want to press on this generate invoice button and actually get outputted with a Word document that fills in the template using the information that we entered here so how can we do this so first things first we're going to import two things we're going to import this docs template which we used before in this short demo so I'm not going to use any of this code I'm just going to put the relevant code in the new file but I will be using it for reference alright so we will import the docs template and another thing we will import date time I'll show you why in just a few minutes while we're using it in the code so now that we've imported them the first thing we want to do is we want to add a command to the generate invoice button so similar to what we did before using the new invoice and add item you can see here command equal generate invoice and of course we have to create a function for it so we go ahead and do that here so we saved generate invoice so now that we have this function we want to fill it in we want to get the information from the interface and save it in different variables first thing let's create the template so this is going to be the template that we're loading of course it's the very same one the invoice template dot docs so you can see this is the one that we have nothing changed the same template that we did in the demo at the very start of the video alright next we want to get the name from the interface to do so it's pretty simple so we say first name entry dot get so we get the first name and we concatenate it with the last name so we say last name entry dot get as well and we save both of these inside a variable called name of course this variable called name will later be filled in here and it will take up this spot so if I enter the name first name John last name Smith John Smith should be outputted here when we generate the invoice now we got the name we can get the phone in the exact same way so I use the phone entry to get the phone all right now now that we've done this I'm going to show you how we're going to render so remember in the first uh the first time the first demo that I showed you this we had the template we loaded it then we rendered it with a doc dot render so we rendered the changes we put in and filled in all the different variables and then we saved so we said doc.save so now I'm showing you how you can render so of course the name is going to be the name variable that we saved then phone is going to be the phone variable that we saved and the rest of them I'll show you how we're going to add them step by step so we need an invoice list so when we were adding these different invoices every time we pressed add item we were adding them to the table but we weren't really saving them anywhere so to do so I'm going to create a list called invoice list which is going to keep storing all my invoices every time I add them and not all invoices I mean all the items so be careful here so it's going to be all the items so every time I add an item for one specific customer they will all be saved inside this invoice list so how do we do that so going back to our add item function I'm going to create a variable called invoice list so this invoice list will keep track of all the items this specific customer added so every time I say add item I'm going to append the invoice item so we set the invoice item contains all the information quantity description price the total so this list we will add it inside this bigger list which is invoice list so the output should look something like this like this one right here so we already created it we hard coded all these values now we're saving and creating this type of list using the python code so we're not doing it manually like you see right here so after appending to it of course when we press new invoice this list should get cleared so here I add a invoice list dot clear so you can see it right here all right so now I was able to save all my items in the list and then clear it every time I have a new invoice so now I actually have an invoice list right here so this variable is taking care of this should fill in the table with all the different items now the rest of them so subtotal sales tax total how do I get those so with subtotal here you can see that we have this function right here so we're using the sum function built in with python and we're summing item sub 3 for item in invoice list now sub 3 means we're getting the fourth element now here you can see each item looks like this quantity description price and line total so I'm summing all the line totals together to achieve my final subtotal of course we have the sales tax now the sales tax you set it to whatever you like so in my case I'm setting it to be 10 in your case you can set it to whatever you want and then you can calculate the total by multiplying the subtotal by 1 minus the sales tax so if the tax is 10 this is going to multiply it by 90 and you will get 90 of the subtotal as your final total now the final step we said before you need to load the template render the changes and then finally save so before we were saving in one file called new invoice.docs now there's a problem with this because if I save every invoice to new invoice.docs this information will keep getting overwritten that means if I get 10 customers all 10 of their invoices will go in the same place and I will lose this information so essentially losing the invoices so how can I fix that to do so we're going to create some unique document names this means that if John Smith walks in and I create an invoice for him it should be different from the invoice generated if Jane Doe walks in and I created invoice for her so how do I do that if I add these two lines of code so as you can see you have the doc name this is the variable this will contain the doc name and finally I will say doc.save Doc name so before we set doc.save new invoice now we're just creating this doc name how does this doc name look like it's going to contain the term new invoice concatenated with the name of the person so their actual name and then the date time the actual time stamp that we're getting from the very moment that we create the invoice so this means that let's say John Smith comes in right now and I generate an invoice for him what this should say is new invoice John Smith 10 October 8 2022 at 8 24 pm and the seconds as well dot docs so by doing so we generate a long dock name but this doc name is going to always be unique because it's Unique to the customer and unique to the date and time and if you're a bit confused by this don't worry because I'll show you a quick demo in just a second but this is essentially what we need this is what we need to create this invoice so let's try it out let's see the result so let's run it so as you can see here let's say John Smith and then let's give him a phone number of zero zero zero and then a bunch of zeros so for me this doesn't really matter we're just doing this for example so let's say he got six pens and each pen cost 50 cents so let's add this to our total he also bought one notebook and the notebook in this case let's say it costs seven dollars so you can see we have his chart you have his table with all his information all the things that he just purchased so now if I press on generate invoice you can see here a new document was just created now let me go to my file explorer it says new invoice John Smith 2022 1008 20 these like these are this is the random seconds so this is the time so now if I open it as you can see all the information was filled in so you have invoice to John Smith with this phone number now you can see that his actual the items that he purchased are all here the subtotal is here the tax is 10 so the total is nine and all the information was filled out and it created this unique file for him one thing I want to comment on is this so you see that his information is still here ideally what I want is I want his information to be erased every time I generate his invoice because now we're creating a new invoice so this is pretty simple I'm just going to call the new invoice function this means that his info will be cleared every time I generate the invoice so let's see if I go ahead and say John Smith and then put his phone number and this could be the same John Smith or another one it doesn't matter because the name of the document will be unique so watch this let's say this is the price and let's generate the invoice now everything got cleared because we called the new invoice function everything got cleared so now we're starting from scratch now going back here you can see there's a new document with the name John Smith but of course it's a different document because the timing is different now opening it you can see we have all our information in the right place and we were able to clear it from the app once we were done so this gives us a blank slate to work with so that we start again and start creating a new invoice now the very very last thing I want to show you is let's create a pop-up that tells us that this document is done generating now to do so we're going to use something called the tikenter message box so going back to your Imports you want to import this line of code so from teakinter import message box and then it's a very simple one line of code inside our function you will say messagebox.show info invoice complete and then I'm just going to to give it invoice complete so I'll show you what these guys mean when I run it so let's go ahead let's say Jane Doe and then let's give her a phone number which is zero zero and let's give the stuff let's say she bought pencils and pencils so and they cost 50 cents and then she bought six books and the books all cost 20 so I'm just going to say 20. add the items and then let's generate an invoice where you see this pop-up it says invoice complete and invoice complete so the first one that we passed was the title of the window and the second one was the text that should be displayed here so as you can see her this pop-up enabled us to know when the document was generated so it's just a nice touch to add you don't need to add it at the end of the application but you can alright so we can verify let's see so you have during though here open the document and all her information is here
Info
Channel: Code First with Hala
Views: 49,968
Rating: undefined out of 5
Keywords:
Id: mJc5gAnnlVQ
Channel Id: undefined
Length: 63min 15sec (3795 seconds)
Published: Mon Oct 10 2022
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.