forked from M-Labs/artiq
Compare commits
6 Commits
aeaa337b1a
...
88ec806879
Author | SHA1 | Date |
---|---|---|
Simon Renblad | 88ec806879 | |
Simon Renblad | 0c8511eab6 | |
Simon Renblad | 13bf72574b | |
Simon Renblad | d1decc9198 | |
Simon Renblad | 2a16b84df9 | |
Simon Renblad | b4fb9b9bc6 |
|
@ -9,6 +9,7 @@ from artiq.coredevice.comm_moninj import CommMonInj, TTLOverride, TTLProbe
|
|||
from artiq.coredevice.ad9912_reg import AD9912_SER_CONF
|
||||
from artiq.gui.tools import LayoutWidget
|
||||
from artiq.gui.flowlayout import FlowLayout
|
||||
from artiq.gui.models import DictSyncTreeSepModel
|
||||
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
@ -157,8 +158,8 @@ class _TTLHandler:
|
|||
self.widget.level_toggled.connect(self.level_toggled)
|
||||
self.refresh_display()
|
||||
|
||||
def sort_key(self):
|
||||
return self.channel
|
||||
def to_model_path(self):
|
||||
return "ttl/{}".format(self.title)
|
||||
|
||||
|
||||
class _DDSWidget(QtWidgets.QFrame):
|
||||
|
@ -353,8 +354,8 @@ class _DDSHandler:
|
|||
def off_clicked(self):
|
||||
self.dm.dds_channel_toggle(self.dds_name, sw=False)
|
||||
|
||||
def sort_key(self):
|
||||
return (self.bus_channel, self.channel)
|
||||
def to_model_path(self):
|
||||
return "dds/{}".format(self.title)
|
||||
|
||||
|
||||
class _DACWidget(QtWidgets.QFrame):
|
||||
|
@ -406,8 +407,60 @@ class _DACHandler:
|
|||
if self.widget is not None:
|
||||
self.widget.set_value(self.cur_value * 100 / 2**16)
|
||||
|
||||
def sort_key(self):
|
||||
return (self.spi_channel, self.channel)
|
||||
def to_model_path(self):
|
||||
return "dac/{}/{}".format(self.title, self.channel)
|
||||
|
||||
|
||||
class Model(DictSyncTreeSepModel):
|
||||
def __init__(self, init):
|
||||
DictSyncTreeSepModel.__init__(self, "/", ["Channels"], init)
|
||||
|
||||
def clear(self):
|
||||
for k in self.backing_store:
|
||||
self._del_item(self, k.split(self.separator))
|
||||
self.backing_store.clear()
|
||||
|
||||
def update(self, d):
|
||||
for k, v in d.items():
|
||||
self[v.to_model_path()] = v
|
||||
|
||||
|
||||
class _AddChannelDialog(QtWidgets.QDialog):
|
||||
def __init__(self, parent, model):
|
||||
QtWidgets.QDialog.__init__(self, parent=parent)
|
||||
self.setContextMenuPolicy(QtCore.Qt.ActionsContextMenu)
|
||||
self.setWindowTitle("Add channels")
|
||||
|
||||
layout = QtWidgets.QVBoxLayout()
|
||||
self.setLayout(layout)
|
||||
|
||||
self._model = model
|
||||
self._tree_view = QtWidgets.QTreeView()
|
||||
self._tree_view.setHeaderHidden(True)
|
||||
self._tree_view.setSelectionBehavior(
|
||||
QtWidgets.QAbstractItemView.SelectItems)
|
||||
self._tree_view.setSelectionMode(
|
||||
QtWidgets.QAbstractItemView.ExtendedSelection)
|
||||
self._tree_view.setModel(self._model)
|
||||
layout.addWidget(self._tree_view)
|
||||
|
||||
self._button_box = QtWidgets.QDialogButtonBox(
|
||||
QtWidgets.QDialogButtonBox.Ok | QtWidgets.QDialogButtonBox.Cancel
|
||||
)
|
||||
self._button_box.setCenterButtons(True)
|
||||
self._button_box.accepted.connect(self.add_channels)
|
||||
self._button_box.rejected.connect(self.reject)
|
||||
layout.addWidget(self._button_box)
|
||||
|
||||
def add_channels(self):
|
||||
selection = self._tree_view.selectedIndexes()
|
||||
channels = []
|
||||
for select in selection:
|
||||
key = self._model.index_to_key(select)
|
||||
if key is not None:
|
||||
channels.append(self._model[key].ref)
|
||||
self.channels = channels
|
||||
self.accept()
|
||||
|
||||
|
||||
_HandlerDesc = namedtuple("_HandlerDesc", "uid comment cls arguments")
|
||||
|
@ -487,12 +540,10 @@ class _DeviceManager:
|
|||
self.handlers_by_uid = dict()
|
||||
|
||||
self.dds_sysclk = 0
|
||||
self.ttl_cb = lambda: None
|
||||
self.ttl_handlers = dict()
|
||||
self.dds_cb = lambda: None
|
||||
self.dds_handlers = dict()
|
||||
self.dac_cb = lambda: None
|
||||
self.dac_handlers = dict()
|
||||
self.channels_cb = lambda: None
|
||||
|
||||
def init_ddb(self, ddb):
|
||||
self.ddb = ddb
|
||||
|
@ -513,17 +564,14 @@ class _DeviceManager:
|
|||
self.setup_ttl_monitoring(False, handler.channel)
|
||||
handler.delete_widget()
|
||||
del self.ttl_handlers[handler.channel]
|
||||
self.ttl_cb()
|
||||
elif isinstance(handler, _DDSHandler):
|
||||
self.setup_dds_monitoring(False, handler.bus_channel, handler.channel)
|
||||
handler.delete_widget()
|
||||
del self.dds_handlers[(handler.bus_channel, handler.channel)]
|
||||
self.dds_cb()
|
||||
elif isinstance(handler, _DACHandler):
|
||||
self.setup_dac_monitoring(False, handler.spi_channel, handler.channel)
|
||||
handler.delete_widget()
|
||||
del self.dac_handlers[(handler.spi_channel, handler.channel)]
|
||||
self.dac_cb()
|
||||
else:
|
||||
raise ValueError
|
||||
|
||||
|
@ -536,19 +584,19 @@ class _DeviceManager:
|
|||
|
||||
if isinstance(handler, _TTLHandler):
|
||||
self.ttl_handlers[handler.channel] = handler
|
||||
self.ttl_cb()
|
||||
self.setup_ttl_monitoring(True, handler.channel)
|
||||
elif isinstance(handler, _DDSHandler):
|
||||
self.dds_handlers[(handler.bus_channel, handler.channel)] = handler
|
||||
self.dds_cb()
|
||||
self.setup_dds_monitoring(True, handler.bus_channel, handler.channel)
|
||||
elif isinstance(handler, _DACHandler):
|
||||
self.dac_handlers[(handler.spi_channel, handler.channel)] = handler
|
||||
self.dac_cb()
|
||||
self.setup_dac_monitoring(True, handler.spi_channel, handler.channel)
|
||||
else:
|
||||
raise ValueError
|
||||
|
||||
if description != self.description:
|
||||
self.channels_cb()
|
||||
|
||||
self.description = description
|
||||
|
||||
def ttl_set_mode(self, channel, mode):
|
||||
|
@ -787,38 +835,43 @@ class _DeviceManager:
|
|||
await self.mi_connection.close()
|
||||
|
||||
|
||||
class _MonInjDock(QtWidgets.QDockWidget):
|
||||
def __init__(self, name):
|
||||
QtWidgets.QDockWidget.__init__(self, name)
|
||||
self.setObjectName(name)
|
||||
class MonInjDock(QtWidgets.QDockWidget):
|
||||
def __init__(self, schedule_ctl):
|
||||
QtWidgets.QDockWidget.__init__(self, "MonInj")
|
||||
self.setObjectName("MonInj")
|
||||
self.setFeatures(QtWidgets.QDockWidget.DockWidgetMovable |
|
||||
QtWidgets.QDockWidget.DockWidgetFloatable)
|
||||
|
||||
def layout_widgets(self, handlers):
|
||||
self.dm = _DeviceManager(schedule_ctl)
|
||||
self.dm.channels_cb = lambda: self.set_channels(self.dm.handlers_by_uid)
|
||||
|
||||
layout = LayoutWidget()
|
||||
self.setWidget(layout)
|
||||
self._channel_model = Model({})
|
||||
self.add_channel_dialog = _AddChannelDialog(self, self._channel_model)
|
||||
self.add_channel_dialog.accepted.connect(
|
||||
lambda: self.layout_widgets(self.add_channel_dialog.channels))
|
||||
add_channel_btn = QtWidgets.QToolButton()
|
||||
add_channel_btn.setToolTip("Add channels...")
|
||||
add_channel_btn.setIcon(
|
||||
QtWidgets.QApplication.style().standardIcon(
|
||||
QtWidgets.QStyle.SP_FileDialogListView))
|
||||
add_channel_btn.clicked.connect(self.add_channel_dialog.open)
|
||||
layout.addWidget(add_channel_btn, 0, 0, colspan=1)
|
||||
scroll_area = QtWidgets.QScrollArea()
|
||||
self.setWidget(scroll_area)
|
||||
|
||||
grid = FlowLayout()
|
||||
layout.addWidget(scroll_area, 1, 0, colspan=10)
|
||||
self.grid = FlowLayout()
|
||||
grid_widget = QtWidgets.QWidget()
|
||||
grid_widget.setLayout(grid)
|
||||
|
||||
for handler in sorted(handlers, key=lambda h: h.sort_key()):
|
||||
grid.addWidget(handler.widget)
|
||||
|
||||
grid_widget.setLayout(self.grid)
|
||||
scroll_area.setWidgetResizable(True)
|
||||
scroll_area.setWidget(grid_widget)
|
||||
|
||||
def layout_widgets(self, handlers):
|
||||
for handler in handlers:
|
||||
self.grid.addWidget(handler.widget)
|
||||
|
||||
class MonInj:
|
||||
def __init__(self, schedule_ctl):
|
||||
self.ttl_dock = _MonInjDock("TTL")
|
||||
self.dds_dock = _MonInjDock("DDS")
|
||||
self.dac_dock = _MonInjDock("DAC")
|
||||
|
||||
self.dm = _DeviceManager(schedule_ctl)
|
||||
self.dm.ttl_cb = lambda: self.ttl_dock.layout_widgets(self.dm.ttl_handlers.values())
|
||||
self.dm.dds_cb = lambda: self.dds_dock.layout_widgets(self.dm.dds_handlers.values())
|
||||
self.dm.dac_cb = lambda: self.dac_dock.layout_widgets(self.dm.dac_handlers.values())
|
||||
def set_channels(self, handlers):
|
||||
self._channel_model.update(handlers)
|
||||
|
||||
async def stop(self):
|
||||
if self.dm is not None:
|
||||
|
|
|
@ -226,7 +226,7 @@ def main():
|
|||
smgr.register(d_applets)
|
||||
broadcast_clients["ccb"].notify_cbs.append(d_applets.ccb_notify)
|
||||
|
||||
d_ttl_dds = moninj.MonInj(rpc_clients["schedule"])
|
||||
d_ttl_dds = moninj.MonInjDock(rpc_clients["schedule"])
|
||||
atexit_register_coroutine(d_ttl_dds.stop, loop=loop)
|
||||
|
||||
d_waveform = waveform.WaveformDock(
|
||||
|
@ -260,8 +260,7 @@ def main():
|
|||
|
||||
# lay out docks
|
||||
right_docks = [
|
||||
d_explorer, d_shortcuts,
|
||||
d_ttl_dds.ttl_dock, d_ttl_dds.dds_dock, d_ttl_dds.dac_dock,
|
||||
d_explorer, d_shortcuts, d_ttl_dds,
|
||||
d_datasets, d_applets, d_waveform, d_interactive_args
|
||||
]
|
||||
main_window.addDockWidget(QtCore.Qt.RightDockWidgetArea, right_docks[0])
|
||||
|
@ -279,10 +278,6 @@ def main():
|
|||
smgr.start(loop=loop)
|
||||
atexit_register_coroutine(smgr.stop, loop=loop)
|
||||
|
||||
# work around for https://github.com/m-labs/artiq/issues/1307
|
||||
d_ttl_dds.ttl_dock.show()
|
||||
d_ttl_dds.dds_dock.show()
|
||||
|
||||
# create first log dock if not already in state
|
||||
d_log0 = logmgr.first_log_dock()
|
||||
if d_log0 is not None:
|
||||
|
|
Loading…
Reference in New Issue