Exemple #1
0
    def __init__(self, parent, client, **settings):
        QMainWindow.__init__(self, parent)
        self.client = client
        self.setWindowTitle(' ')  # window title is unnecessary
        flags = self.windowFlags()
        flags |= Qt.WindowStaysOnTopHint
        flags ^= Qt.WindowMinimizeButtonHint
        self.setWindowFlags(flags)

        self.sgroup = SettingGroup('EstopTool')
        with self.sgroup as settings:
            self.restoreGeometry(settings.value('geometry', '', QByteArray))

        icon = QIcon(':/estop')
        icon.addFile(':/estopdown', mode=QIcon.Active)
        self.btn = PicButton(icon, self)

        widget = QWidget(self)
        layout = QHBoxLayout()
        layout.addWidget(self.btn)
        layout.setContentsMargins(3, 3, 3, 3)
        widget.setLayout(layout)
        self.setCentralWidget(widget)
        self.btn.clicked.connect(self.dostop)
        self.setFixedSize(self.minimumSize())
        self.show()
Exemple #2
0
    def loadNicosData(self):
        while self.topLevelItemCount() > 0:
            self.takeTopLevelItem(0)

        # list of topLevelItems representing the directories in
        # nicos_*: for example instruments, ...
        self.topLevelItems = []
        for directory in setupcontroller.setup_directories:
            self.topLevelItems.append(
                QTreeWidgetItem([directory], ItemTypes.Directory))
        self.addTopLevelItems(self.topLevelItems)

        # ask the controller to return the setups for current directory
        # add the setups as childitems
        for setup_directory in self.topLevelItems:
            # directories can neither be dragged nor have something dropped on
            setup_directory.setFlags(setup_directory.flags()
                                     & ~Qt.ItemIsDragEnabled
                                     & ~Qt.ItemIsDropEnabled)
            setup_directory.setIcon(
                0, QIcon(path.join(getResDir(), 'folder.png')))
            for setup in setupcontroller.setup_directories[
                    setup_directory.text(0)]:
                treeWidgetItem = QTreeWidgetItem([setup.name], ItemTypes.Setup)
                # scripts cannot be dragged, but they can have
                # something dropped on them (a device).
                treeWidgetItem.setFlags(treeWidgetItem.flags()
                                        & ~Qt.ItemIsDragEnabled)
                treeWidgetItem.setIcon(
                    0, QIcon(path.join(getResDir(), 'setup.png')))
                treeWidgetItem.setup = setup
                setup_directory.addChild(treeWidgetItem)

            # setup for this directory has been loaded, add the devices.
            currentIndex = 0
            while currentIndex < setup_directory.childCount():
                currentItem = setup_directory.child(currentIndex)
                setup = currentItem.setup
                devices = setup.devices.keys()
                for device in devices:
                    # read setup and add all the devices as child tree items
                    deviceItem = QTreeWidgetItem([device], ItemTypes.Device)
                    # devices can be dragged, but they can't have something
                    # dropped on them.
                    deviceItem.setFlags(deviceItem.flags()
                                        & ~Qt.ItemIsDropEnabled)
                    deviceItem.device = setup.devices[device]
                    currentItem.addChild(deviceItem)

                # icons for all devices
                deviceIndex = 0
                while deviceIndex < currentItem.childCount():
                    currentItem.child(deviceIndex).setIcon(
                        0, QIcon(path.join(getResDir(), 'device.png')))
                    deviceIndex += 1
                currentIndex += 1

        self.setSortingEnabled(True)
        self.sortByColumn(0, Qt.AscendingOrder)
Exemple #3
0
    def __init__(self, parent, client, **configs):
        QDialog.__init__(self, parent)
        DlgUtils.__init__(self, self.toolName)
        loadUi(self, 'tools/downtime.ui')
        self.sendBtn = self.buttonBox.addButton('&Send',
                                                QDialogButtonBox.AcceptRole)
        self.sendBtn.setIcon(QIcon(':/mail'))
        self.sendBtn.setDisabled(True)

        self.parentwindow = parent
        self.client = client
        if hasattr(parent, 'mainwindow'):
            self.mainwindow = parent.mainwindow
            self.log = NicosLogger(self.toolName)
            self.log.parent = self.mainwindow.log
        else:
            self.log = configs.get('log', None)
        self.sgroup = SettingGroup(self.toolName)

        self._sender = configs.get('sender', '*****@*****.**')
        self._receiver = configs.get('receiver', '*****@*****.**')
        self._mailserver = configs.get('mailserver', '') or \
            self._getDeviceComponent('experiment', 'mailserver', 'smtp.frm2.tum.de')
        self._instrument = configs.get('instrument', '') or \
            self._getDeviceComponent('instrument', 'instrument', 'DEMO')
        t = self.mailheaderText.text().replace('{{instrument}}',
                                               self._instrument)
        self.mailheaderText.setText(t)

        self.startDown.setDateTime(QDateTime.currentDateTime().addSecs(-3600))
        self.endDown.setDateTime(QDateTime.currentDateTime())
        self.errorText.setVisible(False)
        with self.sgroup as settings:
            self.loadSettings(settings)
        self.reasons.clearEditText()
