0

I am attempting to build an Python custom PDF invoicing code where with a GUI where: -The user types input into the GUI. -The inputs can be "Save as" into a new file generated. -This file is an executable to generate a custom invoice PDF file with the user's input. -However I am trying to get all of this done on the one screen GUI, with all the buttons to save as and execute the file to generate a custom PDF.

--My biggest challenge right now is how to save user inputs as variables in a new "Save as" file. Should I use arrays for this? Thanks in advance!

---Here is my attempt so far.

#Form filling mapping
import io

import pdfrw
from reportlab.pdfgen import canvas


def run():
    canvas_data = get_overlay_canvas()
    form = merge(canvas_data, template_path='./SmartInvoice.pdf')
    save(form, filename='merged.pdf')


def get_overlay_canvas() -> io.BytesIO:
    data = io.BytesIO()
    pdf = canvas.Canvas(data)
    #Invoice issuer, company name etc:
    pdf.drawString(x=100, y=727, text='Midland REalty Pty Ltd')
    #Issuer address
    pdf.drawString(x=100, y=711, text='477 Darling Street, Balmain NSW 2041')
    #ABN or ACN
    pdf.drawString(x=100, y=696, text='ABN: 113 646 174')
    #Phone Contact
    pdf.drawString(x=100, y=681, text='Ph: 0433163800')
    #Invoice issued to:
    pdf.drawString(x=83, y=606, text='Invoiced to Client Name')
    #Customer Details:
    pdf.drawString(x=83, y=591, text='22 Moonview Crescent, Henley, NSW 2011, 0404755999')
    #Tax Invoice No.
    pdf.drawString(x=535, y=674, text='22')
    #Date of issuance of invoice
    pdf.drawString(x=516, y=658, text='Date of issuance of invoice')
    #Form Description
    pdf.drawString(x=33, y=650, text='Midland Realty Invoice #0209')
    #Subtotal
    pdf.drawString(x=500, y=458, text='$1,000,000')
    #Subtotal 2
    pdf.drawString(x=500, y=400, text='$1,500,000')
    #Subtotal 3
    pdf.drawString(x=500, y=342, text='$4,000,000')
    #Total
    pdf.drawString(x=500, y=237, text='$6,500,000')
    #GST
    pdf.drawString(x=500, y=210, text='$715,000')
    #Total Inc. GST
    pdf.drawString(x=500, y=178, text='$7,150,000')
    #Description of good or service provided.
    pdf.drawString(x=45, y=465, text='Sales Commision')
    #Payment methods:
    pdf.drawString(x=150, y=120, text='ETF. BSB: 012123 Accnt No.: 123 145 234')
    #Payment due by date:
    pdf.drawString(x=86, y=151, text='16/08/2018')
    pdf.save()
    data.seek(0)
    return data


def merge(overlay_canvas: io.BytesIO, template_path: str) -> io.BytesIO:
    template_pdf = pdfrw.PdfReader(template_path)
    overlay_pdf = pdfrw.PdfReader(overlay_canvas)
    for page, data in zip(template_pdf.pages, overlay_pdf.pages):
        overlay = pdfrw.PageMerge().add(data)[0]
        pdfrw.PageMerge(page).add(overlay).render()
    form = io.BytesIO()
    pdfrw.PdfWriter().write(form, template_pdf)
    form.seek(0)
    return form


def save(form: io.BytesIO, filename: str):
    with open(filename, 'wb') as f:
        f.write(form.read())

if __name__ == '__main__':
    run()




#GUI
from tkinter import *
import fileinput
import os
import re 
import time


root = Tk()
root.title("New Application")
root.geometry("640x640+0+0")

#Text label
heading = Label(root, text="Welcome to the really useful APP", font=("arial", 40, "bold"), fg="steelblue").pack()

#Text label
label1 = Label(root, text="Enter your Company Name: ", font=("arial",20, "bold"), fg="black").place(x=10, y=200)


#Text box for name of customer
name = StringVar()
entry_box = Entry(root, textvariable = name, width = 25, bg = "orange").place(x=450, y=210)


#Text box for date of issue of invoice
invoice_date = StringVar()
entry_box = Entry(root, textvariable = invoice_date, width = 25, bg = "green").place(x=450, y=270)


#Defines the buttons
def do_it():
    print("Hello Valued Customer. How are you doing today " + str(name.get()) + "?")

#Defines the buttons
'''def do_it_2():
    for line in fileinput.input('PythonSmartInvoice.py', inplace=True): 
        print (line.rstrip().replace('Invoiced to Client Name', str(name.get())))'''

#Defines the buttons    
'''def do_it_3():
    for line in fileinput.input('PythonSmartInvoice.py', inplace=True):
        print (line.rstrip(),replace('Date of issuance of invoice', str(invoice_date.get())))'''

#Buttons 1
work = Button(root, text="Work", width=30, height = 5, bg = "lightblue", command=do_it).place(x=250, y=300)
#Buttons 2
work2 = Button(root, text="Button", width=30, height = 5, bg = "orange", command=do_it_2).place(x=250, y=400)
#Buttons 3
work3 = Button(root, text="Button", width=30, height = 5, bg = "red", command=do_it_3).place(x=250, y=500)


root.mainloop()
  • https://stackoverflow.com/questions/14824163/how-to-get-the-input-from-the-tkinter-text-box-widget Look into this post – v0rtex Aug 18 '18 at 04:34
  • Thank you, I've made progress. What I really want to do is that, when the user types in a user input to the tkinter GUI, this is saved in a variable such that he or she could "Save As" the variable, and close the file, and open the file again, and the user input before would still be there. I hope I'm making sense? – ThunderWolf. Aug 20 '18 at 07:34
  • Yeah that makes sense. I would suggest creating a .txt cfg file, or a json that lets you write data to it and read from it. You could easily fetch the data from the json whenever the programs starts, and write to it when a certain command is run. – v0rtex Aug 20 '18 at 22:51
  • Thank you, Vortex. I think I get the general idea. Do you know of any good examples that fleshes out this concept? – ThunderWolf. Aug 21 '18 at 04:53
  • Tutorial site: http://interactivepython.org/runestone/static/pip/Files/files.html Test site: https://www.w3resource.com/python-exercises/file/python-io-exercise-6.php To store the data from the text file as a variable, you should look into using JSON, as it is easier. Here is a good json doc: https://stackabuse.com/reading-and-writing-json-to-a-file-in-python/ – v0rtex Aug 21 '18 at 05:38
  • Thank you, this has been very helpful. Also, is there a way for the user to modify the 'text=' variable within pdf.drawString(x=100, y=727, text='Midland REalty Pty Ltd') straight from user input in the GUI? Could you please give an example of the code for this? – ThunderWolf. Sep 11 '18 at 11:37

0 Answers0