I have a pandas database with slides and text named "df_slides". I would like to make a tkinter GUI to click through the slides and display the text, like that:
This is what I have implemented so far:
import tkinter
from PIL import Image, ImageTk
import base64
import pandas as pd
i = 0
def load_next_img():
global pil_image, tk_image, i, text
i = i+1
base64string = df_slides["Slide_Image"][i]
imgdata = base64.b64decode(base64string)
pil_image = Image.open(io.BytesIO(imgdata))
tk_image = ImageTk.PhotoImage(pil_image)
label['image'] = tk_image
text = df_slides["Text"][i]
def load_previous_img():
global pil_image, tk_image, i, text
i = i-1
base64string = df_slides["Slide_Image"][i]
imgdata = base64.b64decode(base64string)
pil_image = Image.open(io.BytesIO(imgdata))
tk_image = ImageTk.PhotoImage(pil_image)
label['image'] = tk_image
text = df_slides["Text"][i]
root = tkinter.Tk()
label = tkinter.Label(root)
label.pack(side = "bottom", fill = "both", expand = "yes")
load_next_img()
nextbutton = tkinter.Button(text="next", command=load_next_img)
nextbutton.pack()
backbutton = tkinter.Button(text="back", command=load_previous_img)
backbutton.pack()
T = tkinter.Text(root, height=10, width=30)
T.pack()
T.insert(tkinter.END, text)
root.mainloop()
This is the current result:
As you can see the text does not use the full width and more importantly it does not update together with the slide when I press "next" and "back". The slide updates but the text stays the same all the time.
T.insert(tkinter.END, text) must appear in the functions load_next_img and load_previous_img. For me the easiest way is to define a class 'Slides' to get the namespace right. Note to update the label use self.label.configure(image=tk_image)
Below an example where I have commented out the dataframe but should give a hint on how to resolve. Note to clear the text I have also added a line self.T.delete('1.0', tkinter.END)
import tkinter
from PIL import Image, ImageTk
import base64
import pandas as pd
class Slides:
def __init__(self):
self.text_array = ['hello there', 'good bye']
self.pic_array = ['test_1.jpg', 'test_2.jpg']
self.root = tkinter.Tk()
nextbutton = tkinter.Button(text="next", command=self.load_next_img)
nextbutton.pack()
backbutton = tkinter.Button(text="back", command=self.load_previous_img)
backbutton.pack()
self.slide_image = tkinter.Label(self.root)
self.slide_image.pack(side="bottom", fill="both", expand="yes")
self.text_box = tkinter.Text(self.root, height=10, width=30)
self.text_box.pack()
self.i = -1
self.load_next_img()
self.root.mainloop()
def load_next_img(self):
self.i += 1
# base64string = df_slides["Slide_Image"][i]
# imgdata = base64.b64decode(base64string)
pil_image = Image.open(self.pic_array[self.i % 2])
pil_image = pil_image.resize((200, 200), Image.ANTIALIAS) # just for my convenience
tk_image = ImageTk.PhotoImage(image=pil_image)
self.slide_image.configure(image=tk_image)
self.slide_image.image = tk_image
text = self.text_array[self.i % 2]
self.text_box.delete('1.0', tkinter.END)
self.text_box.insert(tkinter.END, text)
def load_previous_img(self):
self.i -= 1
# base64string = df_slides["Slide_Image"][i]
# imgdata = base64.b64decode(base64string)
pil_image = Image.open(self.pic_array[self.i % 2])
pil_image = pil_image.resize((200, 200), Image.ANTIALIAS) # just for my convenience
tk_image = ImageTk.PhotoImage(image=pil_image)
self.slide_image.configure(image=tk_image)
self.slide_image.image = tk_image
text = self.text_array[self.i % 2]
self.text_box.delete('1.0', tkinter.END)
self.text_box.insert(tkinter.END, text)
def main():
slides = Slides()
if __name__ == '__main__':
main()
To get the positioning right for the buttons, label and text I would advice to use grid, rather than pack.
PS. I took the liberty to change the variables label to slide_image and T to text_box
Related
I have bunch of links and labels in list to view those I want to make a image viewer with next, previous functionality. My links and labels for respective images are in list. Up to now I had tried this :
urls=[url,url1,url2,url3]
labels=["label 1","label 2","label 3","label 4"]
images=[]
for ur in urls:
raw_data = urllib.request.urlopen(ur).read()
im = Image.open(io.BytesIO(raw_data))
image = ImageTk.PhotoImage(im)
images.append(image)
Now I have images ready in images and now I want to display it in image viewer but only last image is visible in image viewer.
Label(root).grid(row=1,column=1)
for i in range(len(images)):
image_label=Label(root,image=images[i])
image_label.grid(row=1,column=2)
name=Label(root,text=labels[i])
name.grid(row=2,column=2)
def left():
image_label=Label(root,image=images[i-1])
image_label.grid(row=1,column=2)
def right():
image_label=Label(root,image=images[i+1])
image_label.grid(row=1,column=2)
left_button=Button(root,text="Left",command=left)
left_button.grid(row=2,column=1)
right_button=Button(root,text="Right",command=right)
right_button.grid(row=2,column=3)
Right button is not working and left button is working but for one time only. When I click left button second time then nothing is working.
Error while clicking in right button :
line 45, in right
image_label=Label(root,image=images[i+1])
IndexError: list index out of range
The code is pretty close to original posted example.
There is no lambda in Button, just straight forward command that gives access to left and right functions.
The name label is unnecessary as label objects already have a text attribute so I've integrated image and text into single label and increased the font size.
label compound is used to control where the image is display relative to the text, I've chosen top. That is, the image will be place above the text.
The use of global in functions keeps track of count
from tkinter import Tk, Label, Frame, Button
from PIL import ImageTk, Image
import io
import requests
import urllib
root = Tk()
urls = [url, url1, url2, url3]
labels = ["label 1","label 2","label 3","label 4"]
count = -1
images = []
for ur in urls:
raw_data = urllib.request.urlopen( ur ).read()
im = Image.open(io.BytesIO( raw_data ))
image = ImageTk.PhotoImage(im)
images.append(image)
def left( ):
global count
count = (count - 1) % len(images)
image_label.config(image = images[count], text = labels[count])
def right( ):
global count
count = (count + 1) % len(images)
image_label.config(image = images[count], text = labels[count])
image_label = Label(
root, image = images[count], font = "Helvetica 20 normal",
text = labels[count], compound = "top")
image_label.grid(row = 0, column = 0, columnspan = 2, sticky = "nsew")
Button(
root, text = "<< LEFT", command = left).grid( row = 1, column = 0, sticky = "ew")
Button(
root, text = "RIGHT >>", command = right).grid(row = 1, column = 1, sticky = "ew")
right( ) # display first image
root.mainloop()
Here's a way to do it by showing and hiding pairs of Labels with the image and it name on them. For development and testing purposes, it loads the images from disk instead of downloading them, but you can easily replace that with what you have in your question.
from pathlib import Path
from PIL import Image, ImageTk
from tkinter import Button, Tk, Label
root = Tk()
root.title('Image Viewer')
# Create thumbnails of all the images.
image_folder = '/path/to/image/folder'
images = []
for filepath in Path(image_folder).iterdir():
img = Image.open(filepath)
w, h = img.size
if w > h:
f = 100 / w
nw, nh = 100, int(f*h)
else:
f = 100 / h
nw, nh = int(f*w), 100
# Offsets to center thumbnail within (100, 100).
woff, hoff = (100-nw) // 2, (100-nh) // 2
img = img.resize((nw, nh), Image.BICUBIC) # Shrink so largest dimen is 100.
thumbnail = Image.new('RGBA', (100, 100), (255, 255, 255, 0)) # Blank.
thumbnail.paste(img, (woff, hoff)) # Offset keep it centered.
images.append(ImageTk.PhotoImage(thumbnail))
names = ['Name 1', 'Name 2', 'Name 3', 'Name 4']
def get_images():
"""Create all image and name Label pairs but initially hidden."""
global image_labels, name_labels
image_labels, name_labels = [], []
for i, (img, name) in enumerate(zip(images, names)):
image_label = Label(root, image=img)
image_label.grid(row=1, column=2)
image_labels.append(image_label)
name_label = Label(root, text=name)
name_label.grid(row=2, column=2)
name_labels.append(name_label)
hide(i)
def hide(i):
"""Hide specified image and name pair."""
image_labels[i].grid_remove()
name_labels[i].grid_remove()
def show(i):
"""Unhide specified image and name pair."""
image_labels[i].grid()
name_labels[i].grid()
def shift(direction):
"""Display the image and pair before or after the current one that is
`direction` steps away (usually +/-1).
"""
global current
hide(current)
current = (current + direction) % len(images)
show(current)
left_button = Button(root, text="Left", command=lambda: shift(-1))
left_button.grid(row=2, column=1)
right_button = Button(root, text="Right", command=lambda: shift(+1))
right_button.grid(row=2, column=3)
get_images()
current = 0 # Currently displayed image.
show(current)
root.mainloop()
Screenshot of it running:
Should just update a image label when shift left or right, not create a new label.
Using modulus % to find which one next turn.
To reduce code and executable, I use the image data in PySimpleGUI and simple name for image here.
import tkinter as tk
import PySimpleGUI as sg
def shift(num):
global index
index = (index + num) % size
label1.configure(image=images[index])
label2.configure(text =labels[index])
root = tk.Tk()
images = [tk.PhotoImage(data=image) for image in sg.EMOJI_BASE64_HAPPY_LIST]
size = len(images)
labels = [f'Image {i:0>2d}' for i in range(size)]
index = 0
label1 = tk.Label(root, image=images[index])
label1.grid(row=1, column=2)
label2 = tk.Label(root, text=labels[index])
label2.grid(row=2, column=2)
button1 = tk.Button(root, text="<LEFT", width=6, anchor='center', command=lambda num=-1:shift(num))
button1.grid(row=1, column=1)
button2 = tk.Button(root, text="RIGHT>", width=6, anchor='center', command=lambda num=+1:shift(num))
button2.grid(row=1, column=3)
root.mainloop()
You can try this :
from tkinter import Tk,Label,Button
from PIL import ImageTk,Image
import io
import requests
import urllib
root=Tk()
count=0 # To know the current image and label
urls=[url,url1,url2,url3]
labels=["label 1","label 2","label 3","label 4"]
images=[]
for ur in urls:
raw_data = urllib.request.urlopen(ur).read()
im = Image.open(io.BytesIO(raw_data))
image = ImageTk.PhotoImage(im)
images.append(image)
def change(direction): # Function to change image
global count
if direction=="left":
if count<=0:
count=len(urls)-1
else:
count-=1
else:
if count>=len(urls)-1:
count=0
else:
count+=1
name.config(text=labels[count])
image_label.config(image=images[count])
Label(root).grid(row=1,column=1)
image_label=Label(root,image=images[count])
image_label.grid(row=1,column=2)
left_button=Button(root,text="Left",command=lambda : change("left"))
left_button.grid(row=2,column=1)
name=Label(root,text=labels[count])
name.grid(row=2,column=2)
right_button=Button(root,text="Right",command=lambda : change("right"))
right_button.grid(row=2,column=3)
root.mainloop()
I am working on a project on tkinter python.
This is how my graphic interface looks like:
And I have this database.txt:
ChickenCurry,Rice,Curry,Chicken,0.ppm
ChocolateCake,Chocolate,Flour,Sugar,Eggs,1.ppm
BolognesePasta,Pasta,Beef,TomatoeSauce,Cheese,2.ppm
Really simple. 0.ppm, 1.ppm and 2.ppm are the name of 3 images, the first one is the image of chicken curry the second one of chocolate and the last one of bolognese pasta.
My project: I would like to display the image of the chicken dish when I am clicking on the button ChickenCurry, the image of the chocolate cake when I am clicking on the chocolate cake, etc...
Here is my code:
import sys
from tkinter import *
import tkinter as tk
from PIL import Image
class Application(tk.Frame):
x = 2
def __init__(self, param = None, i = None, master=None):
super().__init__(master)
self.master = master
self.pack()
self.create_widgets()
def create_widgets(self):
if (self.x == 2):
param = "coucou"
self.hi_there = tk.Label(self)
self.hi_there["text"] = param
#self.hi_there["command"] = self.say_hi
self.hi_there.pack(side="top")
self.quit = tk.Button(self, text="QUIT", fg="red",
command=self.master.destroy)
self.quit.pack(side="bottom")
# Opening file in read format
File = open('data.txt',"r")
if(File == None):
print("File Not Found..")
else:
while(True):
# extracting data from records
record = File.readline()
if (record == ''): break
data = record.split(',')
print('Name of the dish:', data[0])
self.hi_there = tk.Button(self)
self.hi_there["text"] = data[0]
self.hi_there["command"] = self.photoOfTheDish
self.hi_there.pack(side="top")
# printing each record's data in organised form
for i in range(1, len(data)-1):
print('Ingredients:',data[i])
self.hi_there = tk.Label(self)
self.hi_there["text"] = data[i]
self.hi_there.pack(side="top")
File.close()
def photoOfTheDish(self):
novi = Toplevel()
self.canvas = Canvas(novi, width = 1500, height = 1000)
self.canvas.pack(expand = YES, fill = BOTH)
File = open('data.txt',"r")
with open('data.txt') as f:
record = File.readline()
data = record.split(',')
gif1 = PhotoImage(file = data[-1].rstrip('\n'))
#image not visual
self.canvas.create_image(50, 10, image = gif1, anchor = NW)
#assigned the gif1 to the canvas object
self.canvas.gif1 = gif1
root = tk.Tk()
root.geometry("5000x2000")
app = Application(master=root)
app.mainloop()
My issue is whatever the button I am clicking on, it's always the image corresponding to "0.ppm" which is displaying. I don't know how to link the button to his set of value from the database.
Inside photoOfTheDish(), you open data.txt and read only the first line to get the image filename. Therefore you always get the 0.ppm.
You can use lambda to pass the image filename to photoOfTheDish() when creating the buttons:
def create_widgets(self):
...
else:
while True:
...
# extracting data from records
record = File.readline().rstrip() # strip out the trailing newline
...
# pass image filename to callback
self.hi_there["command"] = lambda image=data[-1]: self.photoOfTheDish(image)
...
...
def photoOfTheDish(self, image):
novi = Toplevel()
self.canvas = Canvas(novi, width = 1500, height = 1000)
self.canvas.pack(expand = YES, fill = BOTH)
self.canvas.gif1 = PhotoImage(file=image)
self.canvas.create_image(50, 10, image=self.canvas.gif1, anchor=NW)
I have this forward arrow button, which when clicked should display the next image in the picturesList. The initial image works fine, but the moment I click the forward button I get this.
Before Clicking
After Clicking:
I am adding the entire code, because I can't really understand where the problem actually is, apologies for it.
from tkinter import *
from PIL import ImageTk, Image
import os
def moveForward():
global currImageIndex
global imgLabel
currImageIndex += 1
imgLabel.grid_forget()
print(picturesList)
img = ImageTk.PhotoImage(Image.open(picturesList[currImageIndex]))
imgLabel = Label(root,image=img)
imgLabel.grid(row=0,column=1)
picturesList = []
for pictures in os.listdir('images'):
if pictures.startswith('img'):
picturesList.append('images/'+pictures)
currImageIndex = 0
root = Tk()
img = ImageTk.PhotoImage(Image.open("images/img5.jpg"))
imgLabel = Label(image=img)
imgLabel.grid(row=0,column=1)
backwardImg = ImageTk.PhotoImage(Image.open("images/backward.ico"))
backButton = Button(image=backwardImg,width=80,height=80,relief=FLAT)
backButton.grid(row=0,column=0)
forwardImg = ImageTk.PhotoImage(Image.open("images/forward.ico"))
forwardButton = Button(image=forwardImg, width=80, height=80, relief=FLAT, command=moveForward)
forwardButton.grid(row=0,column=2)
root.mainloop()
Keep a reference to the image
from tkinter import *
from PIL import ImageTk, Image
import os
def moveForward():
global current_img
global currImageIndex
global imgLabel
currImageIndex += 1
imgLabel.grid_forget()
print(picturesList)
img = ImageTk.PhotoImage(Image.open(picturesList[currImageIndex]))
current_img = img
imgLabel = Label(root,image=img)
imgLabel.grid(row=0,column=1)
picturesList = []
#Here is the variable where the reference will be stored
current_img = None
for pictures in os.listdir('images'):
if pictures.startswith('img'):
picturesList.append('images/'+pictures)
currImageIndex = 0
root = Tk()
img = ImageTk.PhotoImage(Image.open("images/img5.jpg"))
imgLabel = Label(image=img)
imgLabel.grid(row=0,column=1)
backwardImg = ImageTk.PhotoImage(Image.open("images/backward.ico"))
backButton = Button(image=backwardImg,width=80,height=80,relief=FLAT)
backButton.grid(row=0,column=0)
forwardImg = ImageTk.PhotoImage(Image.open("images/forward.ico"))
forwardButton = Button(image=forwardImg, width=80, height=80, relief=FLAT, command=moveForward)
forwardButton.grid(row=0,column=2)
root.mainloop()
I am currently trying to make a simple Jukebox/Music Player in Python and ran into some concerns with class inheritance and tkinter's listBox method.
I have to two classes JukeboxGUI and JukeboxContent (the content one is incomplete). The JukeboxContent class inherits the JukeboxGUI:
import os
import pygame
#from PIL import Image
from tkinter.filedialog import askdirectory
from tkinter import *
import eyed3
class JukeboxGUI:
def __init__(self, window):
self.photo = PhotoImage(file = "//Users//nukhbahmajid//Desktop//Jukebox//background2.gif")
self.canvas = Canvas(width = 1000, height = 1000, bg = "black")
self.label = Label(self.canvas, text = "Jukebox")
self.listBox = Listbox(self.canvas)
self.playPauseButton = Button(self.canvas, text = "Play / Pause")
self.nextButton = Button(self.canvas, text = "Next Song")
self.previousButton = Button(self.canvas, text = "Previous Song")
self.stopButton = Button(self.canvas, text = "Stop")
self.labelVar = StringVar()
self.songLabel = Label(self.canvas, textvariable = self.labelVar, width = 20)
def constructButtons(self):
self.canvas.pack()
self.canvas.create_image(0,0, image = self.photo, anchor = NW)
self.label = self.canvas.create_window(325, 40, anchor = NW, window = self.label)
self.listBox = self.canvas.create_window(270, 80, anchor = NW, window = self.listBox)
self.playPauseButton = self.canvas.create_window(110, 120, anchor = NW, window = self.playPauseButton)
self.nextButton = self.canvas.create_window(500, 120, anchor = NW, window = self.nextButton)
self.previousButton = self.canvas.create_window(500, 180, anchor = NW, window = self.previousButton)
self.stopButton = self.canvas.create_window(130, 183, anchor = NW, window = self.stopButton)
self.songLabel = self.canvas.create_window(268, 268, anchor = NW, window = self.songLabel)
class JukeboxContent(JukeboxGUI):
def __init__(self, window):
#JukeboxGUI.__init__(self, window)
super(JukeboxContent, self).__init__(window)
listOfSongs = []
songTitles = []
num_songs = len(songTitles)
self.index = 1
self.listOfSongs = listOfSongs
self.songTitles = songTitles
self.directoryAsk = askdirectory()
self.num_songs = num_songs
self.Error_NoMP3s = "No \".mp3\" files found."
def directoryChooser(self):
self.directoryAsk
os.chdir(self.directoryAsk)
for files in os.listdir(self.directoryAsk):
if files.endswith(".mp3"):
realdir = os.path.realpath(files)
audioTag = eyed3.load(realdir)
self.songTitles.append(audioTag.tag.title)
self.listOfSongs.append(files)
print(files) ## comment out or remove later
print("These are the Song titles:", self.songTitles) #check if the list gets appended
for items in self.songTitles:
self.listBox.insert(END, items) ## the list doesn't get inserted into the listbox
pygame.mixer.init()
pygame.mixer.music.load(self.listOfSongs[0])
self.labelVar.set(self.songTitles[0])
print("The label variable:", self.labelVar) ## the variable isn't set either
print("The label is accessible:", self.songLabel) ## songLabel doesn't get updated
pygame.mixer.music.play() # the song doesn't play
if __name__ == "__main__":
window = Tk()
window.geometry("700x500+450+200")
window.title("Jukebox")
constructGUI = JukeboxGUI(window)
constructGUI.constructButtons()
initiateJukebox = JukeboxContent(window)
initiateJukebox.directoryChooser()
window.mainloop()
When I try to access the attributes of the parent class, like inserting the songs into the list box, there isn't an error here specifically, but the list isn't into the box either
Secondly, when I update the label variable and songLabel, and try to print out later to see if it was implemented, the following gets printed to the terminal:
The label variable: PY_VAR1
The label is accessible: .!canvas2.!label2
The song doesn't play either. What could be the problem? Please help me out! Here's a picture of the interface if it helps:
JukeboxInterface
i have a small ui programm and i need to display a calendar in it or a date picker . (NOTE : userid and password is root")**
i have tried this code :
from Tkinter import *
from PIL import Image, ImageTk
import ttkcalendar
class App():
def __init__(self):
pass
root = Tk()
root.configure(bg='black')
root.attributes('-alpha', 0.0)
def mainWindow(self):
self.root.geometry('{}x{}'.format(600,400))
self.root.attributes('-alpha', 1)
self.root.configure(bg='#404040')
self.ttkcal = ttkcalendar.Calendar(self.root,firstweekday=calendar.SUNDAY)
self.ttkcal.pack()
self.root.wm_title("time sheet management system")
# Create the toolbar as a frame
self.toolbar = Frame(self.root, borderwidth=1, relief='raised')
self.toolbar.configure( bg = '#838383')
# Load all the images first as PNGs and use ImageTk to convert
# them to usable Tkinter images.
self.img1 = Image.open('NewIcon.png')
self.useImg1 = ImageTk.PhotoImage(self.img1)
self.img2 = Image.open('LoadIcon.png')
self.useImg2 = ImageTk.PhotoImage(self.img2)
self.img3 = Image.open('SaveIcon.png')
self.useImg3 = ImageTk.PhotoImage(self.img3)
# Set up all the buttons for use on the toolbars.
newBtn = Button(self.toolbar, image=self.useImg1, command=self.callback)
newBtn.pack(side=LEFT, fill=X)
loadBtn = Button(self.toolbar, image=self.useImg2, command=self.callback)
loadBtn.pack(side=LEFT, fill=X)
saveBtn = Button(self.toolbar, image=self.useImg3, command=self.callback)
saveBtn.pack(side=LEFT, fill=X)
# Add the toolbar
self.toolbar.pack(side=TOP, fill=X)
"""
#create a frame
self.infoArea= Frame(self.root, borderwidth=2,height=40,width=100, relief='raised',bg='red')"""
self.root.mainloop()
"""
# Set up a Text box and scroll bar.
self.scrollbar = Scrollbar(self.root)
self.scrollbar.pack(side=RIGHT, fill=Y)
self.text = Text(self.root)
self.text.pack()
self.text.config(yscrollcommand=self.scrollbar.set)
self.scrollbar.config(command=self.text.yview)"""
def loginClick(self):
self.userid = self.txt1.get()
self.password = self.txt2.get()
print self.userid,self.password
if self.password == 'root' and self.userid == 'root':
self.wi.destroy()
self.mainWindow()
def callback(self):
print "A button was pressed"
def login(self):
self.wi = Toplevel (self.root)
#self.wi.geometry('{}x{}'.format(200,200))
self.wi.configure(bg='#404040')
self.wi.overrideredirect(1)
self.wi.update_idletasks()
self.w = self.wi.winfo_screenwidth()
self.h = self.wi.winfo_screenheight()
self.size = tuple(int(_) for _ in self.wi.geometry().split('+')[0].split('x'))
self.x = self.w/2 - self.size[0]/2
self.y = self.h/2 - self.size[1]/2
self.wi.geometry("%dx%d+%d+%d" % (self.size + (self.x, self.y)))
self.wi.geometry('{}x{}'.format(400,200))
self.frame1 = Frame ( self.wi,bg='#404040' )
self.frame1.pack(side=BOTTOM,fill=X)
self.butt1 = Button(self.frame1,text= "Cancel" , bg = '#838383',fg='white',command = self.wi.destroy)
self.butt1.pack(side=RIGHT,padx=1)
self.butt2 = Button(self.frame1,text= "Login" ,bg = '#838383',fg='white',command = self.loginClick)
self.butt2.pack(side=RIGHT)
"""self.frame2 = Frame ( self.wi,bg='green' )
self.frame2.pack(side=BOTTOM,fill=BOTH)"""
self.lab1 = Label (self.wi,text='UserID',bg='#404040',fg='white')
#self.lab1.pack(side=LEFT,padx=60,pady=20)
self.lab1.place(x=60,y=20)
self.lab2 = Label (self.wi,text='Password',bg='#404040',fg='white')
#self.lab1.pack(side=LEFT,padx=60,pady=20)
self.lab2.place(x=60,y=60)
self.txt1 = Entry( self.wi)
self.txt1.place(x=140,y=20)
self.txt2 = Entry( self.wi,show='*')
self.txt2.place(x=140,y=60)
"""
self.label = Label(self.wi,text="UserID",bg='#838383',fg='white')
self.label.place("""
self.wi.mainloop()
if __name__ == "__main__":
a = App()
#a.root.mainloop()
a.login()
but it is giving error that "name calendar not defined". how can i solve this ?
or is there any other way to implement a calendar or date picker in tkinter.
The code is using calendar module, but it is not importing the module.
self.ttkcal = ttkcalendar.Calendar(self.root, firstweekday=calendar.SUNDAY)
^^^^^^^^^^^^^^^
Simply adding following import statement will solve the problem.
import calendar