Exemple #4
0
 def createWindow(self, wtype):
     # for the history_wintype or editor_wintype
     if wtype == -1:
         return self
     try:
         wconfig = self.gui_conf.windows[wtype]
     except IndexError:
         # config outdated, window type doesn't exist
         return
     if wtype in self.windows:
         window = self.windows[wtype]
         window.activateWindow()
         return window
     window = AuxiliaryWindow(self, wtype, wconfig)
     if window.centralLayout.count():
         window.setWindowIcon(QIcon(':/' + wconfig.icon))
         self.windows[wtype] = window
         window.closed.connect(self.on_auxWindow_closed)
         for panel in window.panels:
             panel.updateStatus(self.current_status)
         window.show()
         return window
     else:
         del window
         return None
Exemple #5
0
    def newDeviceAddedSlot(self, deviceName, _classString):
        setupItem = self.getCurrentSetupItem()
        if setupItem.setup.abspath not in self.setupWidgets.keys():
            self.loadSetup(setupItem.setup, setupItem.parent().text(0))

        uncombinedModule = _classString.split('.')
        classname = uncombinedModule.pop()
        module = '.'.join(uncombinedModule)
        classes = inspect.getmembers(classparser.modules[module],
                                     predicate=inspect.isclass)
        _class = [_class[1] for _class in classes if _class[0] == classname][0]
        parameters = {
            key: ''
            for key in _class.parameters.keys()
            if _class.parameters[key].mandatory is True
        }
        device = setupcontroller.Device(deviceName,
                                        _classString,
                                        parameters=parameters)
        setupItem.setup.devices[deviceName] = device
        deviceWidget = DeviceWidget(self.setupWidgets[setupItem.setup.abspath])
        deviceWidget.editedDevice.connect(self.editedSetupSlot)
        deviceWidget.loadDevice(device)
        self.workarea.addWidget(deviceWidget)
        self.deviceWidgets[setupItem.setup.abspath][deviceName] = deviceWidget
        deviceItem = QTreeWidgetItem([deviceName], ItemTypes.Device)
        deviceItem.setFlags(deviceItem.flags() & ~Qt.ItemIsDropEnabled)
        deviceItem.device = setupItem.setup.devices[deviceName]
        deviceItem.setIcon(0, QIcon(path.join(getResDir(), 'device.png')))
        setupItem.insertChild(0, deviceItem)
        self.treeWidget.itemActivated.emit(deviceItem, 0)

        if not setupItem.setup.edited:
            setupItem.setText(0, '*' + setupItem.text(0))
            setupItem.setup.edited = True
Exemple #6
0
 def doInit(self, mode):
     CICacheClient.doInit(self, self._mode)
     self._qtapp = QApplication(sys.argv)
     self._qtapp.setOrganizationName('nicos')
     self._qtapp.setApplicationName('cacheinspector')
     self._window = MainWindow(self)
     self._window.setWindowIcon(QIcon(':/inspector'))
     session._qthandler.setStatusbar(self._window.statusBar())
Exemple #7
0
    def _create_device_item(self, devname, add_cat=False):
        ldevname = devname.lower()
        # get all cache keys pertaining to the device
        params = self.client.getDeviceParams(devname)
        if not params:
            return
        lowlevel_device = params.get('lowlevel') or False
        if lowlevel_device and not self._show_lowlevel:
            return
        if 'nicos.core.data.sink.DataSink' in params.get('classes', []) and \
           not self._show_lowlevel:
            return

        # remove still-existing previous item for the same device name
        if ldevname in self._devitems:
            self.on_client_device(('destroy', [devname]))

        cat = self._dev2setup.get(devname)
        if cat is None:  # device is not in any setup? reread setup info
            self._read_setup_info()
            cat = self._dev2setup.get(devname)
            if cat is None:  # still not there -> give up
                return

        if cat not in self._catitems:
            display_order = self._setupinfo[cat].get('display_order', 50)
            representative = self._setupinfo[cat].get('extended', {}).get(
                'representative', '').lower()
            catitem = SetupTreeWidgetItem(cat, display_order, representative)
            catitem.setToolTip(0, self._setupinfo[cat].get('description', ''))
            f = catitem.font(0)
            f.setBold(True)
            catitem.setFont(0, f)
            catitem.setIcon(0, QIcon(':/setup'))
            self._catitems[cat] = catitem
            if add_cat:
                self.tree.addTopLevelItem(catitem)
                catitem.setExpanded(True)
        else:
            catitem = self._catitems[cat]

        # create a tree node for the device
        devitem = QTreeWidgetItem(catitem, [devname, '', ''], DEVICE_TYPE)

        devitem.setForeground(0, lowlevelBrush[lowlevel_device])
        devitem.setFont(0, lowlevelFont[lowlevel_device])

        if self.useicons:
            devitem.setIcon(0, self.statusIcon[OK])
        devitem.setToolTip(0, params.get('description', ''))
        self._devitems[ldevname] = devitem
        # fill the device info with dummy values, will be populated below
        self._devinfo[ldevname] = DevInfo(devname)

        # let the cache handler process all properties
        for key, value in iteritems(params):
            self.on_client_cache(
                (0, ldevname + '/' + key, OP_TELL, cache_dump(value)))
Exemple #8
0
    def __init__(self, parent, connpresets, lastpreset, lastdata, tunnel=''):
        QDialog.__init__(self, parent)
        loadUi(self, 'dialogs/auth.ui')
        self.connpresets = connpresets
        if isinstance(lastpreset, QPyNullVariant):
            lastpreset = None

        pal = self.quickList.palette()
        pal.setColor(QPalette.Window, pal.color(QPalette.Base))
        self.quickList.setPalette(pal)

        if len(connpresets) < 3:
            self.quickList.hide()
        else:
            self.quickList.setStyleSheet('padding: 10px 5px;')
            self.quickList.clear()
            maxw = 64
            icon = QIcon(':/appicon')
            metric = QFontMetrics(self.quickList.font())
            for preset in sorted(connpresets):
                item = QListWidgetItem(preset, self.quickList)
                item.setIcon(icon)
                maxw = max(maxw, metric.width(preset))
            self.quickList.setGridSize(QSize(maxw + 8, 72))
            # the automatic sizing still leads to a vertical scrollbar
            hint = self.quickList.sizeHint()
            hint.setHeight(hint.height() + 50)
            hint.setWidth(max(4.7 * maxw, 330))
            self.quickList.setMinimumSize(hint)
            self.resize(self.sizeHint())

        self.presetOrAddr.addItems(sorted(connpresets))
        self.presetOrAddr.setEditText(lastpreset)
        if not lastpreset and lastdata:
            # if we have no stored last preset connection, put in the raw data
            self.presetOrAddr.setEditText('%s:%s' %
                                          (lastdata.host, lastdata.port))
            self.viewonly.setChecked(lastdata.viewonly)
        self.userName.setText(lastdata.user)
        self.password.setFocus()

        self.viaFrame.setHidden(not tunnel)
        if tunnel:
            host, username, password = splitTunnelString(tunnel)
            self.remotePassword.setText(password)
            if not password:
                self.remotePassword.setFocus()
            self.remoteUserName.setText(username)
            if not username:
                self.remoteUserName.setFocus()
            self.remoteHost.setText(host)
            if not host:
                self.remoteHost.setFocus()

        self.presetFrame.hide()
        self.resize(QSize(self.width(), self.minimumSize().height()))
Exemple #9
0
 def setStatus(self, status, exception=False):
     if status == self.current_status:
         return
     if self.client.last_action_at and \
        self.current_status == 'running' and \
        status in ('idle', 'paused') and \
        current_time() - self.client.last_action_at > 20:
         # show a visual indication of what happened
         if status == 'paused':
             msg = 'Script is now paused.'
         elif exception:
             msg = 'Script has exited with an error.'
         else:
             msg = 'Script has finished.'
         self.trayIcon.showMessage(self.instrument, msg)
         self.client.last_action_at = 0
     self.current_status = status
     is_connected = status != 'disconnected'
     if is_connected:
         self.actionConnect.setText('Disconnect')
         self.statusLabel.setText('\u2713 Connected')
         self.update_instrument_text()
         self.update_experiment_text()
     else:
         self.actionConnect.setText('Connect to server...')
         self.statusLabel.setText('Disconnected')
         self.setTitlebar(False)
     # new status icon
     pixmap = QPixmap(':/' + status + ('exc' if exception else ''))
     new_icon = QIcon()
     new_icon.addPixmap(pixmap, QIcon.Disabled)
     self.trayIcon.setIcon(new_icon)
     self.trayIcon.setToolTip('%s status: %s' % (self.instrument, status))
     if self.showtrayicon:
         self.trayIcon.show()
     if self.promptWindow and status != 'paused':
         self.promptWindow.close()
     # propagate to panels
     for panel in self.panels:
         panel.updateStatus(status, exception)
     for window in self.windows.values():
         for panel in window.panels:
             panel.updateStatus(status, exception)
Exemple #10
0
 def _createIcons(cls):
     # hack to make non-Qt usage as in checksetups work
     if not hasattr(cls, 'statusIcon'):
         cls.statusIcon = {
             OK: QIcon(':/leds/status_green'),
             WARN: QIcon(':/leds/status_warn'),
             BUSY: QIcon(':/leds/status_yellow'),
             NOTREACHED: QIcon(':/leds/status_red'),
             DISABLED: QIcon(':/leds/status_white'),
             ERROR: QIcon(':/leds/status_red'),
             UNKNOWN: QIcon(':/leds/status_unknown'),
         }
Exemple #11
0
 def insertItem(self, *widgets):
     item = QWidget(self.frame)
     item._widgets = widgets
     layout = QHBoxLayout()
     layout.setContentsMargins(0, 0, 0, 0)
     for widget in widgets:
         layout.addWidget(widget)
     if self.allow_reorder:
         btn = QPushButton(QIcon(':/up'), '', item)
         btn._item = item
         btn.clicked.connect(self.on_upBtn_clicked)
         layout.addWidget(btn)
         btn = QPushButton(QIcon(':/down'), '', item)
         btn._item = item
         btn.clicked.connect(self.on_downBtn_clicked)
         layout.addWidget(btn)
     btn = QPushButton(QIcon(':/remove'), '', item)
     btn._item = item
     btn.clicked.connect(self.on_removeBtn_clicked)
     layout.addWidget(btn)
     item.setLayout(layout)
     self.layout.insertWidget(self.layout.count() - 2, item)
     self.items.append(item)
