Version 12 of flexmenu

Updated 2018-09-21 21:44:18 by bll

flexmenu

Source: https://gentoo.com/tcl/flexmenu.tcl (version 1.2)

bll 2018-9-20: An alternative menu system.

2018-9-21: There seems to be a little interest in this (6 downloads so far, Germany, Croatia, Japan, Netherlands, Switzerland (the bots have not found it yet)). I wrote it for a couple of rather minor reasons (one of which I'm not sure is valid). Though I do really like having real checkbuttons and radiobuttons in the menu, and I like the -keepopen option. I have not tried using it in my production code as yet.

If you have interest in using this, let me know, and I will create a sourceforge project so that tickets can be submitted.

 Version History
   1.2 2018-9-21
       Fixed -padx/-pady so they will work for the main menubar
       Set the -acceleratorprefix to \u2318 for Mac OS X.
         This is converted to 'Meta' (hope that's right).
       Changed default -acceleratorprefix to 'Alt-' (due to mac os x changes).
       Fixed the colors on mac os x.  Dark mode and graphite themes
         are supported.
       Documentation
   1.1 2018-9-20
       Fixed active highlight for scrolled menus
   1.0 2018-9-20
       initial release

Disadvantages:

Does not work with .toplevel configure -menu .mymenu. Tk uses the internal menu API to attach menus. flexmenu cannot work with the -menu option.

Must use pack or grid (or place) to attach the menu. Converting an existing program to use flexmenu could be quite painful.

The main menu must be created with either -type menubar or -type menuleft.

It has not been tested much.

Features:

  • Checkbuttons and Radiobuttons are ttk widgets.
  • Supports left side menus (-type menuleft).
  • Scrolling menus (-maxheight).
  • Configure -columnbreak <value> at the menu level to automatically break every <value> items.
  • -keepopen option will leave the menu open after invoking an item.
  • -acceleratorfont, -acceleratorforeground and -acceleratoractiveforeground options.
  • -activerelief option.
  • -hidearrows option.
  • -hideaccelerators option.
  • -acceleratorprefix option to set the default accelerator prefix.
  • -padx, -pady options to change the padding for menu items.
  • Uses ttk widgets where possible.
  • Is a little more dynamic than the standard menu. Many things can be reconfigured and the changes will be picked up.

Item Features:

  • Any widget can be put into the menu (.mymenu add widget -widget .mymenu.mycombobox).
  • Margin images (-marginimage). It is quite common nowadays to use small icons on the left margin of the menu as an aid for the user.
  • Accelerator labels are automatically generated based on either an & prefix in the label, the -underline option, or the -accelerator option.
  • Accelerator bindings are automatically generated.
  • -activerelief option.

Notes:

Ignored: -bitmap, -tearoff, -tearoffcommand, -title, -selectcolor.

-hidemargin works properly on a per-entry basis. menu seems to treat it as a menu option even though it is specified per entry. I think -hidemargin would be better off as a menu option rather than an item option, but backwards compatibility is an issue.

Problems:

May be overeager in generating accelerator labels. The user may not want accelerator labels displayed for every item.

Has not been tested much.

At this time, flexmenu does not check to see if the entire menu is visible, and does not do any relocation of the menu.

Known Issues:

Fixed in 1.1: Active item highlighting for scrolling menus is not working right.

Fixed in 1.2: The accelerator key prefix is set to Alt. This needs to be set correctly for Mac OS X, but I do not recall which meta key the Mac sends.

The clone command has only a very basic implementation.

Flicker with -selectimage. Currently, the menu layout is reapplied when a -image is changed to a -selectimage. This is just in case the -selectimage is a different size. If the assumption can be made that the image sizes are identical, this redraw could be removed.

Example:

package require Tk
source flexmenu.tcl

# standard checkbutton widgets
# -keepopen set
flexmenu .mcb -keepopen true
.mcb add checkbutton -variable ::x -text Check -onvalue 0 -offvalue 1 \
    -accelerator Ctrl-4
.mcb add checkbutton -variable ::x -text Check -onvalue 0 -offvalue 1 \
    -accelerator Ctrl-5 -indicatoron false
.mcb add checkbutton -variable ::x -text Check -onvalue 0 -offvalue 1 \
    -state disabled

# standard radiobutton widgets
flexmenu .mrb -keepopen true
.mrb add radiobutton -variable ::x -value 0 -text Radio-0 \
    -accelerator Ctrl-2
.mrb add radiobutton -variable ::x -value 1 -text Radio-1 \
    -accelerator Ctrl-3
.mrb add radiobutton -variable ::x -value 2 -text Radio-2 \
    -accelerator Ctrl-4 -state disabled

# automatic column break every fifth item.
# frame widgets in the menu
set clist {#000000 #ff0000 #00ff00 #0000ff #ff8000 #ff0080 #80ff00
    #00ff80 #8000ff #0080ff #ffff00 #ff00ff #00ffff #ffff80 #ff80ff
    #80ffff #ffffff #ff4040 #40ff40 #4040ff #404040 #808080 #ffff40
    #ff40ff #40ffff}
set col [flexmenu .col -columnbreak 5]
set count 0
foreach {c} $clist {
  set tf [frame .col.x$c \
      -background $c -relief raised -borderwidth 2 \
      -width 20 -height 20 ]
  .col add widget -widget $tf -hidemargin 1
  incr count
}

# scrolling menu
# frame widgets in the menu
set clist {#000000 #ff0000 #00ff00 #0000ff #ff8000 #ff0080 #80ff00
    #00ff80 #8000ff #0080ff #ffff00 #ff00ff #00ffff #ffff80 #ff80ff
    #80ffff #ffffff #ff4040 #40ff40 #4040ff #404040 #808080 #ffff40
    #ff40ff #40ffff}
set colsc [flexmenu .colsc -keepopen true -maxheight 5]
foreach {c} $clist {
  set tf [frame .colsc.bbb$c \
      -background $c -relief raised -borderwidth 2 \
      -width 20 -height 20 ]
  .colsc add widget -widget $tf -hidemargin 1
}

# combobox widget
flexmenu .mw 
ttk::combobox .mw.cb -values {aa bb cc dd ee ff gg} \
    -textvariable ::y -state readonly -width 5
.mw add widget -widget .mw.cb

# main cascade
flexmenu .m
.m add cascade -menu .col -label {Colors}
.m add cascade -menu .colsc -label {Scrolling Colors}
.m add cascade -menu .mcb -label {Check Buttons}
.m add cascade -menu .mrb -label {Radio Buttons}
.m add cascade -menu .mw -label {Widgets}
.m add command -label E&xit -command exit

flexmenu .mtop -type menubar
.mtop add cascade -label Test -menu .m
.mtop add command -label E&xit -command exit
pack .mtop -side top -fill x -expand 1 -anchor nw
frame .f -width 200 -height 200 
pack .f