0

I want to create a multi-item selection drop-down in enaml.

ComboBox widget offers this but we can only select one item at a time. Same is the case with ObjectCombo widget (however slightly different in functionality from ComboBox).

Even something which closely replicates the end-functionality of being able to select multi items from a list, will be helpful, even if it's not a drop-down necessarily.

Drise
  • 4,310
  • 5
  • 41
  • 66
nstack
  • 13
  • 3

1 Answers1

1

You can use the PopupMenu and make the actions checkable.

enaml multi select menu

Like this:

#------------------------------------------------------------------------------
# Copyright (c) 2018, Nucleic Development Team.
#
# Distributed under the terms of the Modified BSD License.
#
# The full license is in the file COPYING.txt, distributed with this software.
#------------------------------------------------------------------------------
""" This example demonstrates how to popup a menu.

A menu can be popped up in 2-ways. The first is by declaring the menu as
a child of a widget and setting the 'context_menu' attribute to True. The
second method is by creating the menu on-demand, and then invoking it's
'popup()' method to show the menu at the current mouse location.


"""
from __future__ import print_function
from enaml.widgets.api import (
    Window, Container, PushButton, Menu, Action, Field
)
from enaml.core.api import Looper

enamldef PopupMenu(Menu): menu:
    attr selected = set()
    attr choices = []
    Looper:
        iterable << choices
        Action:
            text = loop_item
            triggered :: print(text + ' triggered')
            checkable = True
            checked << self.text in selected
            checked ::  selected.add(self.text) if self.checked else selected.remove(self.text)


enamldef Main(Window):
    Container:
        PushButton:
            text = 'Popup Menu'
            attr selected = set()
            clicked :: PopupMenu(selected=self.selected,
                                 choices=['foo', 'bar', 'baz', 'bam']).popup()
        Field:
            text = 'Context Menu'
            read_only = True
            PopupMenu:
                context_menu = True
                choices = ['a', 'b', 'c', 'd']
frmdstryr
  • 20,142
  • 3
  • 38
  • 32
  • yes, this will work for the question, however when making many selections, the popup has to be clicked several times, there is no way to keep it in the active state? – nstack Mar 18 '18 at 15:28
  • You can re-show the menu in the action triggered handler with `triggered :: menu.proxy.widget.show()` but it flickers between clicks as its showing/hiding. If that doesn't suite you, you probably need to implement a custom menu or modify the one here https://github.com/nucleic/enaml/blob/master/enaml/qt/qt_menu.py. You can also try to post a question here https://groups.google.com/forum/#!forum/enaml – frmdstryr Mar 18 '18 at 22:37
  • See https://stackoverflow.com/questions/2050462/prevent-a-qmenu-from-closing-when-one-of-its-qaction-is-triggered/11571550#11571550 if you want to make a custom widget – frmdstryr Mar 18 '18 at 22:54