Exemple #12
0
    def _newSetup(self, instrument=None):
        dlg = NewSetupDialog([
            item.text(0) for item in self.topLevelItems
            if item.type() == ItemTypes.Directory
        ], instrument)
        if dlg.exec_():
            fileName = dlg.getValue()
            if not fileName:
                QMessageBox.warning(self, 'Error', 'No setup name entered.')
                return None, None

            if not fileName.endswith('.py'):
                fileName += '.py'
            if dlg.isSpecialSetup():
                abspath = path.join(getNicosDir(), 'nicos_mlz',
                                    dlg.currentInstrument(), 'setups',
                                    'special', fileName)
            else:
                abspath = path.join(getNicosDir(), 'nicos_mlz',
                                    dlg.currentInstrument(), 'setups',
                                    fileName)
            if abspath in [
                    i.abspath for i in setupcontroller.setup_directories[
                        dlg.currentInstrument()]
            ]:
                QMessageBox.warning(self, 'Error', 'Setup already exists!')
                return None, None
            try:
                open(abspath, 'w', encoding='utf-8').close()
            except OSError:
                QMessageBox.warning(self, 'Error', 'Could not create new '
                                    'setup!')
                return None, None

            setupcontroller.addSetup(dlg.currentInstrument(), abspath)
            newSetup = None
            for setup in setupcontroller.setup_directories[
                    dlg.currentInstrument()]:
                if setup.abspath == abspath:
                    newSetup = setup
            treeWidgetItem = QTreeWidgetItem(['*' + newSetup.name],
                                             ItemTypes.Setup)
            treeWidgetItem.setFlags(treeWidgetItem.flags()
                                    & ~Qt.ItemIsDragEnabled)
            treeWidgetItem.setIcon(0, QIcon(path.join(getResDir(),
                                                      'setup.png')))
            treeWidgetItem.setup = newSetup
            treeWidgetItem.setup.edited = True
            return treeWidgetItem, dlg.currentInstrument()
        return None, None
Exemple #13
0
 def __init__(self, parent, client):
     uipath = findResource('nicos_ess/loki/gui/ui_files/table.ui')
     Cmdlet.__init__(self, parent, client, uipath)
     self.measdef = self.meas_def_class()
     self.updateTable()
     for loop in LOOPS:
         self.outerLoop.addItem(loop)
     self.outerLoop.setCurrentIndex(0)
     client.experiment.connect(self.on_client_experiment)
     self.expandBtn = QToolButton()
     self.expandBtn.setIcon(QIcon(':/down'))
     self.expandBtn.setAutoRaise(True)
     self.expandBtn.clicked.connect(self.on_expandBtn_clicked)
     self.table.setCornerWidget(self.expandBtn)
Exemple #14
0
    def createWindowContent(self):
        self.sgroup = SettingGroup('MainWindow')
        with self.sgroup as settings:
            loadUserStyle(self, settings)
            # load saved settings and stored layout for panel config
            self.loadSettings(settings)

        # create panels in the main window
        widget = createWindowItem(self.gui_conf.main_window, self, self, self,
                                  self.log)
        if widget:
            self.centralLayout.addWidget(widget)
        self.centralLayout.setContentsMargins(0, 0, 0, 0)

        # call postInit after creation of all panels
        for panel in self.panels:
            panel.postInit()

        with self.sgroup as settings:
            # geometry and window appearance
            loadBasicWindowSettings(self, settings)
            self.update()
            # load auxiliary windows state
            self.loadAuxWindows(settings)
        if len(self.splitstate) == len(self.splitters):
            for sp, st in zip(self.splitters, self.splitstate):
                sp.restoreState(st)

        if not self.gui_conf.windows:
            self.menuBar().removeAction(self.menuWindows.menuAction())
        for i, wconfig in enumerate(self.gui_conf.windows):
            action = ToolAction(self.client, QIcon(':/' + wconfig.icon),
                                wconfig.name, wconfig.options, self)
            self.toolBarWindows.addAction(action)
            self.menuWindows.addAction(action)

            def window_callback(on, i=i):
                self.createWindow(i)

            action.triggered[bool].connect(window_callback)
        if not self.gui_conf.windows:
            self.toolBarWindows.hide()
        else:
            self.toolBarWindows.show()

        createToolMenu(self, self.gui_conf.tools, self.menuTools)
        if isinstance(self.gui_conf.main_window, tabbed) and widget:
            widget.tabChangedTab(0)
Exemple #15
0
 def __init__(self, parent, client):
     uipath = findResource('nicos_mlz/kws1/gui/table.ui')
     Cmdlet.__init__(self, parent, client, uipath)
     self.measdef = self.meas_def_class(rtmode=False)
     self.rt_settings = RtConfigDialog.DEFAULT_SETTINGS.copy()
     self.rtConfBtn.setEnabled(False)
     self.updateTable()
     for loop in LOOPS:
         self.outerLoop.addItem(loop)
     self.outerLoop.setCurrentIndex(0)
     client.experiment.connect(self.on_client_experiment)
     self.expandBtn = QToolButton()
     self.expandBtn.setIcon(QIcon(':/down'))
     self.expandBtn.setAutoRaise(True)
     self.expandBtn.clicked.connect(self.on_expandBtn_clicked)
     self.table.setCornerWidget(self.expandBtn)
Exemple #16
0
    def dropEvent(self, event):
        """
        To satisfy Qt, a call to TreeWidgetContextMenu.dropEvent is neccessary.

        Else, the animation would look really gross and suggest the object
        might actually not have been copied.
        But after the call, the newly appended child item seems to be
        completely useless: It carries neither data nor does it emit the
        treeWidget's itemActivated signal.
        This may be a bug or my inability to find what's wrong.
        Because of that, I need to construct my own item, find the old one and
        replace it with my new one.
        """
        target = self.getSetupOfDropPos(event.pos())
        if self.dragItem.device.name in target.setup.devices.keys():
            QMessageBox.warning(
                self, 'Error', 'The target setup already '
                'contains a device with that name!')
            self.dragItem = None
            event.ignore()
            return
        count = 0
        previousItems = []
        while count < target.childCount():
            previousItems.append(target.child(count))
            count += 1
        TreeWidgetContextMenu.dropEvent(self, event)
        count = 0
        afterDropItems = []
        while count < target.childCount():
            afterDropItems.append(target.child(count))
            count += 1
        newItem = None
        for child in afterDropItems:
            if child not in previousItems:
                newItem = child
        index = target.indexOfChild(newItem)
        target.takeChild(index)
        deviceName = self.dragItem.device.name
        target.setup.devices[deviceName] = deepcopy(self.dragItem.device)
        deviceItem = QTreeWidgetItem([deviceName], ItemTypes.Device)
        deviceItem.setFlags(deviceItem.flags() & ~Qt.ItemIsDropEnabled)
        deviceItem.device = target.setup.devices[deviceName]
        deviceItem.setIcon(0, QIcon(path.join(getResDir(), 'device.png')))
        target.insertChild(index, deviceItem)
        self.deviceAdded.emit(target, deviceName)
        self.itemActivated.emit(deviceItem, 0)
Exemple #17
0
 def __init__(self, parent, nmin, allow_enter=False):
     QScrollArea.__init__(self, parent)
     self.setWidgetResizable(True)
     self.frame = QFrame(self)
     self.layout = QVBoxLayout()
     self.layout.setContentsMargins(2, 2, 2, 2)
     self.addBtn = QPushButton(QIcon(':/add'), '', self.frame)
     self.addBtn.clicked.connect(self.on_addBtn_clicked)
     self.addBtn.setSizePolicy(
         QSizePolicy(QSizePolicy.Fixed, QSizePolicy.Preferred))
     self.layout.addWidget(self.addBtn)
     self.layout.addStretch()
     self.frame.setLayout(self.layout)
     self.setWidget(self.frame)
     self.items = []
     self.nmin = nmin
     self.allow_enter = allow_enter
Exemple #18
0
    def __init__(self, parent, client, options):
        Panel.__init__(self, parent, client, options)
        loadUi(self, findResource('nicos_demo/demo/gui/sanspanel.ui'))

        self.current_status = None

        self._idle = QColor('#99FF99')
        self._busy = QColor(Qt.yellow)

        self.statusBar = QStatusBar(self)
        policy = self.statusBar.sizePolicy()
        policy.setVerticalPolicy(QSizePolicy.Fixed)
        self.statusBar.setSizePolicy(policy)
        self.statusBar.setSizeGripEnabled(False)
        self.layout().addWidget(self.statusBar)

        client.cache.connect(self.on_client_cache)

        run = self.buttonBox.button(QDialogButtonBox.Yes)
        run.setText('Run')
        run.setIcon(QIcon(':/continue'))
        self.buttonBox.accepted.connect(self.on_start_clicked)
Exemple #19
0
    def __init__(self):
        self._reconfiguring = False
        QMainWindow.__init__(self)
        # set app icon in multiple sizes
        icon = QIcon()
        icon.addFile(':/appicon')
        icon.addFile(':/appicon-16')
        icon.addFile(':/appicon-48')
        self.setWindowIcon(icon)

        self.keyChange.connect(lambda obj, args: obj.on_keyChange(*args))
        self.reconfigure.connect(self.do_reconfigure)

        self.sgroup = SettingGroup('Monitor')
        with self.sgroup as settings:
            # geometry and window appearance
            loadBasicWindowSettings(self, settings)
Exemple #20
0
    def __init__(self, reason, parent=None):
        QDialog.__init__(self, parent)
        loadUi(self, 'dialogs/instr_select.ui')
        icon = QIcon(':/appicon-16')
        if reason:
            self.reasonLbl.setText(reason)
        else:
            self.reasonLbl.hide()
            self.saveBox.hide()

        self.confTree.itemDoubleClicked.connect(self.handleDoubleClick)
        for entry in sorted(os.listdir(config.nicos_root)):
            full = path.join(config.nicos_root, entry)
            if not (entry.startswith('nicos_') and path.isdir(full)):
                continue
            pkgitem = QTreeWidgetItem(self.confTree, [entry])
            pkgitem.setIcon(0, icon)
            for subentry in sorted(os.listdir(full)):
                configfile = path.join(full, subentry, 'guiconfig.py')
                if not path.isfile(configfile):
                    continue
                item = QTreeWidgetItem(pkgitem, [subentry])
                item.setData(0, QTreeWidgetItem.UserType, configfile)
