Skip to main content
Made answer more specific and clear
Source Link
Kartikeya
  • 837
  • 2
  • 8
  • 12

So the question is, how do I make it so when middle-clicking, it opens the first menu AND then automatically runs the cascade, as if it was clicked?

Considering this answer by Bryan Oakley and the documentation available on the internet, there is no way for making a menu and a submenu visible simultaneously. "That's just not how Tkinter menus are designed to work."

You will have to create a customized menu bar without using the widget tk.Menu.


When I middle-click, I tried to make it so it displays both the menus (my_menu, my_menu2), but my attempt just displays both but with the first menu overlapping, so the other doesn't show.

They are not overlapping. Even if you add some gap to the x-y values using some integers, still you won't be seeing the second menu.

The reason is that using tk_popup or post will make the menu appear on the screen for sure, but then the program's focus gets shifted to the user's mouse and keyboard. So, until the user clicks out of the focus of that menu, the program won't be coming out to execute the next lines of the function (in which you are calling the tk_popup for the submenu.)

Here you can see what I mean:

import tkinter as tk root = tk.Tk() root.geometry("500x400") def contextMenu(e, openCascade=False):   my_menu2 = tk.Menu(root, tearoff=False) my_menu2.add_command(label="command2") my_menu = tk.Menu(root, tearoff=False) my_menu.add_cascade(label="cascade1", menu=my_menu2) my_menu.add_command(label="command1") print("Before my_menu popup") my_menu.tk_popup(e.x_root, e.y_root) print("After my_menu popup") if openCascade: print("Before my_menu2 popup") my_menu2.tk_popup(e.x_root+30, e.y_root+50) #added some gap to show they are not overlapping print("After my_menu2 popup") root.bind("<Button-3>", contextMenu) root.bind("<Button-2>", lambda e: contextMenu(e,True)) root.mainloop() 

So, when you are middle-clicking (< Button-2> bind), the output is:

Before my_menu popup 

my_menu is visible on the screen. Then, when the user clicks out of the focus of that menu, the my_menu disappears you get the following output:

After my_menu popup Before my_menu2 popup After my_menu2 popup 

The submenu appears on the screen but due to clicking out, the new focus is on the root and the submenu disappears in less than a second.

So the question is, how do I make it so when middle-clicking, it opens the first menu AND then automatically runs the cascade, as if it was clicked?

Considering this answer by Bryan Oakley and the documentation available on the internet, there is no way for making a menu and a submenu visible simultaneously. "That's just not how Tkinter menus are designed to work."


When I middle-click, I tried to make it so it displays both the menus (my_menu, my_menu2), but my attempt just displays both but with the first menu overlapping, so the other doesn't show.

They are not overlapping. Even if you add some gap to the x-y values using some integers, still you won't be seeing the second menu.

The reason is that using tk_popup or post will make the menu appear on the screen for sure, but then the program's focus gets shifted to the user's mouse and keyboard. So, until the user clicks out of the focus of that menu, the program won't be coming out to execute the next lines of the function (in which you are calling the tk_popup for the submenu.)

Here you can see what I mean:

import tkinter as tk root = tk.Tk() root.geometry("500x400") def contextMenu(e, openCascade=False):   my_menu2 = tk.Menu(root, tearoff=False) my_menu2.add_command(label="command2") my_menu = tk.Menu(root, tearoff=False) my_menu.add_cascade(label="cascade1", menu=my_menu2) my_menu.add_command(label="command1") print("Before my_menu popup") my_menu.tk_popup(e.x_root, e.y_root) print("After my_menu popup") if openCascade: print("Before my_menu2 popup") my_menu2.tk_popup(e.x_root+30, e.y_root+50) #added some gap to show they are not overlapping print("After my_menu2 popup") root.bind("<Button-3>", contextMenu) root.bind("<Button-2>", lambda e: contextMenu(e,True)) root.mainloop() 

So, when you are middle-clicking (< Button-2> bind), the output is:

Before my_menu popup 

my_menu is visible on the screen. Then, when the user clicks out of the focus of that menu, the my_menu disappears you get the following output:

After my_menu popup Before my_menu2 popup After my_menu2 popup 

The submenu appears on the screen but due to clicking out, the new focus is on the root and the submenu disappears in less than a second.

So the question is, how do I make it so when middle-clicking, it opens the first menu AND then automatically runs the cascade, as if it was clicked?

Considering this answer by Bryan Oakley and the documentation available on the internet, there is no way for making a menu and a submenu visible simultaneously. "That's just not how Tkinter menus are designed to work."

You will have to create a customized menu bar without using the widget tk.Menu.


When I middle-click, I tried to make it so it displays both the menus (my_menu, my_menu2), but my attempt just displays both but with the first menu overlapping, so the other doesn't show.

They are not overlapping. Even if you add some gap to the x-y values using some integers, still you won't be seeing the second menu.

The reason is that using tk_popup or post will make the menu appear on the screen for sure, but then the program's focus gets shifted to the user's mouse and keyboard. So, until the user clicks out of the focus of that menu, the program won't be coming out to execute the next lines of the function (in which you are calling the tk_popup for the submenu.)

Here you can see what I mean:

 . . . my_menu.add_command(label="command1") print("Before my_menu popup") my_menu.tk_popup(e.x_root, e.y_root) print("After my_menu popup") if openCascade: print("Before my_menu2 popup") my_menu2.tk_popup(e.x_root+30, e.y_root+50) #added some gap to show they are not overlapping print("After my_menu2 popup") root.bind("<Button-3>", contextMenu) root.bind("<Button-2>", lambda e: contextMenu(e,True)) root.mainloop() 

So, when you are middle-clicking (< Button-2> bind), the output is:

Before my_menu popup 

my_menu is visible on the screen. Then, when the user clicks out of the focus of that menu, the my_menu disappears you get the following output:

After my_menu popup Before my_menu2 popup After my_menu2 popup 

The submenu appears on the screen but due to clicking out, the new focus is on the root and the submenu disappears in less than a second.

Source Link
Kartikeya
  • 837
  • 2
  • 8
  • 12

So the question is, how do I make it so when middle-clicking, it opens the first menu AND then automatically runs the cascade, as if it was clicked?

Considering this answer by Bryan Oakley and the documentation available on the internet, there is no way for making a menu and a submenu visible simultaneously. "That's just not how Tkinter menus are designed to work."


When I middle-click, I tried to make it so it displays both the menus (my_menu, my_menu2), but my attempt just displays both but with the first menu overlapping, so the other doesn't show.

They are not overlapping. Even if you add some gap to the x-y values using some integers, still you won't be seeing the second menu.

The reason is that using tk_popup or post will make the menu appear on the screen for sure, but then the program's focus gets shifted to the user's mouse and keyboard. So, until the user clicks out of the focus of that menu, the program won't be coming out to execute the next lines of the function (in which you are calling the tk_popup for the submenu.)

Here you can see what I mean:

import tkinter as tk root = tk.Tk() root.geometry("500x400") def contextMenu(e, openCascade=False): my_menu2 = tk.Menu(root, tearoff=False) my_menu2.add_command(label="command2") my_menu = tk.Menu(root, tearoff=False) my_menu.add_cascade(label="cascade1", menu=my_menu2) my_menu.add_command(label="command1") print("Before my_menu popup") my_menu.tk_popup(e.x_root, e.y_root) print("After my_menu popup") if openCascade: print("Before my_menu2 popup") my_menu2.tk_popup(e.x_root+30, e.y_root+50) #added some gap to show they are not overlapping print("After my_menu2 popup") root.bind("<Button-3>", contextMenu) root.bind("<Button-2>", lambda e: contextMenu(e,True)) root.mainloop() 

So, when you are middle-clicking (< Button-2> bind), the output is:

Before my_menu popup 

my_menu is visible on the screen. Then, when the user clicks out of the focus of that menu, the my_menu disappears you get the following output:

After my_menu popup Before my_menu2 popup After my_menu2 popup 

The submenu appears on the screen but due to clicking out, the new focus is on the root and the submenu disappears in less than a second.