Python 3.5 och Tkinter binda musklick till label [LÖST]

C, C++, Pascal, Assembly, Raspberry, Java, Matlab, Python, BASIC, SQL, PHP, etc.
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Python 3.5 och Tkinter binda musklick till label [LÖST]

Inlägg av Magnus_K »

Hej hej,

Jag försöker få till så att när jag högerklickar på label1 så ökas variablen counter med 50.
När jag kör koden och högerklickar på labeln så får jag felet:
TypeError: rightClick() takes 0 positional arguments but 1 was given
Exception in Tkinter callback


Är det någon här som har en aning om vad som är tok och kan det här?

Kod: Markera allt

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import tkinter as tk
button1_flag = True
counter=0

def click1():
    
    global button1_flag
    # toggle between picture and no picture
    if button1_flag:
       button1.config(image=photo1)
       button1_flag = False
    else:
       button1.config(image=pixel, width=100, height=100)
       button1_flag = True
       
def rightClick():
    counter+=50

root = tk.Tk()
# create a frame and pack it
frame1 = tk.Frame(root, bg="black")
frame1.pack(side=tk.TOP, fill=tk.X)
# Resizing image
from PIL import Image
from PIL import ImageTk
image1 = Image.open('/home/pi/Todo_list/16489823.jpg')
image1 = image1.resize((100, 100), Image.ANTIALIAS)
photo1 = ImageTk.PhotoImage(image1)
# create the image button
pixel = tk.PhotoImage(width=1, height=1)
button1 = tk.Button(frame1, compound=tk.TOP, bg="black", highlightbackground="white", activebackground="#373635", image=pixel, width=100, height=100, command=click1)
label1 = tk.Label(frame1, textvariable=counter, width=10, height=5)

label1.bind("<Button-3>", rightClick)

#button1.pack(padx=10, pady=10)
button1.grid(row=0, column=0, padx=5, pady=5)
label1.grid(row=0, column=1, padx=5, pady=5)

# save the button's image from garbage collection (needed?)
button1.image = photo1

# start the event loop
root.mainloop()
Senast redigerad av Magnus_K 9 januari 2020, 16:33:43, redigerad totalt 1 gång.
Shimonu
Inlägg: 294
Blev medlem: 21 oktober 2015, 22:44:33

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Shimonu »

Det är inte så att click1 ska ta en 'self' parameter också?
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

Joo, har läst lite om det men jag är så himla grön så jag förstår inte vad detta "self" är, och vart det ska in.
XorXaX
Inlägg: 409
Blev medlem: 27 maj 2004, 09:44:16

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av XorXaX »

Det skickas med en event parameter när du klickar. Så din funktion rightClick behöver kunna ta emot det.

def rightClick(event) :
...

https://www.python-course.eu/tkinter_events_binds.php

.
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

M,, det här är nog bra. Behöver läsa på lite.
När jag placerade event inom parantesen så fick jag tillbaka UnboundLocalError: local variable 'counter' referenced before assignment

Ska läsa igenom den länken nu och se om jag blir något klokare. :tumupp:
Shimonu
Inlägg: 294
Blev medlem: 21 oktober 2015, 22:44:33

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Shimonu »

I right_click behöver du säga att counter är global
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

Snyggt!
Inte för att jag riktigt förstår varför jag gör det i en funktion.
I andra språk har man deklarerat sånt först i koden, dock ser jag att det är gjort så på andra ställen.

Koden körs nu utan fel men labeltexten syns inte. Vet inte heller om counter uppdateras med 50.
Känns som att inte labeln "uppdateras" vid varje tryck, utan den laddas först och sen är den statisk.

EDIT: Oooo, ser att det är så nära. Variablen uppdateras som den ska i debuggern, bara att det inte visas i labeln!
EDIT2: Det här var mig en himla nöt att knäcka... svårsökt också!

Ps. Ledsen om jag fräser ur mig frågor men är verkligen inte bra med kod Ds.
kabelhaerva
Inlägg: 93
Blev medlem: 11 september 2010, 09:41:58
Ort: Gbg

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av kabelhaerva »

Saxat från stackoverflow:
You'll want to set the label's textvariable with a StringVar; when the StringVar changes (by you calling myStringVar.set("text here")), then the label's text also gets updated. And yes, I agree, this is a strange way to do things.