Exemple #21
0
 def groupIcon(self):
     return QIcon(':/setup')
Exemple #22
0
def get_icon(icon_name):
    return QIcon(path.join(icons_path, icon_name))
Exemple #23
0
    def __init__(self, log, gui_conf, viewonly=False, tunnel=''):
        QMainWindow.__init__(self)
        DlgUtils.__init__(self, 'NICOS')
        loadUi(self, self.ui)

        # set app icon in multiple sizes
        icon = QIcon()
        icon.addFile(':/appicon')
        icon.addFile(':/appicon-16')
        icon.addFile(':/appicon-48')
        self.setWindowIcon(icon)

        if tunnel and SSHTunnelForwarder is None:
            self.showError('You want to establish a connection to NICOS via '
                           "a SSH tunnel, but the 'sshtunnel' module is not "
                           'installed. The tunneling feature will disabled.')
        self.tunnel = tunnel if SSHTunnelForwarder is not None else ''
        self.tunnelServer = None

        # hide admin label until we are connected as admin
        self.adminLabel.hide()

        # our logger instance
        self.log = log

        # window for displaying errors
        self.errorWindow = None

        # window for "prompt" event confirmation
        self.promptWindow = None

        # debug console window, if opened
        self.debugConsole = None

        # log messages sent by the server
        self.messages = []

        # are we in expert mode?  (always false on startup)
        self.expertmode = False

        # no wrapping at startup
        self.allowoutputlinewrap = False

        # set-up the initial connection data
        self.conndata = ConnectionData(host='localhost',
                                       port=1301,
                                       user='******',
                                       password=None,
                                       viewonly=viewonly)

        # state members
        self.current_status = None

        # connect the client's events
        self.client = NicosGuiClient(self, self.log)
        self.client.error.connect(self.on_client_error)
        self.client.broken.connect(self.on_client_broken)
        self.client.failed.connect(self.on_client_failed)
        self.client.connected.connect(self.on_client_connected)
        self.client.disconnected.connect(self.on_client_disconnected)
        self.client.status.connect(self.on_client_status)
        self.client.showhelp.connect(self.on_client_showhelp)
        self.client.clientexec.connect(self.on_client_clientexec)
        self.client.plugplay.connect(self.on_client_plugplay)
        self.client.watchdog.connect(self.on_client_watchdog)
        self.client.prompt.connect(self.on_client_prompt)

        # data handling setup
        self.data = DataHandler(self.client)

        # panel configuration
        self.gui_conf = gui_conf
        self.initDataReaders()
        self.mainwindow = self

        # determine if there is an editor window type, because we would like to
        # have a way to open files from a console panel later
        self.editor_wintype = self.gui_conf.find_panel(
            ('editor.EditorPanel',
             'nicos.clients.gui.panels.editor.EditorPanel'))
        self.history_wintype = self.gui_conf.find_panel(
            ('history.HistoryPanel',
             'nicos.clients.gui.panels.history.HistoryPanel'))

        # additional panels
        self.panels = []
        self.splitters = []
        self.windowtypes = []
        self.windows = {}

        # setting presets
        self.instrument = self.gui_conf.name

        self.createWindowContent()

        # timer for reconnecting
        self.reconnectTimer = QTimer(singleShot=True, timeout=self._reconnect)
        self._reconnect_count = 0
        self._reconnect_time = 0

        # timer for session keepalive, every 12 hours
        self.keepaliveTimer = QTimer(singleShot=False, timeout=self._keepalive)
        self.keepaliveTimer.start(self.keepaliveInterval)

        # setup tray icon
        self.trayIcon = QSystemTrayIcon(self)
        self.trayIcon.activated.connect(self.on_trayIcon_activated)
        self.trayMenu = QMenu(self)
        nameAction = self.trayMenu.addAction(self.instrument)
        nameAction.setEnabled(False)
        self.trayMenu.addSeparator()
        toggleAction = self.trayMenu.addAction('Hide main window')
        toggleAction.setCheckable(True)
        toggleAction.triggered[bool].connect(
            lambda hide: self.setVisible(not hide))
        self.trayIcon.setContextMenu(self.trayMenu)

        # help window
        self.helpWindow = None
        # watchdog window
        self.watchdogWindow = None
        # plug-n-play notification windows
        self.pnpWindows = {}

        # create initial state
        self._init_toolbar()
Exemple #24
0
 def icon(self):
     if self.widget_class.designer_icon is None:
         return QIcon()
     return QIcon(self.widget_class.designer_icon)
