How can i add a tooltip to menu item? How can i add a tooltip to menu item? tkinter tkinter

How can i add a tooltip to menu item?


Question: add a tooltip to menu item

I'm not aware to bind to a Menu Item.

The following class MenuTooltip use the Event <Motion> to find the Menu Item if the Pointer y-Position is inside a Menu Items .yposition.


class MenuTooltip(tk.Menu):    def __init__(self, parent):        """        :param parent: The parent of this Menu, either 'root' or 'Menubar'         .tooltip == List of tuple (yposition, text)         .tooltip_active == Index (0-based) of the active shown Tooltip         Bind events <Leave>, <Motion>        """        super().__init__(parent, tearoff=0)        self.tooltip = []        self.tooltip_active = None        self.bind('<Leave>', self.leave)        self.bind('<Motion>', self.on_motion)    def add_command(self, *cnf, **kwargs):        tooltip = kwargs.get('tooltip')        if tooltip:            del kwargs['tooltip']        super().add_command(*cnf, **kwargs)        self.add_tooltip(len(self.tooltip), tooltip)    def add_tooltip(self, index, tooltip):        """        :param index: Index (0-based) of the Menu Item         :param tooltip: Text to show as Tooltip        :return: None        """        self.tooltip.append((self.yposition(index) + 2, tooltip))    def on_motion(self, event):        """        Loop .tooltip to find matching Menu Item        """        for idx in range(len(self.tooltip) - 1, -1, -1):            if event.y >= self.tooltip[idx][0]:                self.show_tooltip(idx)                break    def leave(self, event):        """        On leave, destroy the Tooltip and reset .tooltip_active to None        """        if not self.tooltip_active is None:            print('leave()'.format())            # destroy(<tooltip_active>)            self.tooltip_active = None    def show_tooltip(self, idx):        """        Show the Tooltip if not already shown, destroy the active Tooltip        :param idx: Index of the Tooltip to show        :return: None         """        if self.tooltip_active != idx:            # destroy(<tooltip_active>)            self.tooltip_active = idx            print('{}'.format(self.tooltip[idx][1]))

Usage:

class App(tk.Tk):    def __init__(self):        super().__init__()        menu = MenuTooltip(self)        menu.add_command(label='Help 1', tooltip='\tToolTip.Help 1')        menu.add_command(label='Help 2', tooltip='\tToolTip.Help 2')        self.menubar.add_cascade(label="Help", menu=menu)if __name__ == "__main__":    App().mainloop()

Tested with Python: 3.5

Note: Couldn't test with Python 2.7, please report back if it works with 2.7