See the Tkinter Book for a little more information on this:

You can associate a Tkinter variable with a label. When the contents of the variable changes, the label is automatically updated:

v = StringVar()
Label(master, textvariable=v).pack()

v.set("New Text!")
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

Ja det är nära!

I.o.m att det är en int så fanns det tydligen IntVar() istället.
Försöker använda det likadant som i ditt exempel men får varning om Invalid syntax +=.
Det förstår jag om det hade varit en string men som en int så borde det ju gå.

Kod: Markera allt

def rightClick(event):
    global counter
    counter = tk.IntVar()
    counter.set(counter+=50)
Zkronk
Inlägg: 1423
Blev medlem: 23 augusti 2005, 16:44:36
Ort: Uppsala

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Zkronk »

Något i den här stilen kanske kan fungera?

Kod: Markera allt

counter = tk.IntVar()

def rightClick(event):
    global counter
    counter.set(counter.get() + 50)
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

Precis. Är ungefär där också med en del surfande. Försöker även att uppdatera labeln manuellt som nedan.
Både in och min kod genererar dock AttributeError: 'NoneType' object has no attribute '_root'

Kod: Markera allt

    counter = tk.IntVar()
     
    def rightClick(event):
        global counter
        counter.set(counter.get() + 50)
        label1.configure(textvariable=counter)
Så här ser mitt testprogram ut för att bryta ner den här funktionen till så liten beståndsdel som möjligt.
Den genererar bara ett fönster med en grå ruta i. Högerklickar man så dyker "50" upp i rutan men sen händer inget mer.

Kod: Markera allt

import tkinter as tk
counter = 0
      
def rightClick(event):
    
    global counter
    counter = tk.IntVar()
    counter.set(counter.get() + 50)
    label1.configure(textvariable=counter)

root = tk.Tk()
# create a frame and pack it
frame1 = tk.Frame(root, bg="black")
frame1.pack(side=tk.TOP, fill=tk.X)

label1 = tk.Label(frame1, textvariable=counter, width=10, height=5)
label1.bind('<Button-3>', rightClick)

label1.grid(row=0, column=0, padx=5, pady=5)

# start the event loop
root.mainloop()
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

Nähä, jag får fasen inte till det.
Att det skulle vara så svårt... Får köra manuell uppdatering av siffrorna istället.
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av Magnus_K »

Nu fick jag i ordning på det!

Vet inte riktigt vad skillnaden är men har struntat i allt vad IntVar() heter och kör siffran som en String (samt lite andra mindre ändringar).

Kod: Markera allt

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import tkinter as tk

counter = 0
      
def rightClick(event):
    
    global counter
    counter += 50
    label1.configure(text=str(counter))


root = tk.Tk()
# create a frame and pack it
frame1 = tk.Frame(root, bg="black")
frame1.pack(side=tk.TOP, fill=tk.X)
# Resizing image

label1 = tk.Label(frame1, text=counter, width=10, height=5)
label1.bind('<Button-3>', rightClick)


#button1.pack(padx=10, pady=10)
label1.grid(row=0, column=0, padx=5, pady=5)

# start the event loop
root.mainloop()
Användarvisningsbild
swesysmgr
Inlägg: 14127
Blev medlem: 28 mars 2009, 06:56:43
Ort: Göteborg

Re: Python 3.5 och Tkinter binda musklick till label

Inlägg av swesysmgr »

Jag hade provat:

Kod: Markera allt

self.counter=0

def rightClick(self, event)
    self.counter+=1

label1.bind('<Button-3>', self.rightClick)
Antar button 3 är makro för musknapp höger?

Det där med att dribbla runt med globaler hade jag inte litat på. Dokumentationen för Tk i Python lämnar väldigt mycket i övrigt att önska så fort man skall göra något mer avancerat.
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Python 3.5 och Tkinter binda musklick till label [LÖST]

Inlägg av Magnus_K »

Testade även som du skrev men det blev någon varning om att self inte var deklarerat (eller något sånt).
Är så ofin så jag låter det vara som jag postade innan ditt inlägg. Det fungerade även utmärkt i den skarpa filen.

Ja precis Button 1, 2 eller 3 är makron för vänster, mitten och höger musknapp.

Tack för all hjälp i all fall!
Skriv svar