Exemple #25
0
    def _reinit(self):
        classes = self.devinfo.classes

        if sip.isdeleted(self.devitem):
            # The item we're controlling has been removed from the list (e.g.
            # due to client reconnect), get it again.
            self.devitem = self.device_panel._devitems.get(
                self.devname.lower())
            # No such device anymore...
            if self.devitem is None:
                self.close()
                return

        self.deviceName.setText('Device: %s' % self.devname)
        self.setWindowTitle('Control %s' % self.devname)

        self.settingsBtn = self.buttonBox.button(
            QDialogButtonBox.RestoreDefaults)
        self.settingsBtn.clicked.connect(self.on_settingsBtn_clicked)

        # trigger parameter poll
        self.client.eval('%s.pollParams()' % self.devname, None)

        # now get all cache keys pertaining to the device and set the
        # properties we want
        params = self.client.getDeviceParams(self.devname)
        self.paraminfo = self.client.getDeviceParamInfo(self.devname)
        self.paramvalues = dict(params)

        # put parameter values in the list widget
        self.paramItems.clear()
        self.paramList.clear()
        for key, value in sorted(iteritems(params)):
            if self.paraminfo.get(key):
                # normally, show only userparams, except in expert mode
                is_userparam = self.paraminfo[key]['userparam']
                if is_userparam or self.device_panel._show_lowlevel:
                    self.paramItems[key] = item = \
                        QTreeWidgetItem(self.paramList, [key, str(value)])
                    # display non-userparams in grey italics, like lowlevel
                    # devices in the device list
                    if not is_userparam:
                        item.setFont(0, lowlevelFont[True])
                        item.setForeground(0, lowlevelBrush[True])

        # set description label
        if params.get('description'):
            self.description.setText(params['description'])
        else:
            self.description.setVisible(False)

        # check how to refer to the device in commands: if it is lowlevel,
        # we need to use quotes
        self.devrepr = srepr(self.devname) if params.get('lowlevel', True) \
            else self.devname

        # show "Set alias" group box if it is an alias device
        if 'alias' in params:
            if params['alias']:
                self.deviceName.setText(self.deviceName.text() +
                                        ' (alias for %s)' % params['alias'])
            alias_config = self.client.eval('session.alias_config', {})
            self.aliasTarget = QComboBox(self)
            self.aliasTarget.setEditable(True)
            if self.devname in alias_config:
                items = [t[0] for t in alias_config[self.devname]]
                self.aliasTarget.addItems(items)
                if params['alias'] in items:
                    self.aliasTarget.setCurrentIndex(
                        items.index(params['alias']))
            self.targetLayoutAlias.takeAt(1).widget().deleteLater()
            self.targetLayoutAlias.insertWidget(1, self.aliasTarget)
            if self.client.viewonly:
                self.setAliasBtn.setEnabled(False)
        else:
            self.aliasGroup.setVisible(False)

        historyBtn = self.buttonBox.button(QDialogButtonBox.Reset)
        # show current value/status if it is readable
        if 'nicos.core.device.Readable' not in classes:
            self.valueFrame.setVisible(False)
            self.buttonBox.removeButton(historyBtn)
        else:
            self.valuelabel.setText(self.devitem.text(1))
            self.statuslabel.setText(self.devitem.text(2))
            self.statusimage.setPixmap(self.devitem.icon(0).pixmap(16, 16))
            setForegroundBrush(self.statuslabel, self.devitem.foreground(2))
            setBackgroundBrush(self.statuslabel, self.devitem.background(2))

            # modify history button: add icon and set text
            historyBtn.setIcon(QIcon(':/find'))
            historyBtn.setText('Plot history...')
            historyBtn.clicked.connect(self.on_historyBtn_clicked)

        if self.client.viewonly:
            self.limitFrame.setVisible(False)
            self.targetFrame.setVisible(False)
            return

        # add a menu for the "More" button
        self.moveBtns.clear()
        menu = QMenu(self)
        if 'nicos.core.mixins.HasLimits' in classes:
            menu.addAction(self.actionSetLimits)
        if 'nicos.core.mixins.HasOffset' in classes:
            menu.addAction(self.actionAdjustOffset)
        if 'nicos.devices.abstract.CanReference' in classes:
            menu.addAction(self.actionReference)
        if 'nicos.devices.abstract.Coder' in classes:
            menu.addAction(self.actionSetPosition)
        if 'nicos.core.device.Moveable' in classes:
            if not menu.isEmpty():
                menu.addSeparator()
            menu.addAction(self.actionFix)
            menu.addAction(self.actionRelease)
        if 'nicos.core.mixins.CanDisable' in classes:
            if not menu.isEmpty():
                menu.addSeparator()
            menu.addAction(self.actionEnable)
            menu.addAction(self.actionDisable)
        if not menu.isEmpty():
            menuBtn = QPushButton('More', self)
            menuBtn.setMenu(menu)
            self.moveBtns.addButton(menuBtn, QDialogButtonBox.ResetRole)

        def reset(checked):
            self.device_panel.exec_command('reset(%s)' % self.devrepr)

        def stop(checked):
            self.device_panel.exec_command('stop(%s)' % self.devrepr,
                                           immediate=True)

        self.moveBtns.addButton('Reset', QDialogButtonBox.ResetRole)\
                     .clicked.connect(reset)

        if 'nicos.core.device.Moveable' in classes or \
           'nicos.core.device.Measurable' in classes:
            self.moveBtns.addButton('Stop', QDialogButtonBox.ResetRole)\
                         .clicked.connect(stop)

        # show target and limits if the device is Moveable
        if 'nicos.core.device.Moveable' not in classes:
            self.limitFrame.setVisible(False)
            self.targetFrame.setVisible(False)
        else:
            if 'nicos.core.mixins.HasLimits' not in classes:
                self.limitFrame.setVisible(False)
            else:
                self.limitMin.setText(str(params['userlimits'][0]))
                self.limitMax.setText(str(params['userlimits'][1]))

            # insert a widget to enter a new device value
            # allowEnter=False because we catch pressing Enter ourselves
            self.target = DeviceValueEdit(self,
                                          dev=self.devname,
                                          useButtons=True,
                                          allowEnter=False)
            self.target.setClient(self.client)

            def btn_callback(target):
                self.device_panel.exec_command('move(%s, %s)' %
                                               (self.devrepr, srepr(target)))

            self.target.valueChosen.connect(btn_callback)
            self.targetFrame.layout().takeAt(1).widget().deleteLater()
            self.targetFrame.layout().insertWidget(1, self.target)

            def move(checked):
                try:
                    target = self.target.getValue()
                except ValueError:
                    return
                self.device_panel.exec_command('move(%s, %s)' %
                                               (self.devrepr, srepr(target)))

            if self.target.getValue() is not Ellipsis:  # (button widget)
                self.moveBtn = self.moveBtns.addButton(
                    'Move', QDialogButtonBox.AcceptRole)
                self.moveBtn.clicked.connect(move)
            else:
                self.moveBtn = None

            if params.get('fixed') and self.moveBtn:
                self.moveBtn.setEnabled(False)
                self.moveBtn.setText('(fixed)')
