diff --git a/artiq/dashboard/applets_ccb.py b/artiq/dashboard/applets_ccb.py index c51f8b70c..963855a6b 100644 --- a/artiq/dashboard/applets_ccb.py +++ b/artiq/dashboard/applets_ccb.py @@ -16,6 +16,35 @@ class AppletsCCBDock(applets.AppletsDock): sep.setSeparator(True) self.table.addAction(sep) + ccbp_group_menu = QtWidgets.QMenu() + actiongroup = QtWidgets.QActionGroup(self.table) + actiongroup.setExclusive(True) + self.ccbp_group_none = QtWidgets.QAction("No policy", self.table) + self.ccbp_group_none.setCheckable(True) + self.ccbp_group_none.triggered.connect(lambda: self.set_ccbp("")) + ccbp_group_menu.addAction(self.ccbp_group_none) + actiongroup.addAction(self.ccbp_group_none) + self.ccbp_group_ignore = QtWidgets.QAction("Ignore requests", self.table) + self.ccbp_group_ignore.setCheckable(True) + self.ccbp_group_ignore.triggered.connect(lambda: self.set_ccbp("ignore")) + ccbp_group_menu.addAction(self.ccbp_group_ignore) + actiongroup.addAction(self.ccbp_group_ignore) + self.ccbp_group_create = QtWidgets.QAction("Create applets", self.table) + self.ccbp_group_create.setCheckable(True) + self.ccbp_group_create.triggered.connect(lambda: self.set_ccbp("create")) + ccbp_group_menu.addAction(self.ccbp_group_create) + actiongroup.addAction(self.ccbp_group_create) + self.ccbp_group_enable = QtWidgets.QAction("Create and enable applets", + self.table) + self.ccbp_group_enable.setCheckable(True) + self.ccbp_group_enable.triggered.connect(lambda: self.set_ccbp("enable")) + ccbp_group_menu.addAction(self.ccbp_group_enable) + actiongroup.addAction(self.ccbp_group_enable) + self.ccbp_group_action = QtWidgets.QAction("Group CCB policy", self.table) + self.ccbp_group_action.setMenu(ccbp_group_menu) + self.table.addAction(self.ccbp_group_action) + self.table.itemSelectionChanged.connect(self.update_group_ccbp_menu) + ccbp_global_menu = QtWidgets.QMenu() actiongroup = QtWidgets.QActionGroup(self.table) actiongroup.setExclusive(True) @@ -33,12 +62,35 @@ class AppletsCCBDock(applets.AppletsDock): self.ccbp_global_enable.setCheckable(True) ccbp_global_menu.addAction(self.ccbp_global_enable) actiongroup.addAction(self.ccbp_global_enable) - - ccbp_global_action = QtWidgets.QAction( - "Client control broadcast policy (global)", self.table) + ccbp_global_action = QtWidgets.QAction("Global CCB policy", self.table) ccbp_global_action.setMenu(ccbp_global_menu) self.table.addAction(ccbp_global_action) + def update_group_ccbp_menu(self): + selection = self.table.selectedItems() + if selection: + item = selection[0] + if item.ty == "applet": + item = item.parent() + if item is None: + self.ccbp_group_action.setEnabled(False) + else: + self.ccbp_group_action.setEnabled(True) + print(item, item.ty) + ccbp = self.table.itemWidget(item, 1).text() + if ccbp == "": + self.ccbp_group_none.setChecked(True) + else: + getattr(self, "ccbp_group_" + ccbp).setChecked(True) + else: + self.ccbp_group_action.setEnabled(False) + + def set_ccbp(self, ccbp): + item = self.table.selectedItems()[0] + if item.ty == "applet": + item = item.parent() + self.table.itemWidget(item, 1).setText(ccbp) + def get_ccpb_global(self): if self.ccbp_global_ignore.isChecked(): return "ignore" @@ -47,6 +99,29 @@ class AppletsCCBDock(applets.AppletsDock): if self.ccbp_global_enable.isChecked(): return "enable" + def get_ccpb(self, group): + if group is None: + group = [] + elif isinstance(group, str): + group = [group] + ccbp = self.get_ccpb_global() + parent = self.table.invisibleRootItem() + for g in group: + new_parent = None + for i in range(parent.childCount()): + child = parent.child(i) + if child.ty == "group" and child.text(0) == g: + c_ccbp = self.table.itemWidget(child, 1).text() + if c_ccbp: + ccbp = c_ccbp + new_parent = child + break + if new_parent is None: + return ccbp + else: + parent = new_parent + return ccbp + def locate_applet(self, name, group, create_groups): if group is None: group = [] @@ -77,7 +152,7 @@ class AppletsCCBDock(applets.AppletsDock): return parent, applet def ccb_create_applet(self, name, command, group=None, code=None): - ccbp = self.get_ccpb_global() + ccbp = self.get_ccpb(group) if ccbp == "ignore": return parent, applet = self.locate_applet(name, group, True) @@ -93,7 +168,7 @@ class AppletsCCBDock(applets.AppletsDock): applet.setCheckState(0, QtCore.Qt.Checked) def ccb_disable_applet(self, name, group=None): - ccbp = self.get_ccpb_global() + ccbp = self.get_ccpb(group) if ccbp != "create": return parent, applet = self.locate_applet(name, group, False) diff --git a/artiq/gui/applets.py b/artiq/gui/applets.py index 86b6eecf7..66c011bea 100644 --- a/artiq/gui/applets.py +++ b/artiq/gui/applets.py @@ -502,7 +502,7 @@ class AppletsDock(QtWidgets.QDockWidget): parent.addChild(item) return item - def new_group(self, name=None, parent=None): + def new_group(self, name=None, attr="", parent=None): if name is None: name = self.get_untitled() item = QtWidgets.QTreeWidgetItem([name]) @@ -522,7 +522,7 @@ class AppletsDock(QtWidgets.QDockWidget): parent.addChild(item) # HACK: make the cell non-editable. Qt doesn't even provide # a clean API for such a basic feature. - self.table.setItemWidget(item, 1, QtWidgets.QLabel()) + self.table.setItemWidget(item, 1, QtWidgets.QLabel(attr)) return item def new_with_parent(self, cb, **kwargs): @@ -605,9 +605,10 @@ class AppletsDock(QtWidgets.QDockWidget): state.append(("applet", uid, enabled, name, spec, geometry)) elif cwi.ty == "group": name = cwi.text(0) + attr = self.table.itemWidget(cwi, 1).text() expanded = cwi.isExpanded() state_child = self.save_state_item(cwi) - state.append(("group", name, expanded, state_child)) + state.append(("group", name, attr, expanded, state_child)) else: raise ValueError return state @@ -629,8 +630,8 @@ class AppletsDock(QtWidgets.QDockWidget): if enabled: item.setCheckState(0, QtCore.Qt.Checked) elif wis[0] == "group": - _, name, expanded, state_child = wis - item = self.new_group(name, parent=parent) + _, name, attr, expanded, state_child = wis + item = self.new_group(name, attr, parent=parent) item.setExpanded(expanded) self.restore_state_item(state_child, item) else: