Button in one class, methods in another one - Printable Version +- Python Forum (https://python-forum.io) +-- Forum: Python Coding (https://python-forum.io/forum-7.html) +--- Forum: GUI (https://python-forum.io/forum-10.html) +--- Thread: Button in one class, methods in another one (/thread-19693.html) |
Button in one class, methods in another one - alan9979 - Jul-10-2019 Hi, I spent 2 days trying to solve this little exercice, creating a face with button open or closing his mouth. I do have 2 questions about this code :
RE: Button in one class, methods in another one - metulburr - Jul-10-2019 That is not the best way to interact classes with each other. The best solution would be to make the Face object in the canvas class like this: from tkinter import * class Button_Can(Frame): def __init__(self): Frame.__init__(self) self.larg,self.haut=200,200 self.can=Canvas(self.master,width=self.larg,height=self.haut,bg='ivory') self.can.pack() self.face = Face(self.can) self.b1=Button(self.master,text='Open it !',command=self.face.openMouth) self.b2=Button(self.master,text='Close it !',command=self.face.closeMouth) self.b1.pack(side=RIGHT) self.b2.pack(side=LEFT) class Face(): def __init__(self, can): self.can = can self.setup() def setup(self): self.can.delete(ALL) cc =[[100, 100, 80, 'red'],[70, 70, 15, 'blue'], [130, 70, 15, 'blue'],[70, 70, 5, 'black'], [130, 70, 5, 'black'],[44, 115, 20, 'red'], [156, 115, 20, 'red'],[100, 95, 15, 'purple']] i =0 while i < len(cc): el = cc[i] self.circle(el[0], el[1], el[2], el[3]) i += 1 self.opened_mouth = None self.closed_mouth = None def circle(self,x, y, r, coul ='black'): "Draw a circle center x,y radius r " self.can.create_oval(x-r, y-r, x+r, y+r, outline=coul) def openMouth(self): #self.can.delete(self.closed_mouth) self.setup() self.opened_mouth=self.circle(100, 145, 30, 'purple') def closeMouth(self): #self.can.delete(self.opened_mouth) self.setup() self.closed_mouth=self.can.create_line(80,145,120,145,fill='purple') root = Tk() A=Button_Can() B=Face(A.can) root.mainloop()NOTE: I am more use to pygame's redraw everything style... every frame, so i am not sure if tkinter has a method to just delete a portion of the canvas or not. So i just redrew everything. RE: Button in one class, methods in another one - alan9979 - Jul-10-2019 Thanks for your very fast reply metulburr, I am still trying to erase just the mouth. But I don't understand why my erase methode, using what you said above, doesn't work : When I click the erase button, nothing happens, no error message either. from tkinter import * class C1(Frame): def __init__(self): Frame.__init__(self) self.larg,self.haut=100,100 self.can=Canvas(self.master,width=self.larg,height=self.haut,bg='ivory') self.can.pack() self.c2=C2(self.can) self.b1=Button(self.master,text='Erase',command=self.c2.erase) self.b1.pack() class C2(): def __init__(self,can): self.can=can self.redline=self.can.create_line(10, 10, 90, 90, fill ='red',width=5) def erase(self): self.can.delete(self.redline) root = Tk() A=C1() canevas =A.can B=C2(canevas) root.mainloop() RE: Button in one class, methods in another one - metulburr - Jul-11-2019 You are creaing two objects with C2 class. One inside C1 on line 9, and another at line 27. Comment out the line 27 one. What is happening is you are creating two lines overlapping each other, where one only has access to delete it. from tkinter import * class C1(Frame): def __init__(self): Frame.__init__(self) self.larg,self.haut=100,100 self.can=Canvas(self.master,width=self.larg,height=self.haut,bg='ivory') self.can.pack() self.c2=C2(self.can) self.b1=Button(self.master,text='Erase',command=self.c2.erase) self.b1.pack() class C2(): def __init__(self,can): self.can=can self.redline=self.can.create_line(10, 10, 90, 90, fill ='red',width=5) def erase(self): self.can.delete(self.redline) root = Tk() A=C1() canevas =A.can #B=C2(canevas) root.mainloop() RE: Button in one class, methods in another one - joe_momma - Jul-11-2019 The easiest way to control or work with objects in tkinter is to use tags. I don't see the need for 2 classes here from tkinter import Tk,Frame,Canvas,Button,RIGHT,LEFT class Button_Can(Frame): def __init__(self): Frame.__init__(self) self.pack(expand='yes',fill='both') self.larg,self.haut=200,200 self.can=Canvas(self.master,width=self.larg,height=self.haut,bg='ivory') self.can.pack() self.b1=Button(self.master,text='Open it !',command=self.openMouth) self.b2=Button(self.master,text='Close it !',command=self.closeMouth) self.b3=Button(self.master,text='delete it!',command=self.delete_mouth) self.b1.pack(side=RIGHT) self.b2.pack(side=LEFT) self.b3.pack(side='bottom') self.setup() def setup(self): cc =[[100, 100, 80, 'red'],[70, 70, 15, 'blue'], [130, 70, 15, 'blue'],[70, 70, 5, 'black'], [130, 70, 5, 'black'],[44, 115, 20, 'red'], [156, 115, 20, 'red'],[100, 95, 15, 'purple']] i =0 while i < len(cc): el = cc[i] self.circle(el[0], el[1], el[2], el[3]) i += 1 def circle(self,x, y, r, coul ='black'): "Draw a circle center x,y radius r " self.can.create_oval(x-r, y-r, x+r, y+r, outline=coul) def openMouth(self): self.can.delete('bouche') self.opened_mouth= self.can.create_oval(70, 115, 130, 175, outline='purple',tag='bouche') def closeMouth(self): self.can.delete('bouche') self.closed_mouth=self.can.create_line(80,145,120,145, fill='purple', tag='bouche') def delete_mouth(self): self.can.delete('bouche') if __name__ == '__main__': root = Tk() root.title('la visage') A=Button_Can() root.mainloop() |