Exemple #26
0
    def __init__(self, parent, client, options):
        Panel.__init__(self, parent, client, options)
        loadUi(self, 'panels/status.ui')

        self.stopcounting = False
        self.menus = None
        self.bar = None
        self.queueFrame.hide()
        self.statusLabel.hide()
        self.pause_color = QColor('#ffdddd')
        self.idle_color = parent.user_color

        self.script_queue = ScriptQueue(self.queueFrame, self.queueView)
        self.current_line = -1
        self.current_request = {}
        self.curlineicon = QIcon(':/currentline')
        self.errlineicon = QIcon(':/errorline')
        empty = QPixmap(16, 16)
        empty.fill(Qt.transparent)
        self.otherlineicon = QIcon(empty)
        self.traceView.setItemDelegate(LineDelegate(24, self.traceView))

        self.stopcounting = bool(options.get('stopcounting', False))
        if self.stopcounting:
            tooltip = 'Aborts the current executed script'
            self.actionStop.setToolTip(tooltip)
            self.actionStop.setText('Abort current script')
            self.actionStop2.setToolTip(tooltip)

        self.showETA = bool(options.get('eta', False))
        self.etaWidget.hide()

        client.request.connect(self.on_client_request)
        client.processing.connect(self.on_client_processing)
        client.blocked.connect(self.on_client_blocked)
        client.status.connect(self.on_client_status)
        client.initstatus.connect(self.on_client_initstatus)
        client.disconnected.connect(self.on_client_disconnected)
        client.rearranged.connect(self.on_client_rearranged)
        client.updated.connect(self.on_client_updated)
        client.eta.connect(self.on_client_eta)

        bar = QToolBar('Script control')
        bar.setObjectName(bar.windowTitle())
        # unfortunately it is not wise to put a menu in its own dropdown menu,
        # so we have to duplicate the actionBreak and actionStop...
        dropdown1 = QMenu('', self)
        dropdown1.addAction(self.actionBreak)
        dropdown1.addAction(self.actionBreakCount)
        dropdown1.addAction(self.actionFinishEarly)
        self.actionBreak2.setMenu(dropdown1)
        dropdown2 = QMenu('', self)
        dropdown2.addAction(self.actionStop)
        dropdown2.addAction(self.actionFinish)
        dropdown2.addAction(self.actionFinishEarlyAndStop)
        self.actionStop2.setMenu(dropdown2)
        bar.addAction(self.actionBreak2)
        bar.addAction(self.actionContinue)
        bar.addAction(self.actionStop2)
        bar.addAction(self.actionEmergencyStop)
        self.bar = bar
        # self.mainwindow.addToolBar(bar)

        menu = QMenu('&Script control', self)
        menu.addAction(self.actionBreak)
        menu.addAction(self.actionBreakCount)
        menu.addAction(self.actionContinue)
        menu.addAction(self.actionFinishEarly)
        menu.addSeparator()
        menu.addAction(self.actionStop)
        menu.addAction(self.actionFinish)
        menu.addAction(self.actionFinishEarlyAndStop)
        menu.addSeparator()
        menu.addAction(self.actionEmergencyStop)
        self.mainwindow.menuBar().insertMenu(
            self.mainwindow.menuWindows.menuAction(), menu)

        self.activeGroup = QActionGroup(self)
        self.activeGroup.addAction(self.actionBreak)
        self.activeGroup.addAction(self.actionBreak2)
        self.activeGroup.addAction(self.actionBreakCount)
        self.activeGroup.addAction(self.actionContinue)
        self.activeGroup.addAction(self.actionStop)
        self.activeGroup.addAction(self.actionStop2)
        self.activeGroup.addAction(self.actionFinish)
        self.activeGroup.addAction(self.actionFinishEarly)
        self.activeGroup.addAction(self.actionFinishEarlyAndStop)

        self._status = 'idle'
Exemple #27
0
 def on_client_disconnected(self):
     DefaultMainWindow.on_client_disconnected(self)
     self.actionConnect.setIcon(
         QIcon("resources/material/icons/power-24px.svg"))