Please explain what I can improve, and why. I'm new to Python, Tkinter & Code Review, so I have a lot to learn. :)
I created a Tkinter app for user-input, and the same types of widgets are repeated on each row. A single row is similar to a slide in PowerPoint because it has an image, numbers, and input text. I will later add the "export to separate file" functionality, but for now I'm focused on the "skeleton" of the code, which is the creation & display of the widgets.
Since each row is a repeat of the one above it, I know I could somehow create a "row-object" using a class, and/or use a for-loop to create each row. Since I'm not sure how to do either, my code is verbose and repetitive. I manually create each widget. I used Excel to spit out this part of the code. This is what my GUI looks like: notice the repetition in each row 
This is my code:
import tkinter as tk from tkinter import simpledialog,filedialog,colorchooser,messagebox,Frame,Button from PIL import ImageTk, Image root = tk.Tk() load1 = Image.open("example.jpg") root.render1 = ImageTk.PhotoImage(load1) canv_1 = tk.Canvas(root, bg="gray") canv_1.grid_rowconfigure(0, weight=1) #canv_1.grid_columnconfigure((0, 1, 2, 3, 4, 5, 7), weight=1) canv_1.grid_columnconfigure(6, weight=2) canv_1.grid(row=0, column=0, sticky="news") canv_1.grid(row=1, column=0, sticky="news") labels = ["Image", "Chapter #", "Chapter Title", "Step", "Slide", "Sequence Step", "Instructions"] root.label_wid = [] font1 = ("arial", 15, "bold") for i in range(len(labels)): root.label_wid.append(tk.Label(canv_1, font=font1, relief="raised", text=labels[i]).grid(row=0, column=i, sticky="we")) def exportCode(): print("code exported") def change_img(row): if row == 1: root.img1 = filedialog.askopenfilename() root.load_img1 = Image.open(root.img1) root.render_img1 = ImageTk.PhotoImage(root.load_img1) R1C0['image']=root.render_img1 if row == 2: root.img2 = filedialog.askopenfilename() root.load_img2 = Image.open(root.img2) root.render_img2 = ImageTk.PhotoImage(root.load_img2) R2C0['image']=root.render_img2 if row == 3: root.img3 = filedialog.askopenfilename() root.load_img3 = Image.open(root.img3) root.render_img3 = ImageTk.PhotoImage(root.load_img3) R3C0['image']=root.render_img3 if row == 4: root.img4 = filedialog.askopenfilename() root.load_img4 = Image.open(root.img4) root.render_img4 = ImageTk.PhotoImage(root.load_img4) R3C0['image']=root.render_img4 if row == 5: root.img5 = filedialog.askopenfilename() root.load_img5 = Image.open(root.img5) root.render_img5 = ImageTk.PhotoImage(root.load_img5) R3C0['image']=root.render_img5 c1 = "#a9d08e" c2 = "#8dd1bf" # Below is the really repetitive part that I would love to simplify: ########################################################################################### # =============================================================================================== R1C0= tk.Button(canv_1, image=root.render1, relief="raised", bg="light gray", command = lambda: change_img(1)) R1C0.grid(row=1, column= 0, sticky="news") R1C1= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 1, column= 1, sticky= "news") R1C2= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 1, column= 2, sticky= "news") R1C3= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 1, column= 3, sticky= "news") R1C4= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 1, column= 4, sticky= "news") R1C5= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 1, column= 5, sticky= "news") R1C6= tk.Text(canv_1, bg="white", wrap="word", font=("arial",15), width=20, height=10) R1C6.grid(row=1, column= 6, sticky= "news") R2C0= tk.Button(canv_1, image=root.render1, relief="raised", bg="light gray", command = lambda: change_img(2)) R2C0.grid(row=2, column= 0, sticky="news") R2C1= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 2, column= 1, sticky= "news") R2C2= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 2, column= 2, sticky= "news") R2C3= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 2, column= 3, sticky= "news") R2C4= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 2, column= 4, sticky= "news") R2C5= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 2, column= 5, sticky= "news") R2C6= tk.Text(canv_1, bg="white", wrap="word", font=("arial",15), width=20, height=10) R2C6.grid(row=2, column= 6, sticky= "news") R3C0= tk.Button(canv_1, image=root.render1, relief="raised", bg="light gray", command = lambda: change_img(3)) R3C0.grid(row=3, column= 0, sticky="news") R3C1= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 3, column= 1, sticky= "news") R3C2= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 3, column= 2, sticky= "news") R3C3= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 3, column= 3, sticky= "news") R3C4= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 3, column= 4, sticky= "news") R3C5= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 3, column= 5, sticky= "news") R3C6= tk.Text(canv_1, bg="white", wrap="word", font=("arial",15), width=20, height=10) R3C6.grid(row=3, column= 6, sticky= "news") R4C0= tk.Button(canv_1, image=root.render1, relief="raised", bg="light gray", command = lambda: change_img(4)) R4C0.grid(row=4, column= 0, sticky="news") R4C1= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 4, column= 1, sticky= "news") R4C2= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 4, column= 2, sticky= "news") R4C3= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 4, column= 3, sticky= "news") R4C4= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 4, column= 4, sticky= "news") R4C5= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 4, column= 5, sticky= "news") R4C6= tk.Text(canv_1, bg="white", wrap="word", font=("arial",15), width=20, height=10) R4C6.grid(row=4, column= 6, sticky= "news") R5C0= tk.Button(canv_1, image=root.render1, relief="raised", bg="light gray", command = lambda: change_img(5)) R5C0.grid(row=5, column= 0, sticky="news") R5C1= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 5, column= 1, sticky= "news") R5C2= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 5, column= 2, sticky= "news") R5C3= tk.Entry(canv_1, bg = c1, font=("arial",15)).grid(row= 5, column= 3, sticky= "news") R5C4= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 5, column= 4, sticky= "news") R5C5= tk.Entry(canv_1, bg = c2, font=("arial",15)).grid(row= 5, column= 5, sticky= "news") R5C6= tk.Text(canv_1, bg="white", wrap="word", font=("arial",15), width=20, height=10) R5C6.grid(row=5, column= 6, sticky= "news") # ================================================================================================ bt1 = tk.Button(canv_1, text="Export", font=font1, command=exportCode).grid(row=0, column=7) load2 = Image.open("scroll-up.png") root.render2 = ImageTk.PhotoImage(load2) load3 = Image.open("scroll-down.png") root.render3 = ImageTk.PhotoImage(load3) scroll_up = tk.Button(canv_1, image=root.render2).grid(row=1, column=7, rowspan=2) # , sticky="n") scroll_up = tk.Button(canv_1, image=root.render3).grid(row=3, column=7, rowspan=2) # , sticky="s") root.mainloop() Any tips on simplifying and refactoring this would be awesome.