mirror of
https://github.com/naruxde/revpicommander.git
synced 2025-11-09 00:53:53 +01:00
Add a simulator dialog to manage simulator settings
This commit is contained in:
1
.idea/vcs.xml
generated
1
.idea/vcs.xml
generated
@@ -2,6 +2,5 @@
|
|||||||
<project version="4">
|
<project version="4">
|
||||||
<component name="VcsDirectoryMappings">
|
<component name="VcsDirectoryMappings">
|
||||||
<mapping directory="$PROJECT_DIR$" vcs="Git" />
|
<mapping directory="$PROJECT_DIR$" vcs="Git" />
|
||||||
<mapping directory="$PROJECT_DIR$/lib/revpimodio2" vcs="Git" />
|
|
||||||
</component>
|
</component>
|
||||||
</project>
|
</project>
|
||||||
135
include/ui/simulator_ui.py
Normal file
135
include/ui/simulator_ui.py
Normal file
@@ -0,0 +1,135 @@
|
|||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
# Form implementation generated from reading ui file 'simulator.ui'
|
||||||
|
#
|
||||||
|
# Created by: PyQt5 UI code generator 5.14.1
|
||||||
|
#
|
||||||
|
# WARNING! All changes made in this file will be lost!
|
||||||
|
|
||||||
|
|
||||||
|
from PyQt5 import QtCore, QtGui, QtWidgets
|
||||||
|
|
||||||
|
|
||||||
|
class Ui_diag_simulator(object):
|
||||||
|
def setupUi(self, diag_simulator):
|
||||||
|
diag_simulator.setObjectName("diag_simulator")
|
||||||
|
diag_simulator.resize(522, 500)
|
||||||
|
self.verticalLayout = QtWidgets.QVBoxLayout(diag_simulator)
|
||||||
|
self.verticalLayout.setObjectName("verticalLayout")
|
||||||
|
self.gb_settings = QtWidgets.QGroupBox(diag_simulator)
|
||||||
|
self.gb_settings.setObjectName("gb_settings")
|
||||||
|
self.gridLayout = QtWidgets.QGridLayout(self.gb_settings)
|
||||||
|
self.gridLayout.setObjectName("gridLayout")
|
||||||
|
self.lbl_history = QtWidgets.QLabel(self.gb_settings)
|
||||||
|
self.lbl_history.setObjectName("lbl_history")
|
||||||
|
self.gridLayout.addWidget(self.lbl_history, 0, 0, 1, 1)
|
||||||
|
self.lbl_configrsc = QtWidgets.QLabel(self.gb_settings)
|
||||||
|
self.lbl_configrsc.setObjectName("lbl_configrsc")
|
||||||
|
self.gridLayout.addWidget(self.lbl_configrsc, 1, 0, 1, 1)
|
||||||
|
self.txt_configrsc = QtWidgets.QLineEdit(self.gb_settings)
|
||||||
|
self.txt_configrsc.setFocusPolicy(QtCore.Qt.NoFocus)
|
||||||
|
self.txt_configrsc.setText("")
|
||||||
|
self.txt_configrsc.setObjectName("txt_configrsc")
|
||||||
|
self.gridLayout.addWidget(self.txt_configrsc, 1, 1, 1, 1)
|
||||||
|
self.btn_configrsc = QtWidgets.QPushButton(self.gb_settings)
|
||||||
|
self.btn_configrsc.setObjectName("btn_configrsc")
|
||||||
|
self.gridLayout.addWidget(self.btn_configrsc, 1, 2, 1, 1)
|
||||||
|
self.lbl_procimg = QtWidgets.QLabel(self.gb_settings)
|
||||||
|
self.lbl_procimg.setObjectName("lbl_procimg")
|
||||||
|
self.gridLayout.addWidget(self.lbl_procimg, 2, 0, 1, 1)
|
||||||
|
self.txt_procimg = QtWidgets.QLineEdit(self.gb_settings)
|
||||||
|
self.txt_procimg.setFocusPolicy(QtCore.Qt.NoFocus)
|
||||||
|
self.txt_procimg.setText("")
|
||||||
|
self.txt_procimg.setObjectName("txt_procimg")
|
||||||
|
self.gridLayout.addWidget(self.txt_procimg, 2, 1, 1, 1)
|
||||||
|
self.lbl_stop = QtWidgets.QLabel(self.gb_settings)
|
||||||
|
self.lbl_stop.setObjectName("lbl_stop")
|
||||||
|
self.gridLayout.addWidget(self.lbl_stop, 3, 0, 1, 1)
|
||||||
|
self.lbl_restart = QtWidgets.QLabel(self.gb_settings)
|
||||||
|
self.lbl_restart.setObjectName("lbl_restart")
|
||||||
|
self.gridLayout.addWidget(self.lbl_restart, 4, 0, 1, 1)
|
||||||
|
self.cbb_history = QtWidgets.QComboBox(self.gb_settings)
|
||||||
|
self.cbb_history.setSizeAdjustPolicy(QtWidgets.QComboBox.AdjustToMinimumContentsLength)
|
||||||
|
self.cbb_history.setObjectName("cbb_history")
|
||||||
|
self.gridLayout.addWidget(self.cbb_history, 0, 1, 1, 2)
|
||||||
|
self.cbx_stop_remove = QtWidgets.QCheckBox(self.gb_settings)
|
||||||
|
self.cbx_stop_remove.setObjectName("cbx_stop_remove")
|
||||||
|
self.gridLayout.addWidget(self.cbx_stop_remove, 3, 1, 1, 2)
|
||||||
|
self.rb_restart_pictory = QtWidgets.QRadioButton(self.gb_settings)
|
||||||
|
self.rb_restart_pictory.setChecked(True)
|
||||||
|
self.rb_restart_pictory.setObjectName("rb_restart_pictory")
|
||||||
|
self.gridLayout.addWidget(self.rb_restart_pictory, 4, 1, 1, 2)
|
||||||
|
self.rb_restart_zero = QtWidgets.QRadioButton(self.gb_settings)
|
||||||
|
self.rb_restart_zero.setObjectName("rb_restart_zero")
|
||||||
|
self.gridLayout.addWidget(self.rb_restart_zero, 5, 1, 1, 2)
|
||||||
|
self.verticalLayout.addWidget(self.gb_settings)
|
||||||
|
self.gb_info = QtWidgets.QGroupBox(diag_simulator)
|
||||||
|
self.gb_info.setObjectName("gb_info")
|
||||||
|
self.verticalLayout_2 = QtWidgets.QVBoxLayout(self.gb_info)
|
||||||
|
self.verticalLayout_2.setObjectName("verticalLayout_2")
|
||||||
|
self.lbl_info = QtWidgets.QLabel(self.gb_info)
|
||||||
|
self.lbl_info.setWordWrap(True)
|
||||||
|
self.lbl_info.setObjectName("lbl_info")
|
||||||
|
self.verticalLayout_2.addWidget(self.lbl_info)
|
||||||
|
self.txt_info = QtWidgets.QPlainTextEdit(self.gb_info)
|
||||||
|
self.txt_info.setSizeAdjustPolicy(QtWidgets.QAbstractScrollArea.AdjustToContents)
|
||||||
|
self.txt_info.setReadOnly(True)
|
||||||
|
self.txt_info.setPlainText("")
|
||||||
|
self.txt_info.setObjectName("txt_info")
|
||||||
|
self.verticalLayout_2.addWidget(self.txt_info)
|
||||||
|
self.verticalLayout.addWidget(self.gb_info)
|
||||||
|
self.btn_start_pictory = QtWidgets.QPushButton(diag_simulator)
|
||||||
|
self.btn_start_pictory.setObjectName("btn_start_pictory")
|
||||||
|
self.verticalLayout.addWidget(self.btn_start_pictory)
|
||||||
|
self.btn_start_empty = QtWidgets.QPushButton(diag_simulator)
|
||||||
|
self.btn_start_empty.setObjectName("btn_start_empty")
|
||||||
|
self.verticalLayout.addWidget(self.btn_start_empty)
|
||||||
|
self.btn_start_nochange = QtWidgets.QPushButton(diag_simulator)
|
||||||
|
self.btn_start_nochange.setObjectName("btn_start_nochange")
|
||||||
|
self.verticalLayout.addWidget(self.btn_start_nochange)
|
||||||
|
|
||||||
|
self.retranslateUi(diag_simulator)
|
||||||
|
self.btn_start_empty.clicked.connect(diag_simulator.accept)
|
||||||
|
self.btn_start_nochange.clicked.connect(diag_simulator.accept)
|
||||||
|
self.btn_start_pictory.clicked.connect(diag_simulator.accept)
|
||||||
|
QtCore.QMetaObject.connectSlotsByName(diag_simulator)
|
||||||
|
diag_simulator.setTabOrder(self.cbb_history, self.btn_configrsc)
|
||||||
|
diag_simulator.setTabOrder(self.btn_configrsc, self.cbx_stop_remove)
|
||||||
|
diag_simulator.setTabOrder(self.cbx_stop_remove, self.rb_restart_pictory)
|
||||||
|
diag_simulator.setTabOrder(self.rb_restart_pictory, self.rb_restart_zero)
|
||||||
|
diag_simulator.setTabOrder(self.rb_restart_zero, self.txt_info)
|
||||||
|
diag_simulator.setTabOrder(self.txt_info, self.btn_start_pictory)
|
||||||
|
diag_simulator.setTabOrder(self.btn_start_pictory, self.btn_start_empty)
|
||||||
|
diag_simulator.setTabOrder(self.btn_start_empty, self.btn_start_nochange)
|
||||||
|
|
||||||
|
def retranslateUi(self, diag_simulator):
|
||||||
|
_translate = QtCore.QCoreApplication.translate
|
||||||
|
diag_simulator.setWindowTitle(_translate("diag_simulator", "piControl simulator"))
|
||||||
|
self.gb_settings.setTitle(_translate("diag_simulator", "Simulator settings"))
|
||||||
|
self.lbl_history.setText(_translate("diag_simulator", "Last used:"))
|
||||||
|
self.lbl_configrsc.setText(_translate("diag_simulator", "piCtory file:"))
|
||||||
|
self.btn_configrsc.setText(_translate("diag_simulator", "change..."))
|
||||||
|
self.lbl_procimg.setText(_translate("diag_simulator", "Process image:"))
|
||||||
|
self.lbl_stop.setText(_translate("diag_simulator", "Stop action:"))
|
||||||
|
self.lbl_restart.setText(_translate("diag_simulator", "Restart action:"))
|
||||||
|
self.cbx_stop_remove.setText(_translate("diag_simulator", "Remove process image"))
|
||||||
|
self.rb_restart_pictory.setText(_translate("diag_simulator", "Restore piCtory default values"))
|
||||||
|
self.rb_restart_zero.setText(_translate("diag_simulator", "Reset everything to ZERO"))
|
||||||
|
self.gb_info.setTitle(_translate("diag_simulator", "RevPiModIO integration"))
|
||||||
|
self.lbl_info.setText(_translate("diag_simulator", "You can work with this simulator if your call RevPiModIO with this additional parameters:"))
|
||||||
|
self.btn_start_pictory.setText(_translate("diag_simulator", "Start with piCtory default values"))
|
||||||
|
self.btn_start_pictory.setShortcut(_translate("diag_simulator", "Ctrl+1"))
|
||||||
|
self.btn_start_empty.setText(_translate("diag_simulator", "Start with empty process image"))
|
||||||
|
self.btn_start_empty.setShortcut(_translate("diag_simulator", "Ctrl+2"))
|
||||||
|
self.btn_start_nochange.setText(_translate("diag_simulator", "Start without changing actual process image"))
|
||||||
|
self.btn_start_nochange.setShortcut(_translate("diag_simulator", "Ctrl+3"))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
import sys
|
||||||
|
app = QtWidgets.QApplication(sys.argv)
|
||||||
|
diag_simulator = QtWidgets.QDialog()
|
||||||
|
ui = Ui_diag_simulator()
|
||||||
|
ui.setupUi(diag_simulator)
|
||||||
|
diag_simulator.show()
|
||||||
|
sys.exit(app.exec_())
|
||||||
245
include/ui_dev/simulator.ui
Normal file
245
include/ui_dev/simulator.ui
Normal file
@@ -0,0 +1,245 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<ui version="4.0">
|
||||||
|
<class>diag_simulator</class>
|
||||||
|
<widget class="QDialog" name="diag_simulator">
|
||||||
|
<property name="geometry">
|
||||||
|
<rect>
|
||||||
|
<x>0</x>
|
||||||
|
<y>0</y>
|
||||||
|
<width>522</width>
|
||||||
|
<height>500</height>
|
||||||
|
</rect>
|
||||||
|
</property>
|
||||||
|
<property name="windowTitle">
|
||||||
|
<string>piControl simulator</string>
|
||||||
|
</property>
|
||||||
|
<layout class="QVBoxLayout" name="verticalLayout">
|
||||||
|
<item>
|
||||||
|
<widget class="QGroupBox" name="gb_settings">
|
||||||
|
<property name="title">
|
||||||
|
<string>Simulator settings</string>
|
||||||
|
</property>
|
||||||
|
<layout class="QGridLayout" name="gridLayout">
|
||||||
|
<item row="0" column="0">
|
||||||
|
<widget class="QLabel" name="lbl_history">
|
||||||
|
<property name="text">
|
||||||
|
<string>Last used:</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="0">
|
||||||
|
<widget class="QLabel" name="lbl_configrsc">
|
||||||
|
<property name="text">
|
||||||
|
<string>piCtory file:</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="1">
|
||||||
|
<widget class="QLineEdit" name="txt_configrsc">
|
||||||
|
<property name="focusPolicy">
|
||||||
|
<enum>Qt::NoFocus</enum>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string notr="true"/>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="1" column="2">
|
||||||
|
<widget class="QPushButton" name="btn_configrsc">
|
||||||
|
<property name="text">
|
||||||
|
<string>select...</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="2" column="0">
|
||||||
|
<widget class="QLabel" name="lbl_procimg">
|
||||||
|
<property name="text">
|
||||||
|
<string>Process image:</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="2" column="1">
|
||||||
|
<widget class="QLineEdit" name="txt_procimg">
|
||||||
|
<property name="focusPolicy">
|
||||||
|
<enum>Qt::NoFocus</enum>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string notr="true"/>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="3" column="0">
|
||||||
|
<widget class="QLabel" name="lbl_stop">
|
||||||
|
<property name="text">
|
||||||
|
<string>Stop action:</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="4" column="0">
|
||||||
|
<widget class="QLabel" name="lbl_restart">
|
||||||
|
<property name="text">
|
||||||
|
<string>Restart action:</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="0" column="1" colspan="2">
|
||||||
|
<widget class="QComboBox" name="cbb_history">
|
||||||
|
<property name="sizeAdjustPolicy">
|
||||||
|
<enum>QComboBox::AdjustToMinimumContentsLength</enum>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="3" column="1" colspan="2">
|
||||||
|
<widget class="QCheckBox" name="cbx_stop_remove">
|
||||||
|
<property name="text">
|
||||||
|
<string>Remove process image</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="4" column="1" colspan="2">
|
||||||
|
<widget class="QRadioButton" name="rb_restart_pictory">
|
||||||
|
<property name="text">
|
||||||
|
<string>Restore piCtory default values</string>
|
||||||
|
</property>
|
||||||
|
<property name="checked">
|
||||||
|
<bool>true</bool>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item row="5" column="1" colspan="2">
|
||||||
|
<widget class="QRadioButton" name="rb_restart_zero">
|
||||||
|
<property name="text">
|
||||||
|
<string>Reset everything to ZERO</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
</layout>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QGroupBox" name="gb_info">
|
||||||
|
<property name="title">
|
||||||
|
<string>RevPiModIO integration</string>
|
||||||
|
</property>
|
||||||
|
<layout class="QVBoxLayout" name="verticalLayout_2">
|
||||||
|
<item>
|
||||||
|
<widget class="QLabel" name="lbl_info">
|
||||||
|
<property name="text">
|
||||||
|
<string>You can work with this simulator if your call RevPiModIO with this additional parameters:</string>
|
||||||
|
</property>
|
||||||
|
<property name="wordWrap">
|
||||||
|
<bool>true</bool>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QPlainTextEdit" name="txt_info">
|
||||||
|
<property name="sizeAdjustPolicy">
|
||||||
|
<enum>QAbstractScrollArea::AdjustToContents</enum>
|
||||||
|
</property>
|
||||||
|
<property name="readOnly">
|
||||||
|
<bool>true</bool>
|
||||||
|
</property>
|
||||||
|
<property name="plainText">
|
||||||
|
<string notr="true"/>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
</layout>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QPushButton" name="btn_start_pictory">
|
||||||
|
<property name="text">
|
||||||
|
<string>Start with piCtory default values</string>
|
||||||
|
</property>
|
||||||
|
<property name="shortcut">
|
||||||
|
<string>Ctrl+1</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QPushButton" name="btn_start_empty">
|
||||||
|
<property name="text">
|
||||||
|
<string>Start with empty process image</string>
|
||||||
|
</property>
|
||||||
|
<property name="shortcut">
|
||||||
|
<string>Ctrl+2</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QPushButton" name="btn_start_nochange">
|
||||||
|
<property name="text">
|
||||||
|
<string>Start without changing actual process image</string>
|
||||||
|
</property>
|
||||||
|
<property name="shortcut">
|
||||||
|
<string>Ctrl+3</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
</layout>
|
||||||
|
</widget>
|
||||||
|
<tabstops>
|
||||||
|
<tabstop>cbb_history</tabstop>
|
||||||
|
<tabstop>btn_configrsc</tabstop>
|
||||||
|
<tabstop>cbx_stop_remove</tabstop>
|
||||||
|
<tabstop>rb_restart_pictory</tabstop>
|
||||||
|
<tabstop>rb_restart_zero</tabstop>
|
||||||
|
<tabstop>txt_info</tabstop>
|
||||||
|
<tabstop>btn_start_pictory</tabstop>
|
||||||
|
<tabstop>btn_start_empty</tabstop>
|
||||||
|
<tabstop>btn_start_nochange</tabstop>
|
||||||
|
</tabstops>
|
||||||
|
<resources/>
|
||||||
|
<connections>
|
||||||
|
<connection>
|
||||||
|
<sender>btn_start_empty</sender>
|
||||||
|
<signal>clicked()</signal>
|
||||||
|
<receiver>diag_simulator</receiver>
|
||||||
|
<slot>accept()</slot>
|
||||||
|
<hints>
|
||||||
|
<hint type="sourcelabel">
|
||||||
|
<x>268</x>
|
||||||
|
<y>447</y>
|
||||||
|
</hint>
|
||||||
|
<hint type="destinationlabel">
|
||||||
|
<x>268</x>
|
||||||
|
<y>249</y>
|
||||||
|
</hint>
|
||||||
|
</hints>
|
||||||
|
</connection>
|
||||||
|
<connection>
|
||||||
|
<sender>btn_start_nochange</sender>
|
||||||
|
<signal>clicked()</signal>
|
||||||
|
<receiver>diag_simulator</receiver>
|
||||||
|
<slot>accept()</slot>
|
||||||
|
<hints>
|
||||||
|
<hint type="sourcelabel">
|
||||||
|
<x>268</x>
|
||||||
|
<y>478</y>
|
||||||
|
</hint>
|
||||||
|
<hint type="destinationlabel">
|
||||||
|
<x>268</x>
|
||||||
|
<y>249</y>
|
||||||
|
</hint>
|
||||||
|
</hints>
|
||||||
|
</connection>
|
||||||
|
<connection>
|
||||||
|
<sender>btn_start_pictory</sender>
|
||||||
|
<signal>clicked()</signal>
|
||||||
|
<receiver>diag_simulator</receiver>
|
||||||
|
<slot>accept()</slot>
|
||||||
|
<hints>
|
||||||
|
<hint type="sourcelabel">
|
||||||
|
<x>268</x>
|
||||||
|
<y>416</y>
|
||||||
|
</hint>
|
||||||
|
<hint type="destinationlabel">
|
||||||
|
<x>268</x>
|
||||||
|
<y>249</y>
|
||||||
|
</hint>
|
||||||
|
</hints>
|
||||||
|
</connection>
|
||||||
|
</connections>
|
||||||
|
</ui>
|
||||||
@@ -9,6 +9,7 @@ import socket
|
|||||||
from enum import IntEnum
|
from enum import IntEnum
|
||||||
from http.client import CannotSendRequest
|
from http.client import CannotSendRequest
|
||||||
from os import environ, remove
|
from os import environ, remove
|
||||||
|
from os.path import exists
|
||||||
from queue import Queue
|
from queue import Queue
|
||||||
from threading import Lock
|
from threading import Lock
|
||||||
from xmlrpc.client import Binary, ServerProxy
|
from xmlrpc.client import Binary, ServerProxy
|
||||||
@@ -273,7 +274,8 @@ class ConnectionManager(QtCore.QThread):
|
|||||||
|
|
||||||
self._revpi.cleanup()
|
self._revpi.cleanup()
|
||||||
self._revpi_output.cleanup()
|
self._revpi_output.cleanup()
|
||||||
remove(self._revpi.procimg)
|
if settings.value("simulator/stop_remove", False, bool):
|
||||||
|
remove(self._revpi.procimg)
|
||||||
self._revpi = None
|
self._revpi = None
|
||||||
self._revpi_output = None
|
self._revpi_output = None
|
||||||
|
|
||||||
@@ -297,17 +299,18 @@ class ConnectionManager(QtCore.QThread):
|
|||||||
|
|
||||||
self.connection_disconnected.emit()
|
self.connection_disconnected.emit()
|
||||||
|
|
||||||
def pyload_simulate(self, configrsc: str, procimg: str):
|
def pyload_simulate(self, configrsc: str, procimg: str, clean_existing: bool):
|
||||||
"""Start the simulator for piControl on local computer."""
|
"""Start the simulator for piControl on local computer."""
|
||||||
pi.logger.debug("ConnectionManager.start_simulate")
|
pi.logger.debug("ConnectionManager.start_simulate")
|
||||||
|
|
||||||
with open(procimg, "wb") as fh:
|
if not exists(procimg) or clean_existing:
|
||||||
fh.write(b'\x00' * 4096)
|
with open(procimg, "wb") as fh:
|
||||||
|
fh.write(b'\x00' * 4096)
|
||||||
|
|
||||||
try:
|
try:
|
||||||
import revpimodio2
|
import revpimodio2
|
||||||
|
|
||||||
# Prepare process image with default values
|
# Prepare process image with default values for outputs
|
||||||
self._revpi_output = revpimodio2.RevPiModIO(configrsc=configrsc, procimg=procimg)
|
self._revpi_output = revpimodio2.RevPiModIO(configrsc=configrsc, procimg=procimg)
|
||||||
self._revpi_output.setdefaultvalues()
|
self._revpi_output.setdefaultvalues()
|
||||||
self._revpi_output.writeprocimg()
|
self._revpi_output.writeprocimg()
|
||||||
@@ -334,9 +337,14 @@ class ConnectionManager(QtCore.QThread):
|
|||||||
def reset_simulator(self):
|
def reset_simulator(self):
|
||||||
"""Reset all io to piCtory defaults."""
|
"""Reset all io to piCtory defaults."""
|
||||||
pi.logger.debug("ConnectionManager.reset_simulator")
|
pi.logger.debug("ConnectionManager.reset_simulator")
|
||||||
self._revpi_output.writeprocimg()
|
if settings.value("simulator/restart_zero", False, bool):
|
||||||
self._revpi.setdefaultvalues()
|
with open(self._revpi.procimg, "wb") as fh:
|
||||||
self._revpi.writeprocimg()
|
fh.write(b'\x00' * 4096)
|
||||||
|
self._revpi.readprocimg()
|
||||||
|
else:
|
||||||
|
self._revpi_output.writeprocimg()
|
||||||
|
self._revpi.setdefaultvalues()
|
||||||
|
self._revpi.writeprocimg()
|
||||||
|
|
||||||
def run(self):
|
def run(self):
|
||||||
"""Thread worker to check status of RevPiPyLoad."""
|
"""Thread worker to check status of RevPiPyLoad."""
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
__author__ = "Sven Sager"
|
__author__ = "Sven Sager"
|
||||||
__copyright__ = "Copyright (C) 2018 Sven Sager"
|
__copyright__ = "Copyright (C) 2018 Sven Sager"
|
||||||
__license__ = "GPLv3"
|
__license__ = "GPLv3"
|
||||||
__version__ = "0.9.1f"
|
__version__ = "0.9.1g"
|
||||||
|
|
||||||
import webbrowser
|
import webbrowser
|
||||||
from os.path import basename, dirname, join
|
from os.path import basename, dirname, join
|
||||||
@@ -22,6 +22,7 @@ from revpiinfo import RevPiInfo
|
|||||||
from revpioption import RevPiOption
|
from revpioption import RevPiOption
|
||||||
from revpiplclist import RevPiPlcList
|
from revpiplclist import RevPiPlcList
|
||||||
from revpiprogram import RevPiProgram
|
from revpiprogram import RevPiProgram
|
||||||
|
from simulator import Simulator
|
||||||
from ui.revpicommander_ui import Ui_win_revpicommander
|
from ui.revpicommander_ui import Ui_win_revpicommander
|
||||||
|
|
||||||
|
|
||||||
@@ -195,26 +196,15 @@ class RevPiCommander(QtWidgets.QMainWindow, Ui_win_revpicommander):
|
|||||||
"""Start the simulator function."""
|
"""Start the simulator function."""
|
||||||
helper.cm.pyload_disconnect()
|
helper.cm.pyload_disconnect()
|
||||||
|
|
||||||
diag_open = QtWidgets.QFileDialog(
|
diag = Simulator(self)
|
||||||
self, self.tr("Select downloaded piCtory file..."),
|
if diag.exec() != QtWidgets.QDialog.Accepted:
|
||||||
helper.settings.value("simulator_pictory", ".", str),
|
diag.deleteLater()
|
||||||
self.tr("piCtory file (*.rsc);;All files (*.*)")
|
|
||||||
)
|
|
||||||
diag_open.setAcceptMode(QtWidgets.QFileDialog.AcceptOpen)
|
|
||||||
diag_open.setFileMode(QtWidgets.QFileDialog.ExistingFile)
|
|
||||||
diag_open.setDefaultSuffix("rsc")
|
|
||||||
|
|
||||||
if diag_open.exec() != QtWidgets.QFileDialog.AcceptSave or len(diag_open.selectedFiles()) != 1:
|
|
||||||
return
|
return
|
||||||
|
|
||||||
configrsc_file = diag_open.selectedFiles()[0]
|
configrsc_file = helper.settings.value("simulator/configrsc", "", str)
|
||||||
dir_name = dirname(configrsc_file)
|
procimg_file = helper.settings.value("simulator/procimg", "", str)
|
||||||
procimg_file = join(dir_name, "{0}.img".format(
|
|
||||||
basename(configrsc_file).rsplit(".", maxsplit=1)[0]
|
|
||||||
))
|
|
||||||
helper.settings.setValue("simulator_pictory", configrsc_file)
|
|
||||||
|
|
||||||
if helper.cm.pyload_simulate(configrsc_file, procimg_file):
|
if helper.cm.pyload_simulate(configrsc_file, procimg_file, diag.cbx_stop_remove.isChecked()):
|
||||||
QtWidgets.QMessageBox.information(
|
QtWidgets.QMessageBox.information(
|
||||||
self, self.tr("Simulator started..."), self.tr(
|
self, self.tr("Simulator started..."), self.tr(
|
||||||
"The simulator is running!\n\nYou can work with this simulator if your call "
|
"The simulator is running!\n\nYou can work with this simulator if your call "
|
||||||
@@ -233,10 +223,12 @@ class RevPiCommander(QtWidgets.QMainWindow, Ui_win_revpicommander):
|
|||||||
QtWidgets.QMessageBox.critical(
|
QtWidgets.QMessageBox.critical(
|
||||||
self, self.tr("Can not start..."), self.tr(
|
self, self.tr("Can not start..."), self.tr(
|
||||||
"Can not start the simulator! Maybe the piCtory file is corrupt "
|
"Can not start the simulator! Maybe the piCtory file is corrupt "
|
||||||
"or you can not write to the location '{0}'."
|
"or you have no write permissions for '{0}'."
|
||||||
).format(dir_name)
|
).format(procimg_file)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
diag.deleteLater()
|
||||||
|
|
||||||
@QtCore.pyqtSlot()
|
@QtCore.pyqtSlot()
|
||||||
def on_act_logs_triggered(self):
|
def on_act_logs_triggered(self):
|
||||||
"""Show log window."""
|
"""Show log window."""
|
||||||
@@ -407,10 +399,10 @@ class RevPiCommander(QtWidgets.QMainWindow, Ui_win_revpicommander):
|
|||||||
if helper.cm.simulating:
|
if helper.cm.simulating:
|
||||||
rc = QtWidgets.QMessageBox.question(
|
rc = QtWidgets.QMessageBox.question(
|
||||||
self, self.tr("Reset to piCtory defaults..."), self.tr(
|
self, self.tr("Reset to piCtory defaults..."), self.tr(
|
||||||
"Do you want to reset your process image to piCtory default values?\n"
|
"Do you want to reset your process image to {0} values?\n"
|
||||||
"You have to stop other RevPiModIO programs before doing that, "
|
"You have to stop other RevPiModIO programs before doing that, "
|
||||||
"because they could reset the outputs."
|
"because they could reset the outputs."
|
||||||
)
|
).format("zero" if helper.settings.value("simulator/restart_zero", False, bool) else "piCtory default")
|
||||||
) == QtWidgets.QMessageBox.Yes
|
) == QtWidgets.QMessageBox.Yes
|
||||||
if rc:
|
if rc:
|
||||||
# Set piCtory default values in process image
|
# Set piCtory default values in process image
|
||||||
@@ -494,7 +486,7 @@ if __name__ == "__main__":
|
|||||||
|
|
||||||
win = RevPiCommander()
|
win = RevPiCommander()
|
||||||
win.show()
|
win.show()
|
||||||
exit_code = app.exec_()
|
exit_code = app.exec()
|
||||||
|
|
||||||
# Clean up workers
|
# Clean up workers
|
||||||
helper.cm.requestInterruption()
|
helper.cm.requestInterruption()
|
||||||
|
|||||||
@@ -25,7 +25,6 @@ class RevPiPlcList(QtWidgets.QDialog, Ui_diag_connections):
|
|||||||
def __init__(self, parent=None):
|
def __init__(self, parent=None):
|
||||||
super(RevPiPlcList, self).__init__(parent)
|
super(RevPiPlcList, self).__init__(parent)
|
||||||
self.setupUi(self)
|
self.setupUi(self)
|
||||||
self.setFixedSize(self.size())
|
|
||||||
self.__default_name = self.tr("New connection")
|
self.__default_name = self.tr("New connection")
|
||||||
self.__default_port = 55123
|
self.__default_port = 55123
|
||||||
|
|
||||||
|
|||||||
122
revpicommander/simulator.py
Normal file
122
revpicommander/simulator.py
Normal file
@@ -0,0 +1,122 @@
|
|||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
"""Simulator for piControl."""
|
||||||
|
__author__ = "Sven Sager"
|
||||||
|
__copyright__ = "Copyright (C) 2021 Sven Sager"
|
||||||
|
__license__ = "GPLv3"
|
||||||
|
|
||||||
|
from os import W_OK, access
|
||||||
|
from os.path import basename, dirname, exists, join
|
||||||
|
|
||||||
|
from PyQt5 import QtCore, QtGui, QtWidgets
|
||||||
|
|
||||||
|
import helper
|
||||||
|
from ui.simulator_ui import Ui_diag_simulator
|
||||||
|
|
||||||
|
|
||||||
|
class Simulator(QtWidgets.QDialog, Ui_diag_simulator):
|
||||||
|
"""
|
||||||
|
This is a configuration dialog for the simulator of piControl. The
|
||||||
|
selected values will be saved in QSettings section 'simulator' and can be
|
||||||
|
accessed by simulator starting classes.
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self, parent=None):
|
||||||
|
super(Simulator, self).__init__(parent)
|
||||||
|
self.setupUi(self)
|
||||||
|
self.clean_procimg = False
|
||||||
|
self.max_items = 5
|
||||||
|
|
||||||
|
self.cbb_history.addItem("", "")
|
||||||
|
lst_configrsc = helper.settings.value("simulator/history_configrsc", [], list)
|
||||||
|
lst_procimg = helper.settings.value("simulator/history_procimg", [], list)
|
||||||
|
for i in range(len(lst_configrsc)):
|
||||||
|
self.cbb_history.addItem(lst_configrsc[i], lst_procimg[i])
|
||||||
|
|
||||||
|
self.cbx_stop_remove.setChecked(helper.settings.value("simulator/stop_remove", False, bool))
|
||||||
|
self.rb_restart_pictory.setChecked(helper.settings.value("simulator/restart_pictory", False, bool))
|
||||||
|
self.rb_restart_zero.setChecked(helper.settings.value("simulator/restart_zero", False, bool))
|
||||||
|
|
||||||
|
self.btn_start_pictory.setEnabled(False)
|
||||||
|
self.btn_start_empty.setEnabled(False)
|
||||||
|
self.btn_start_nochange.setEnabled(False)
|
||||||
|
|
||||||
|
self.txt_configrsc.textChanged.connect(self.on_txt_textChanged)
|
||||||
|
self.txt_procimg.textChanged.connect(self.on_txt_textChanged)
|
||||||
|
|
||||||
|
def _save_gui(self) -> None:
|
||||||
|
helper.settings.setValue("simulator/stop_remove", self.cbx_stop_remove.isChecked())
|
||||||
|
helper.settings.setValue("simulator/restart_pictory", self.rb_restart_pictory.isChecked())
|
||||||
|
helper.settings.setValue("simulator/restart_zero", self.rb_restart_zero.isChecked())
|
||||||
|
|
||||||
|
def accept(self) -> None:
|
||||||
|
self.cbb_history.removeItem(0)
|
||||||
|
if self.cbb_history.findText(self.txt_configrsc.text()) == -1:
|
||||||
|
self.cbb_history.addItem(self.txt_configrsc.text(), self.txt_procimg.text())
|
||||||
|
if self.cbb_history.count() > self.max_items:
|
||||||
|
self.cbb_history.removeItem(self.max_items)
|
||||||
|
|
||||||
|
helper.settings.setValue("simulator/configrsc", self.txt_configrsc.text())
|
||||||
|
helper.settings.setValue("simulator/procimg", self.txt_procimg.text())
|
||||||
|
self._save_gui()
|
||||||
|
|
||||||
|
lst_configrsc = []
|
||||||
|
lst_procimg = []
|
||||||
|
for i in range(self.cbb_history.count()):
|
||||||
|
lst_configrsc.append(self.cbb_history.itemText(i))
|
||||||
|
lst_procimg.append(self.cbb_history.itemData(i))
|
||||||
|
helper.settings.setValue("simulator/history_configrsc", lst_configrsc)
|
||||||
|
helper.settings.setValue("simulator/history_procimg", lst_procimg)
|
||||||
|
|
||||||
|
self.clean_procimg = self.sender() is self.btn_start_empty
|
||||||
|
|
||||||
|
super(Simulator, self).accept()
|
||||||
|
|
||||||
|
def closeEvent(self, a0: QtGui.QCloseEvent) -> None:
|
||||||
|
self._save_gui()
|
||||||
|
|
||||||
|
@QtCore.pyqtSlot()
|
||||||
|
def on_btn_configrsc_clicked(self) -> None:
|
||||||
|
diag_open = QtWidgets.QFileDialog(
|
||||||
|
self, self.tr("Select downloaded piCtory file..."),
|
||||||
|
helper.settings.value("simulator/last_dir", ".", str),
|
||||||
|
self.tr("piCtory file (*.rsc);;All files (*.*)")
|
||||||
|
)
|
||||||
|
diag_open.setAcceptMode(QtWidgets.QFileDialog.AcceptOpen)
|
||||||
|
diag_open.setFileMode(QtWidgets.QFileDialog.ExistingFile)
|
||||||
|
diag_open.setDefaultSuffix("rsc")
|
||||||
|
|
||||||
|
if diag_open.exec() != QtWidgets.QFileDialog.AcceptSave or len(diag_open.selectedFiles()) != 1:
|
||||||
|
diag_open.deleteLater()
|
||||||
|
return
|
||||||
|
|
||||||
|
configrsc_file = diag_open.selectedFiles()[0]
|
||||||
|
dir_name = dirname(configrsc_file)
|
||||||
|
procimg_file = join(dir_name, "{0}.img".format(basename(configrsc_file).rsplit(".", maxsplit=1)[0]))
|
||||||
|
self.txt_configrsc.setText(configrsc_file)
|
||||||
|
self.txt_procimg.setText(procimg_file)
|
||||||
|
|
||||||
|
helper.settings.setValue("simulator/last_dir", dir_name)
|
||||||
|
diag_open.deleteLater()
|
||||||
|
|
||||||
|
@QtCore.pyqtSlot(int)
|
||||||
|
def on_cbb_history_currentIndexChanged(self, index: int) -> None:
|
||||||
|
if index == 0:
|
||||||
|
return
|
||||||
|
self.txt_configrsc.setText(self.cbb_history.itemText(index))
|
||||||
|
self.txt_procimg.setText(self.cbb_history.itemData(index))
|
||||||
|
|
||||||
|
@QtCore.pyqtSlot(str)
|
||||||
|
def on_txt_textChanged(self, text: str) -> None:
|
||||||
|
configrsc_file = self.txt_configrsc.text()
|
||||||
|
procimg_file = self.txt_procimg.text()
|
||||||
|
if configrsc_file and procimg_file:
|
||||||
|
file_access = access(procimg_file, W_OK)
|
||||||
|
self.txt_info.setPlainText("configrsc=\"{0}\", procimg=\"{1}\"".format(configrsc_file, procimg_file))
|
||||||
|
self.btn_start_pictory.setEnabled(file_access)
|
||||||
|
self.btn_start_empty.setEnabled(file_access)
|
||||||
|
self.btn_start_nochange.setEnabled(file_access and exists(procimg_file))
|
||||||
|
else:
|
||||||
|
self.txt_info.clear()
|
||||||
|
self.btn_start_pictory.setEnabled(False)
|
||||||
|
self.btn_start_empty.setEnabled(False)
|
||||||
|
self.btn_start_nochange.setEnabled(False)
|
||||||
2
setup.py
2
setup.py
@@ -19,7 +19,7 @@ class MyEggInfo(distutils.command.install_egg_info.install_egg_info):
|
|||||||
|
|
||||||
|
|
||||||
setup(
|
setup(
|
||||||
version="0.9.1f",
|
version="0.9.1g",
|
||||||
python_requires="~=3.4",
|
python_requires="~=3.4",
|
||||||
requires=["PyQt5", "revpimodio2", "zeroconf"],
|
requires=["PyQt5", "revpimodio2", "zeroconf"],
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user