1

I have problem with performed command by pressing button (using Tkinter).

I defined function like that:

refPt = []
cropping = False

def main(image_dir):
    def click_and_crop(event, x, y, flags, param):
       global refPt, cropping


    if event == cv2.EVENT_LBUTTONDOWN:
        refPt = [(x, y)]
        cropping = True


    elif event == cv2.EVENT_LBUTTONUP:

        refPt.append((x, y))
        cropping = False


        cv2.rectangle(image, refPt[0], refPt[1], (0, 255, 0), 2)
        cv2.imshow("image", image)

image=cv2.imread(image_dir)
print (image.dtype)
clone = image.copy()
cv2.namedWindow("image")
cv2.setMouseCallback("image", click_and_crop) 

while True:

    cv2.imshow("image", image)
    key = cv2.waitKey(1) & 0xFF


    if key == ord("r"):
        image = clone.copy()


    elif key == ord("c"):
        break


if len(refPt) == 2:
    roi = clone[refPt[0][1]:refPt[1][1], refPt[0][0]:refPt[1][0]]
    cv2.imshow("ROI", roi)
    cv2.waitKey(0)
    cv2.imwrite('template.tif',roi)

cv2.destroyAllWindows()

It works fine, when i tested it alone.

This is small part of my GUI code:

window = tkinter.Tk() window.title("Analog2Digital Transform") 
b2 =    tkinter.Button(window, text="Start", command=main('7_7026_polowa.tif'),   width=10, heigh=10)

Now, when i run my script function main()is performed before showing GUI window. Additionally, it used argument of function - main('7_7026_polowa.tif'), which is included in GUI code. Is it problem with function definition or GUI code?

adamsss
  • 69
  • 1
  • 12

2 Answers2

2

If you want to bind a function to a widget with the command parameter then you can't have the parenthesis.

command = main

Because with them it calls the functions instead. If you want to bind the function and pass in a value then you should look towards lambda

command = lambda : main('7_7026_polowa.tif')

If you are binding the function to a widget using the bind method instead of the command parameter then you need lambda to take the event object.

mywidget.bind("<ButtonRelease-1>", lambda e : function(e, value) )

OR if you are not using the event object then no need to pass it into the funciton.

mywidget.bind("<ButtonRelease-1>", lambda e : function(value) )
Steven Summers
  • 5,079
  • 2
  • 20
  • 31
0
b2 =tkinter.Button(window, text="Start", command=main('7_7026_polowa.tif'),   width=10, heigh=10)

main is executed when the button is created because of the parens "()", and command=the return value. Also height is misspelled. Use partial to pass a value to a function, and command=function --> no parens when you want to call a function without passing a value.

from functools import partial
...
b2=tkinter.Button(window, text="Start", command=partial(main, '7_7026_polowa.tif'),
                  width=10, height=10)