예제 #1
0
    def loadEdfFile(self):
        filePath = QFileDialog.getOpenFileName(self,
                                               u'Choose edf to load',
                                               "./output/",
                                               filter="*.edf",
                                               selectedFilter="*.edf")
        if filePath:
            try:
                self.tabCount += 1
                fileName = ntpath.basename(unicode(filePath))
                jobWidget = JobWidget(self.getParams())
                jobWidget.jobProgressWidget.hide()
                jobWidget.runtimeWidget.hide()
                tabIndex = self.jobTabs.addTab(jobWidget,
                                               u"{0}".format(fileName))
                self.jobs[self.tabCount] = jobWidget
                self.showJobGroup(True)
                self.jobTabs.setCurrentIndex(tabIndex)
                jobWidget.sigCloseJob.connect(
                    lambda jobIndex=self.tabCount: self.closeJob(jobIndex))

                self.uiFinishWait()
                jobWidget.status = STATUS_FINISHED
                jobWidget.displayOutput(unicode(filePath))
            except Exception as e:
                message = QErrorMessage(self)
                message.showMessage(
                    u"Unable to load {0}. Error message: {1}".format(
                        filePath, e.message))
                jobWidget.closeJob()
예제 #2
0
 def accept(self):
     """Acepta el dialogo. Coge la operacion con la que esta trabajando 
     el usuario e inicia el procedimiento de calculo"""
     from pyrqt.excepciones import OpcionesIncorrectaException
     import rpy
     nombre = unicode(self.ui.treeWidget.currentItem().text(0))
     widget = self.__widgets["operaciones"][nombre]
     try:
         resultado = self.__gestoroperaciones[nombre].procedimiento(widget.seleccion(), widget.opciones())
     except OpcionesIncorrectaException:
         errormessage = QErrorMessage(self)
         errormessage.showMessage(u"Las opciones no son correctas")
     #except IndexError:
     #    errormessage = QErrorMessage(self)
     #    errormessage.showMessage(u"Seleccion incorrecta")
     #    LOG.exception("excepcion capturada")
     except KeyError:
         QErrorMessage(self).showMessage(u"Hay elementos de la salida sin definir(o mal definidos) en la operación")
         LOG.exception("Excepción Generada por un módulo de operaciones")
     except rpy.RException:
         QErrorMessage(self).showMessage(u"R devolvio un error")
         log.exception("Excepción de RPY")
     except AssertionError:
         QErrorMessage(self).showMessage(u"Error desconocido")
     else:
         self.__vsalida.ana_res(resultado) #Añadir a la salida el resultado
         self.__vsalida.hide() #TODO averiguar como hacer para que recupere el foco sin ocultar la ventana
         self.__vsalida.show()
예제 #3
0
    def __init__(self, parent=None):
        """The constructor sets up the MainWindow widget, and connects
        all necessary signals and slots
        """
        super(MainWindow, self).__init__(parent)
        self.setupUi(self)
        # We store the window size to make sure the previous window size
        # is restored when leaving fullscreen mode. This varible is used
        # in the toggleFullscreen slot.
        self.__tmpWinSize = self.size()
        self.eventFilter = LumaEventFilter(self)

        self.mainTabs.installEventFilter(self.eventFilter)

        self.translator = QTranslator()
        self.languageHandler = LanguageHandler()
        self.languages = self.languageHandler.availableLanguages

        #self.__createPluginToolBar()
        self.__createLoggerWidget()
        self.__loadSettings()
        self.__createLanguageOptions()

        self.setStatusBar(self.statusBar)

        self.mainTabs.setTabsClosable(True)
        self.mainTabs.setContextMenuPolicy(Qt.CustomContextMenu)
        self.mainTabs.customContextMenuRequested.connect(
            self.__mainTabsContextMenu)

        self.defaultTabStyle = ''
        self.lumaHeadStyle = 'background: url(:/icons/luma-gray);\n' + \
                     'background-position: bottom right;\n' + \
                     'background-attachment: fixed;\n' + \
                     'background-repeat:  no-repeat;'

        #Sets up pluginWidget
        #self in parameter is used to call pluginSelected here...
        self.pluginWidget = PluginListWidget(self)
        self.showPlugins()

        self.welcomeTab = WelcomeTab()
        self.welcomeTab.textBrowser.setStyleSheet(self.lumaHeadStyle)

        #This value comes from __loadSettings()
        #Its a checkbox set in WelcomeTab
        if self.showWelcomeSettings == 2:
            self.showWelcome()
        else:
            # Let's do some styling of the tab widget when no tabs are opened
            if self.mainTabs.currentIndex() == -1:
                self.__setTabWidgetStyle(self.lumaHeadStyle)

            self.actionShowWelcomeTab.setEnabled(True)

        self.serversChangedMessage = QErrorMessage(self)
예제 #4
0
    def __init__(self, args):
        super(QApplication, self).__init__(args)

        self.error_msg = QErrorMessage()
        self.ipcon = IPConnection()

        signal.signal(signal.SIGINT, self.exit_demo)
        signal.signal(signal.SIGTERM, self.exit_demo)

        timer = QTimer(self)
        timer.setSingleShot(True)
        timer.timeout.connect(self.connect)
        timer.start(1)
예제 #5
0
	def second_channel_changed(self, index):
		self.ui.actionStart.setChecked(False)
		
		success, index = self.audiobackend.select_second_channel(index)
		
		self.settings_dialog.comboBox_secondChannel.setCurrentIndex(index)
		
		if not success:
			# Note: the error message is a child of the settings dialog, so that
			# that dialog remains on top when the error message is closed
			error_message = QErrorMessage(self.settings_dialog)
			error_message.setWindowTitle("Input device error")
			error_message.showMessage("Impossible to use the selected channel as the second channel, reverting to the previous one")
		
		self.ui.actionStart.setChecked(True)
예제 #6
0
    def process(self):
        search_name = self.searchName.text()
        layer = self.layerCombo.currentLayer()
        expression = self.fieldExpressionWidget.currentField()[0]
        priority = self.priorityBox.value()
        srid = layer.crs().authid()
        evaluate_directly = self.evaluateCheckBox.isChecked()

        if self.projectSearch is None:
            self.projectSearch = self.project_search_model.addSearch(
                search_name, layer, expression, priority)
        else:
            self.projectSearch.edit(search_name, layer.id(), layer.name(),
                                    expression, priority, srid)

        if evaluate_directly:
            self.progressBar.setMinimum(0)
            self.progressBar.setMaximum(layer.featureCount())
            self.progressBar.show()
            self.cancelButton.show()

            ok, message = self.project_finder.recordSearch(self.projectSearch)

            self.progressBar.hide()
            self.cancelButton.hide()
            self.okButton.show()

            if not ok:
                QErrorMessage().showMessage(message)
                return

        self.close()
예제 #7
0
    def batchFinished(self):
        self.base.stop()

        if len(self.errors) > 0:
            msg = u"Processing of the following files ended with error: <br><br>" + "<br><br>".join(
                self.errors)
            QErrorMessage(self).showMessage(msg)

        inDir = self.getInputFileName()
        outDir = self.getOutputFileName()
        if outDir is None or inDir == outDir:
            self.outFiles = self.inFiles

        # load layers managing the render flag to avoid waste of time
        canvas = self.iface.mapCanvas()
        previousRenderFlag = canvas.renderFlag()
        canvas.setRenderFlag(False)
        notCreatedList = []
        for item in self.outFiles:
            fileInfo = QFileInfo(item)
            if fileInfo.exists():
                if self.base.loadCheckBox.isChecked():
                    self.addLayerIntoCanvas(fileInfo)
            else:
                notCreatedList.append(item)
        canvas.setRenderFlag(previousRenderFlag)

        if len(notCreatedList) == 0:
            QMessageBox.information(self, self.tr("Finished"),
                                    self.tr("Operation completed."))
        else:
            QMessageBox.warning(
                self, self.tr("Warning"),
                self.tr("The following files were not created: \n{0}").format(
                    ', '.join(notCreatedList)))
예제 #8
0
파일: dc.py 프로젝트: karstenerhardt/brickv
 def __init__(self, ipcon, uid, version):
     PluginBase.__init__(self, ipcon, uid, 'DC Brick', version)
     
     self.setupUi(self)
     self.encoder_hide_all()
     
     self.dc = BrickDC(uid, ipcon)
     self.device = self.dc
     
     self.update_timer = QTimer()
     self.update_timer.timeout.connect(self.update_data)
     
     self.speedometer = SpeedoMeter()
     self.vertical_layout_right.insertWidget(4, self.speedometer)
     
     self.new_value = 0
     self.update_counter = 0
     
     self.full_brake_time = 0
     
     self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
     self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
     self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
     
     self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
     self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
     self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
     
     self.frequency_slider.sliderReleased.connect(self.frequency_slider_released)
     self.frequency_slider.valueChanged.connect(self.frequency_spin.setValue)
     self.frequency_spin.editingFinished.connect(self.frequency_spin_finished)
     
     self.radio_mode_brake.toggled.connect(self.brake_value_changed)
     self.radio_mode_coast.toggled.connect(self.coast_value_changed)
     
     self.minimum_voltage_button.pressed.connect(self.minimum_voltage_button_pressed)
     self.full_brake_button.pressed.connect(self.full_brake_pressed)
     self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
     
     self.emergency_signal = None
     self.under_signal = None
     self.current_velocity_signal = None
     self.velocity_reached_signal = None
     
     self.qem = QErrorMessage(self)
     
     self.qtcb_under_voltage.connect(self.cb_under_voltage)
     self.dc.register_callback(self.dc.CALLBACK_UNDER_VOLTAGE,
                               self.qtcb_under_voltage.emit) 
     
     self.qtcb_emergency_shutdown.connect(self.cb_emergency_shutdown)
     self.dc.register_callback(self.dc.CALLBACK_EMERGENCY_SHUTDOWN,
                               self.qtcb_emergency_shutdown.emit) 
     
     self.qtcb_position_reached.connect(self.update_velocity)
     self.dc.register_callback(self.dc.CALLBACK_VELOCITY_REACHED,
                               self.qtcb_position_reached.emit) 
     self.dc.register_callback(self.dc.CALLBACK_CURRENT_VELOCITY,
                               self.qtcb_position_reached.emit)
예제 #9
0
    def processFinished(self, errors):
        self.stopProcessing()
        self.restoreGui()

        if errors:
            msg = self.tr("Processing of the following layers/files ended with error:<br><br>") + "<br>".join(errors)
            QErrorMessage(self).showMessage(msg)

        QMessageBox.information(self, self.tr("Finished"), self.tr("Processing completed."))
예제 #10
0
파일: MainWindow.py 프로젝트: einaru/luma
    def __init__(self, parent=None):
        """The constructor sets up the MainWindow widget, and connects
        all necessary signals and slots
        """
        super(MainWindow, self).__init__(parent)
        self.setupUi(self)
        # We store the window size to make sure the previous window size
        # is restored when leaving fullscreen mode. This varible is used
        # in the toggleFullscreen slot.
        self.__tmpWinSize = self.size()
        self.eventFilter = LumaEventFilter(self)

        self.mainTabs.installEventFilter(self.eventFilter)

        self.translator = QTranslator()
        self.languageHandler = LanguageHandler()
        self.languages = self.languageHandler.availableLanguages

        #self.__createPluginToolBar()
        self.__createLoggerWidget()
        self.__loadSettings()
        self.__createLanguageOptions()

        self.setStatusBar(self.statusBar)

        self.mainTabs.setTabsClosable(True)
        self.mainTabs.setContextMenuPolicy(Qt.CustomContextMenu)
        self.mainTabs.customContextMenuRequested.connect(
            self.__mainTabsContextMenu)

        self.defaultTabStyle = ''
        self.lumaHeadStyle = 'background: url(:/icons/luma-gray);\n' + \
                     'background-position: bottom right;\n' + \
                     'background-attachment: fixed;\n' + \
                     'background-repeat:  no-repeat;'

        #Sets up pluginWidget
        #self in parameter is used to call pluginSelected here...
        self.pluginWidget = PluginListWidget(self)
        self.showPlugins()

        self.welcomeTab = WelcomeTab()
        self.welcomeTab.textBrowser.setStyleSheet(self.lumaHeadStyle)

        #This value comes from __loadSettings()
        #Its a checkbox set in WelcomeTab
        if self.showWelcomeSettings == 2:
            self.showWelcome()
        else:
            # Let's do some styling of the tab widget when no tabs are opened
            if self.mainTabs.currentIndex() == -1:
                self.__setTabWidgetStyle(self.lumaHeadStyle)

            self.actionShowWelcomeTab.setEnabled(True)

        self.serversChangedMessage = QErrorMessage(self)
예제 #11
0
    def __init__(self, args):
        super(QApplication, self).__init__(args)

        self.error_msg = QErrorMessage()
        self.error_msg.setWindowTitle("Starter Kit: Blinkenlights Demo " + config.DEMO_VERSION)

        signal.signal(signal.SIGINT, self.exit_demo)
        signal.signal(signal.SIGTERM, self.exit_demo)

        self.make_gui()
        self.connect()
예제 #12
0
    def loadFields(self, vectorFile):
        self.attributeComboBox.clear()

        if not vectorFile:
            return

        try:
            (fields, names) = Utils.getVectorFields(vectorFile)
        except Utils.UnsupportedOGRFormat, e:
            QErrorMessage(self).showMessage(e.args[0])
            self.inSelector.setLayer(None)
            return
예제 #13
0
    def __init__(self, args):
        super(QApplication, self).__init__(args)

        self.error_msg = QErrorMessage()
        self.ipcon = IPConnection()

        signal.signal(signal.SIGINT, self.exit_demo)
        signal.signal(signal.SIGTERM, self.exit_demo)

        timer = QTimer(self)
        timer.setSingleShot(True)
        timer.timeout.connect(self.connect)
        timer.start(1)
예제 #14
0
    def __init__(self, parent, app):
        super(QWidget, self).__init__()
        self.app = app

        self.setupUi(self)

        self.error_msg = QErrorMessage()
        self.error_msg.setWindowTitle("Starter Kit: Blinkenlights Demo " +
                                      config.DEMO_VERSION)

        self.slider_frame_rate.valueChanged.connect(
            self.slider_frame_rate_changed)
        self.spinbox_frame_rate.valueChanged.connect(
            self.spinbox_frame_rate_changed)
        self.button_choose.pressed.connect(self.choose_pressed)
        self.button_show.pressed.connect(self.show_pressed)
        self.button_default.pressed.connect(self.default_pressed)

        self.update_frame_rate_timer = QTimer(self)
        self.update_frame_rate_timer.timeout.connect(self.update_frame_rate)

        self.default_pressed()
예제 #15
0
    def __init__(self, parent=None):
        super(DialogService, self).__init__(parent)

        # All-purpose error popup message:
        # Used by self.showErrorMsgByErrorCode(<errorCode>),
        # or self.showErrorMsg(<string>). Returns a
        # QErrorMessage without parent, but with QWindowFlags set
        # properly to be a dialog popup box:
        self.errorMsgPopup = QErrorMessage.qtHandler()
        # Re-parent the popup, retaining the window flags set
        # by the qtHandler:
        self.errorMsgPopup.setParent(parent, self.errorMsgPopup.windowFlags())
        # self.errorMsgPopup.setStyleSheet(SpeakEasyGUI.stylesheetAppBG);
        self.infoMsg = QMessageBox(parent=parent)
예제 #16
0
    def __init__(self, parent=None):
        super(DialogService, self).__init__(parent)

        # All-purpose error popup message:
        # Used by self.showErrorMsgByErrorCode(<errorCode>),
        # or self.showErrorMsg(<string>). Returns a
        # QErrorMessage without parent, but with QWindowFlags set
        # properly to be a dialog popup box:
        self.errorMsgPopup = QErrorMessage.qtHandler()
        # Re-parent the popup, retaining the window flags set
        # by the qtHandler:
        self.errorMsgPopup.setParent(parent, self.errorMsgPopup.windowFlags())
        #self.errorMsgPopup.setStyleSheet(SpeakEasyGUI.stylesheetAppBG);
        self.infoMsg = QMessageBox(parent=parent)
예제 #17
0
    def processFinished(self, errors):
        self.stopProcessing()
        outPath = self.outShape.text()
        self.restoreGui()

        if errors:
            msg = self.tr(
                "Processing of the following layers/files ended with error:<br><br>"
            ) + "<br>".join(errors)
            QErrorMessage(self).showMessage(msg)

        QMessageBox.information(
            self, self.tr("Vector Split"),
            self.tr("Created output shapefiles in folder:\n%s") % (outPath))
예제 #18
0
    def addScanNumbers(self):
        result = self.range_dialog.exec_()
        if result == QDialog.Accepted:
            text = self.range_ui.range_edit.text()
            if text:
                not_found = []
                numbers = mythen.parse_range_list(text)
                year, visit = self.getYearAndVisit()
                progress = QProgressDialog(
                    "Locating scan files from numbers...", "Stop", 0,
                    len(numbers), self)
                progress.setWindowModality(Qt.WindowModal)
                progress.forceShow()
                progress.setValue(0)
                for n in numbers:
                    progress.setValue(progress.value() + 1)
                    if progress.wasCanceled():
                        break

                    files = mythen.find_mythen_files(
                        n, visit=visit,
                        year=year)  # FIXME needs to be in separate thread(!)
                    if files:
                        files = [f for f in files if f not in self.scans]
                        self.scans.extend(files)
                        self.scans_model.setStringList(self.scans)
                    else:
                        not_found.append(n)

                progress.setValue(progress.maximum())

                if not_found:
                    error = QErrorMessage(self)
                    msg = "The following numbers were not found: "
                    for n in not_found:
                        msg = msg + str(n) + ", "
                    error.showMessage(msg[:-2])
예제 #19
0
    def crear_y_seleccionar_archivo(self, nombre):
        # Quita la extension si llega a tenerla.
        nombre = nombre.replace('.py', '')
        nombre += ".py"
        nombre_de_archivo = nombre

        if self.ruta_del_archivo_actual:
            base_path = os.path.abspath(
                os.path.dirname(self.ruta_del_archivo_actual))
            ruta = os.path.join(base_path, unicode(nombre_de_archivo))
        else:
            ruta = unicode(nombre_de_archivo)

        if os.path.exists(ruta):
            self._tmp_dialog = QErrorMessage(self)
            self._tmp_dialog.showMessage("Ya existe un archivo con ese nombre")
        else:
            self._crear_archivo_nuevo_en(ruta)

            self.cargar_contenido_desde_archivo(ruta)
            self.ruta_del_archivo_actual = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()
예제 #20
0
    def loadFields(self, vectorFile=''):
        self.zfieldCombo.clear()

        if not vectorFile:
            return

        try:
            (fields, names) = Utils.getVectorFields(vectorFile)
        except Utils.UnsupportedOGRFormat as e:
            QErrorMessage(self).showMessage(e.args[0])
            self.inSelector.setLayer(None)
            return

        ncodec = QTextCodec.codecForName(self.lastEncoding)
        for name in names:
            self.zfieldCombo.addItem(ncodec.toUnicode(name))
예제 #21
0
    def input_device_changed(self, index):
        success, index = self.audio_device.select_input_device(index)
        self.ui.DeviceList.setCurrentIndex(index)
        self.fft_plot.must_plot = True
        if not success:
# Note: the error message is a child of the settings dialog, so that
# that dialog remains on top when the error message is closed
            error_message = QErrorMessage(self.settings_dialog)
            error_message.setWindowTitle("Input device error")
            error_message.showMessage("Impossible to use the selected input"
                                      " device, reverting to the previous one")
예제 #22
0
    def onError(self, error):
        if error == QProcess.FailedToStart:
            msg = QCoreApplication.translate(
                "GdalTools",
                "The process failed to start. Either the invoked program is missing, or you may have insufficient permissions to invoke the program."
            )
        elif error == QProcess.Crashed:
            msg = QCoreApplication.translate(
                "GdalTools",
                "The process crashed some time after starting successfully.")
        else:
            msg = QCoreApplication.translate("GdalTools",
                                             "An unknown error occurred.")

        QErrorMessage(self).showMessage(msg)
        QApplication.processEvents()  # give the user chance to see the message

        self.stop()
예제 #23
0
    def __init__(self, parent, app):
        super(QWidget, self).__init__()
        self.app = app

        self.setupUi(self)

        self.error_msg = QErrorMessage()
        self.error_msg.setWindowTitle("Starter Kit: Blinkenlights Demo " + config.DEMO_VERSION)

        self.slider_frame_rate.valueChanged.connect(self.slider_frame_rate_changed)
        self.spinbox_frame_rate.valueChanged.connect(self.spinbox_frame_rate_changed)
        self.button_choose.pressed.connect(self.choose_pressed)
        self.button_show.pressed.connect(self.show_pressed)
        self.button_default.pressed.connect(self.default_pressed)

        self.update_frame_rate_timer = QTimer(self)
        self.update_frame_rate_timer.timeout.connect(self.update_frame_rate)

        self.default_pressed()
예제 #24
0
    def onFinished(self, exitCode, status):
        if status == QProcess.CrashExit:
            self.stop()
            return

        if self.command.find("gdalinfo") != -1 and exitCode == 0:
            self.emit(SIGNAL("finished(bool)"), self.loadCheckBox.isChecked())
            self.stop()
            return

        # show the error message if there's one, otherwise show the process output message
        msg = unicode(self.process.readAllStandardError())
        if msg == '':
            outMessages = unicode(
                self.process.readAllStandardOutput()).splitlines()

            # make sure to not show the help
            for m in outMessages:
                m = string.strip(m)
                if m == '':
                    continue
                # TODO fix this
                #if m.contains( QRegExp( "^(?:[Uu]sage:\\s)?" + QRegExp.escape(self.command) + "\\s" ) ):
                #  if msg.isEmpty():
                #    msg = self.tr ( "Invalid parameters." )
                #  break
                #if m.contains( QRegExp( "0(?:\\.+[1-9]0{1,2})+" ) ):
                #  continue

                if msg:
                    msg += "\n"
                msg += m

        QErrorMessage(self).showMessage(msg.replace("\n", "<br>"))

        if exitCode == 0:
            self.emit(SIGNAL("finished(bool)"), self.loadCheckBox.isChecked())

        self.stop()
예제 #25
0
파일: editor.py 프로젝트: pprofpc/pilas
    def crear_y_seleccionar_archivo(self, nombre):
        # Quita la extension si llega a tenerla.
        nombre = nombre.replace('.py', '')
        nombre += ".py"
        nombre_de_archivo = nombre

        if self.ruta_del_archivo_actual:
            base_path = os.path.abspath(os.path.dirname(self.ruta_del_archivo_actual))
            ruta = os.path.join(base_path, unicode(nombre_de_archivo))
        else:
            ruta = unicode(nombre_de_archivo)

        if os.path.exists(ruta):
            self._tmp_dialog = QErrorMessage(self)
            self._tmp_dialog.showMessage("Ya existe un archivo con ese nombre")
        else:
            self._crear_archivo_nuevo_en(ruta)

            self.cargar_contenido_desde_archivo(ruta)
            self.ruta_del_archivo_actual = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()
 def loadParameterSet(self):
     s = QSettings()
     name = self.configCombo.currentText()
     s.beginGroup('ParameterSets')
     if not name in s.childGroups():
         dlg = QErrorMessage(self)
         dlg.setWindowTitle('Error')
         dlg.showMessage('No saved parameters available for %s' % name)
         return
     s.beginGroup(name)
     for item in self.parameterItems:
         item.setValue(s.value(item.objectName(), item.value(), type=float))
     self.adjustExcitationCb.setChecked(s.value('adjustExcitation', False, type=bool))
     self.sensorNameLe.setText(s.value('sensorName', '', type=QString))
     self.visaCombo.setCurrentIndex(self.visaCombo.findText(s.value('sr830Visa', 'GPIB0::12', type=QString)))
     self.autoRangingCb.setChecked(s.value('autoRanging', True, type=bool))
     self.minSensitivityCombo.setCurrentCodeSilently(s.value('minSensitivity', 0, type=int))
     s.endGroup()
     s.endGroup()
예제 #27
0
파일: dc.py 프로젝트: fscherwi/brickv
    def __init__(self, *args):
        PluginBase.__init__(self, BrickDC, *args)

        self.setupUi(self)

        self.dc = self.device

        self.encoder_hide_all()

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(4, self.speedometer)

        self.new_value = 0
        self.update_counter = 0

        self.full_brake_time = 0

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.frequency_syncer = SliderSpinSyncer(self.frequency_slider,
                                                 self.frequency_spin,
                                                 self.frequency_changed)

        self.radio_mode_brake.toggled.connect(self.brake_value_changed)
        self.radio_mode_coast.toggled.connect(self.coast_value_changed)

        self.minimum_voltage_button.clicked.connect(
            self.minimum_voltage_button_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)

        self.emergency_signal = None
        self.under_signal = None
        self.current_velocity_signal = None
        self.velocity_reached_signal = None

        self.qem = QErrorMessage(self)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.dc.register_callback(self.dc.CALLBACK_UNDER_VOLTAGE,
                                  self.qtcb_under_voltage.emit)

        self.qtcb_emergency_shutdown.connect(self.cb_emergency_shutdown)
        self.dc.register_callback(self.dc.CALLBACK_EMERGENCY_SHUTDOWN,
                                  self.qtcb_emergency_shutdown.emit)

        self.qtcb_velocity_reached.connect(self.update_velocity)
        self.dc.register_callback(self.dc.CALLBACK_VELOCITY_REACHED,
                                  self.qtcb_velocity_reached.emit)

        self.cbe_current_velocity = CallbackEmulator(
            self.dc.get_current_velocity, self.update_velocity,
            self.increase_error_count)

        if self.firmware_version >= (1, 1, 3):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.dc.reset())
            self.set_actions(reset)
예제 #28
0
class Blinkenlights(QApplication):
    HOST = "localhost"
    PORT = 4223

    ipcon = None

    projects = []
    active_project = None

    error_msg = None

    def __init__(self, args):
        super(QApplication, self).__init__(args)

        self.error_msg = QErrorMessage()
        self.error_msg.setWindowTitle("Starter Kit: Blinkenlights Demo " + config.DEMO_VERSION)

        signal.signal(signal.SIGINT, self.exit_demo)
        signal.signal(signal.SIGTERM, self.exit_demo)

        self.make_gui()
        self.connect()

    def exit_demo(self, signl=None, frme=None):
        try:
            self.ipcon.disconnect()
            self.timer.stop()
            self.tabs.destroy()
        except:
            pass

        sys.exit()

    def make_gui(self):
        self.main = MainWindow(self)
        self.main.setWindowIcon(QIcon(os.path.join(ProgramPath.program_path(), "demo-icon.png")))

        self.tabs = QTabWidget()

        widget = QWidget()
        layout = QVBoxLayout()
        layout.addWidget(self.tabs)
        widget.setLayout(layout)

        self.main.setCentralWidget(widget)

        self.setup = SetupWidget(self.tabs, self)
        self.tetris = TetrisWidget(self.tabs, self)
        self.pong = PongWidget(self.tabs, self)
        self.fire = FireWidget(self.tabs, self)
        self.text = TextWidget(self.tabs, self)
        self.images = ImagesWidget(self.tabs, self)
        self.rainbow = RainbowWidget(self.tabs, self)

        self.projects.append(self.setup)
        self.projects.append(self.tetris)
        self.projects.append(self.pong)
        self.projects.append(self.fire)
        self.projects.append(self.text)
        self.projects.append(self.images)
        self.projects.append(self.rainbow)

        self.tabs.addTab(self.setup, "Setup")
        self.tabs.addTab(self.tetris, "Tetris")
        self.tabs.addTab(self.pong, "Pong")
        self.tabs.addTab(self.fire, "Fire")
        self.tabs.addTab(self.text, "Text")
        self.tabs.addTab(self.images, "Images")
        self.tabs.addTab(self.rainbow, "Rainbow")

        self.active_project = self.projects[0]

        self.tabs.currentChanged.connect(self.tab_changed_slot)

        self.main.setWindowTitle("Starter Kit: Blinkenlights Demo " + config.DEMO_VERSION)
        self.main.show()

    def connect(self):
        config.UID_LED_STRIP_BRICKLET = None
        self.setup.label_led_strip_found.setText('No')
        self.setup.label_led_strip_uid.setText('None')

        config.UID_MULTI_TOUCH_BRICKLET = None
        self.setup.label_multi_touch_found.setText('No')
        self.setup.label_multi_touch_uid.setText('None')

        config.UID_DUAL_BUTTON_BRICKLET = (None, None)
        self.setup.label_dual_button1_found.setText('No')
        self.setup.label_dual_button1_uid.setText('None')
        self.setup.label_dual_button2_found.setText('No')
        self.setup.label_dual_button2_uid.setText('None')

        config.UID_PIEZO_SPEAKER_BRICKLET = None
        self.setup.label_piezo_speaker_found.setText('No')
        self.setup.label_piezo_speaker_uid.setText('None')

        config.UID_SEGMENT_DISPLAY_4X7_BRICKLET = None
        self.setup.label_segment_display_found.setText('No')
        self.setup.label_segment_display_uid.setText('None')

        if self.ipcon != None:
            try:
                self.ipcon.disconnect()
            except:
                pass

        self.ipcon = IPConnection()

        host = self.setup.edit_host.text()
        port = self.setup.spinbox_port.value()
        try:
            self.ipcon.connect(host, port)
        except Error as e:
            self.error_msg.showMessage('Connection Error: ' + str(e.description) + "<br><br>Brickd installed and running?")
            return
        except socket.error as e:
            self.error_msg.showMessage('Socket error: ' + str(e) + "<br><br>Brickd installed and running?")
            return

        self.ipcon.register_callback(IPConnection.CALLBACK_ENUMERATE,
                                     self.cb_enumerate)
        self.ipcon.register_callback(IPConnection.CALLBACK_CONNECTED,
                                     self.cb_connected)

        # Wait for a second to give user visual feedback
        timer = QTimer(self)
        timer.setSingleShot(True)
        timer.timeout.connect(self.ipcon.enumerate)
        timer.start(250)

    def tab_changed_slot(self, tabIndex):
        self.active_project.stop()
        self.active_project = self.projects[tabIndex]
        self.active_project.start()

    def cb_enumerate(self, uid, connected_uid, position, hardware_version,
                     firmware_version, device_identifier, enumeration_type):
        if enumeration_type == IPConnection.ENUMERATION_TYPE_CONNECTED or \
           enumeration_type == IPConnection.ENUMERATION_TYPE_AVAILABLE:
            if device_identifier == LEDStrip.DEVICE_IDENTIFIER:
                config.UID_LED_STRIP_BRICKLET = uid
                self.setup.label_led_strip_found.setText('Yes')
                self.setup.label_led_strip_uid.setText(uid)
            elif device_identifier == MultiTouch.DEVICE_IDENTIFIER:
                config.UID_MULTI_TOUCH_BRICKLET = uid
                self.setup.label_multi_touch_found.setText('Yes')
                self.setup.label_multi_touch_uid.setText(uid)
            elif device_identifier == DualButton.DEVICE_IDENTIFIER:
                if config.UID_DUAL_BUTTON_BRICKLET[0] == None:
                    config.UID_DUAL_BUTTON_BRICKLET = (uid, None)
                    self.setup.label_dual_button1_found.setText('Yes')
                    self.setup.label_dual_button1_uid.setText(uid)
                else:
                    config.UID_DUAL_BUTTON_BRICKLET = (config.UID_DUAL_BUTTON_BRICKLET[0], uid)
                    self.setup.label_dual_button2_found.setText('Yes')
                    self.setup.label_dual_button2_uid.setText(uid)
            elif device_identifier == PiezoSpeaker.DEVICE_IDENTIFIER:
                config.UID_PIEZO_SPEAKER_BRICKLET = uid
                self.setup.label_piezo_speaker_found.setText('Yes')
                self.setup.label_piezo_speaker_uid.setText(uid)
            elif device_identifier == SegmentDisplay4x7.DEVICE_IDENTIFIER:
                config.UID_SEGMENT_DISPLAY_4X7_BRICKLET = uid
                self.setup.label_segment_display_found.setText('Yes')
                self.setup.label_segment_display_uid.setText(uid)

    def cb_connected(self, connected_reason):
        if connected_reason == IPConnection.CONNECT_REASON_AUTO_RECONNECT:
            while True:
                try:
                    self.ipcon.enumerate()
                    break
                except Error as e:
                    self.error_msg.showMessage('Enumerate Error: ' + str(e.description))
                    time.sleep(1)
예제 #29
0
class ProjectXively(QWidget):

    qtcb_update_illuminance = pyqtSignal(float)
    qtcb_update_air_pressure = pyqtSignal(float)
    qtcb_update_temperature = pyqtSignal(float)
    qtcb_update_humidity = pyqtSignal(float)
    qtcb_button_pressed = pyqtSignal(int)

    lcdwidget = None

    xively_host = "api.xively.com"
    xively_agent = "Tinkerforge Starter Kit Weather Station Demo"
    xively_channel = "Enter Feed ID here"
    xively_api_key = "Enter API Key here"

    xively_items = {}
    xively_headers = None
    xively_params = ""
    xively_update_rate = 5 # in minutes

    text_agent = None
    text_channel = None
    text_api_key = None
    number_update_rate = None

    save_button = None

    xively_timer = None

    error_message = None

    label_upload_active = None

    last_upload = None

    def __init__(self, parent, app):
        super(QWidget, self).__init__()

        self.lcdwidget = LCDWidget(self, app)
        self.lcdwidget.hide()

        self.text_agent = QLineEdit(self)
        self.text_agent.setText(self.xively_agent)
        
        self.text_channel = QLineEdit(self)
        self.text_channel.setText(self.xively_channel)
        
        self.text_api_key = QLineEdit(self)
        self.text_api_key.setText(self.xively_api_key)
        
        self.number_update_rate = QSpinBox(self)
        self.number_update_rate.setRange(1, 1440)
        self.number_update_rate.setSuffix(' min')
        self.number_update_rate.setValue(self.xively_update_rate)

        layout1 = QHBoxLayout()
        layout2 = QVBoxLayout()
        
        layout1.addStretch()
        layout1.addLayout(layout2)
        layout1.addStretch()
        
        layout2.addSpacerItem(QSpacerItem(LCDWidget.FIXED_WIDGTH, 0))

        label = QLabel(self)
        label.setText("Project: <b>Connect to Xively</b>. This project uploads the measured values to Xively. Please find documentation how to configure it and program sources in Python <a href=\"http://www.tinkerforge.com/en/doc/Kits/WeatherStation/WeatherStation.html#connect-to-xively\">here</a>.<br>")
        label.setTextFormat(Qt.RichText)
        label.setTextInteractionFlags(Qt.TextBrowserInteraction)
        label.setOpenExternalLinks(True)
        label.setWordWrap(True)
        label.setAlignment(Qt.AlignJustify)

        layout2.addSpacing(10)
        layout2.addWidget(label)
        layout2.addSpacing(10)

        layout3a = QHBoxLayout()
        label = QLabel("Agent Description:")
        label.setMinimumWidth(150)
        layout3a.addWidget(label)
        layout3a.addWidget(self.text_agent, 1)

        layout2.addLayout(layout3a)
        layout2.addSpacing(10)

        layout3b = QHBoxLayout()
        label = QLabel("Feed:")
        label.setMinimumWidth(150)
        layout3b.addWidget(label)
        layout3b.addWidget(self.text_channel, 1)

        layout2.addLayout(layout3b)
        layout2.addSpacing(10)

        layout3c = QHBoxLayout()
        label = QLabel("API Key:")
        label.setMinimumWidth(150)
        layout3c.addWidget(label)
        layout3c.addWidget(self.text_api_key, 1)

        layout2.addLayout(layout3c)
        layout2.addSpacing(10)

        layout3d = QHBoxLayout()
        label = QLabel("Update Rate:")
        label.setMinimumWidth(150)
        layout3d.addWidget(label)
        layout3d.addWidget(self.number_update_rate, 1)

        layout2.addLayout(layout3d)
        layout2.addSpacing(10)

        self.label_upload_active = QLabel("Not Active", self)
        self.label_upload_active.setMinimumWidth(150)
        font = QFont()
        font.setPixelSize(20)
        self.label_upload_active.setFont(font)
        self.set_active_label(False)

        self.save_button = QPushButton("Save/Activate")

        layout4 = QHBoxLayout()
        layout4.addWidget(self.label_upload_active)
        layout4.addWidget(self.save_button, 1)

        layout2.addLayout(layout4)
        layout2.addStretch()

        self.setLayout(layout1)

        self.qtcb_update_illuminance.connect(self.update_illuminance_data_slot)
        self.qtcb_update_air_pressure.connect(self.update_air_pressure_data_slot)
        self.qtcb_update_temperature.connect(self.update_temperature_data_slot)
        self.qtcb_update_humidity.connect(self.update_humidity_data_slot)
        self.qtcb_button_pressed.connect(self.button_pressed_slot)
        self.save_button.clicked.connect(self.save_configuration)

        self.lcdwidget.clear(self)

        self.error_message = QErrorMessage(self)

    def set_active_label(self, value):
        palette = self.label_upload_active.palette()
        if value:
            palette.setColor(self.foregroundRole(), Qt.darkGreen)
            self.label_upload_active.setText("Active")
        else:
            palette.setColor(self.foregroundRole(), Qt.red)
            self.label_upload_active.setText("Not Active")

        self.label_upload_active.setPalette(palette)

    def save_configuration(self):
        try:
            self.xively_agent = str(self.text_agent.text()).decode('ascii')
            self.xively_channel = str(self.text_channel.text()).decode('ascii')
            self.xively_api_key = str(self.text_api_key.text()).decode('ascii')
        except:
            self.error_message.showMessage('Agent, Feed and API Key can only contain ASCII characters')
            return

        self.xively_update_rate = self.number_update_rate.value()

        self.xively_headers = {
            "Content-Type"  : "application/x-www-form-urlencoded",
            "X-ApiKey"      : self.xively_api_key,
            "User-Agent"    : self.xively_agent,
        }
        self.xively_params = "/v2/feeds/" + self.xively_channel

        if self.xively_timer is None:
            self.xively_timer = QTimer(self)
            self.xively_timer.timeout.connect(self.update_xively)
            self.xively_timer.start(self.xively_update_rate*60*1000)

        self.set_active_label(True)
        self.update_xively()

    def write_lcd(self):
        if self.last_upload == None:
            tmp = "Last: Never"
        else:
            tmp = "Last: " + self.last_upload

        self.lcdwidget.write_line(0, 0, "Xively Upload", self)
        self.lcdwidget.write_line(2, 0, tmp, self)

    def update_xively(self):
        if len(self.xively_items) == 0:
            return

        stream_items = []
        for identifier, value in self.xively_items.items():
            stream_items.append({'id': identifier,
                                 'current_value': value[0],
                                 'min_value': value[1],
                                 'max_value': value[2]})

        data = {'version': '1.0.0',
                    'datastreams': stream_items}
        self.xively_items = {}
        body = json.dumps(data)

        try:
            http = httplib.HTTPSConnection(self.xively_host)
            http.request('PUT', self.xively_params, body, self.xively_headers)
            response = http.getresponse()
            http.close()

            if response.status != 200:
                self.error_message.showMessage('Could not upload to xively -> Response:' +
                          str(response.status) + ': ' + response.reason + '. Check your configuration.')
                self.xively_timer.stop()
                self.xively_timer = None
                self.set_active_label(False)
                return
        except Exception as e:
            self.error_message.showMessage('HTTP error: ' + str(e))
            self.xively_timer.stop()
            self.xively_timer = None
            self.set_active_label(False)
            return

        # set upload time if upload was a success
        self.last_upload = time.strftime("%H:%M:%S")


    def put(self, identifier, value):
        self.write_lcd()
        try:
            _, min_value, max_value = self.xively_items[identifier]
            if value < min_value:
                min_value = value
            if value > max_value:
                max_value = value
            self.xively_items[identifier] = (value, min_value, max_value)
        except:
            self.xively_items[identifier] = (value, value, value)

    def update_illuminance_data_slot(self, illuminance):
        self.put('AmbientLight', illuminance/10.0)

    def update_illuminance(self, illuminance):
        self.qtcb_update_illuminance.emit(illuminance)

    def update_humidity_data_slot(self, humidity):
        self.put('Humidity', humidity/10.0)
    
    def update_humidity(self, humidity):
        self.qtcb_update_humidity.emit(humidity)

    def update_air_pressure_data_slot(self, air_pressure):
        self.put('AirPressure', air_pressure/1000.0)
    
    def update_air_pressure(self, air_pressure):
        self.qtcb_update_air_pressure.emit(air_pressure)

    def update_temperature_data_slot(self, temperature):
        self.put('Temperature', temperature/100.0)

    def update_temperature(self, temperature):
        self.qtcb_update_temperature.emit(temperature)

    def button_pressed_slot(self, button):
        pass

    def button_pressed(self, button):
        self.qtcb_button_pressed.emit(button)
예제 #30
0
파일: dc.py 프로젝트: smunix/brickv
class DC(PluginBase, Ui_DC):
    qtcb_position_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)
    qtcb_emergency_shutdown = pyqtSignal()
    
    def __init__ (self, ipcon, uid):
        PluginBase.__init__(self, ipcon, uid)
     
        self.setupUi(self)
        
        self.dc = brick_dc.DC(self.uid)
        self.device = self.dc
        self.ipcon.add_device(self.dc)
        self.version = '.'.join(map(str, self.dc.get_version()[1]))
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)
        

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(4, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0
        
        self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
        self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
        self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
        
        self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
        self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
        self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
        
        self.frequency_slider.sliderReleased.connect(self.frequency_slider_released)
        self.frequency_slider.valueChanged.connect(self.frequency_spin.setValue)
        self.frequency_spin.editingFinished.connect(self.frequency_spin_finished)
        
        self.radio_mode_brake.toggled.connect(self.brake_value_changed)
        self.radio_mode_coast.toggled.connect(self.coast_value_changed)
        
        self.minimum_voltage_button.pressed.connect(self.minimum_voltage_button_pressed)
        self.full_brake_button.pressed.connect(self.full_brake_pressed)
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        
        self.emergency_signal = None
        self.under_signal = None
        self.current_velocity_signal = None
        self.velocity_reached_signal = None
        
        self.qem = QErrorMessage(self)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.dc.register_callback(self.dc.CALLBACK_UNDER_VOLTAGE,
                                  self.qtcb_under_voltage.emit) 
        
        self.qtcb_emergency_shutdown.connect(self.cb_emergency_shutdown)
        self.dc.register_callback(self.dc.CALLBACK_EMERGENCY_SHUTDOWN,
                                  self.qtcb_emergency_shutdown.emit) 
        
        self.qtcb_position_reached.connect(self.update_velocity)
        self.dc.register_callback(self.dc.CALLBACK_VELOCITY_REACHED,
                                  self.qtcb_position_reached.emit) 
        self.dc.register_callback(self.dc.CALLBACK_CURRENT_VELOCITY,
                                  self.qtcb_position_reached.emit) 
    
    def start(self):
        self.update_timer.start(1000)
        try:
            self.dc.set_current_velocity_period(100)
            self.update_start()
            self.update_data()
        except ip_connection.Error:
            return
        
    def stop(self):
        self.update_timer.stop()
        try:
            self.dc.set_current_velocity_period(0)
        except ip_connection.Error:
            return
        
    @staticmethod
    def has_name(name):
        return 'DC Brick' in name 
        
    def cb_emergency_shutdown(self):
        if not self.qem.isVisible():
            self.qem.setWindowTitle("Emergency Shutdown")
            self.qem.showMessage("Emergency Shutdown: Short-Circuit or Over-Temperature")
        
    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV"  % round(ov/1000.0, 1)
        if not self.qem.isVisible():
            self.qem.setWindowTitle("Under Voltage")
            self.qem.showMessage("Under Voltage: Output Voltage of " + ov_str +
                                 " is below minimum voltage of " + mv_str)
        
    def enable_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.dc.enable()
            elif state == Qt.Unchecked:
                self.dc.disable()
        except ip_connection.Error:
            return
            
    def brake_value_changed(self, checked):
        if checked:
            try:
                self.dc.set_drive_mode(0)
            except ip_connection.Error:
                return
        
    def coast_value_changed(self, checked):
        if checked:
            try:
                self.dc.set_drive_mode(1)
            except ip_connection.Error:
                return
        
    def full_brake_pressed(self):
        try:
            self.dc.full_brake()
        except ip_connection.Error:
            return
        
    def minimum_voltage_selected(self, value):
        try:
            self.dc.set_minimum_voltage(value)
        except ip_connection.Error:
            return
        
    def minimum_voltage_button_pressed(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(5000)
        qid.setIntMaximum(0xFFFF)
        qid.setIntStep(100)
        try:
            qid.setIntValue(self.dc.get_minimum_voltage())
        except ip_connection.Error:
            return
        qid.intValueSelected.connect(self.minimum_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()
        
    def stack_input_voltage_update(self, sv):
        sv_str = "%gV"  % round(sv/1000.0, 1)
        self.stack_voltage_label.setText(sv_str)
        
    def external_input_voltage_update(self, ev):
        ev_str = "%gV"  % round(ev/1000.0, 1)
        self.external_voltage_label.setText(ev_str)
        
    def minimum_voltage_update(self, mv):
        mv_str = "%gV"  % round(mv/1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)
        
    def drive_mode_update(self, dm):
        if dm == 0:
            self.radio_mode_brake.setChecked(True)
            self.radio_mode_coast.setChecked(False)
        else:
            self.radio_mode_brake.setChecked(False)
            self.radio_mode_coast.setChecked(True)
            
    def current_consumption_update(self, cc):
        if cc >= 1000:
            cc_str = "%gA"  % round(cc/1000.0, 1)
        else:
            cc_str = "%gmA" % cc
            
        self.current_label.setText(cc_str)

    
    def update_velocity(self, value):
        if value != self.speedometer.value():
            self.speedometer.set_velocity(value)
        
    def update_start(self):
        try:
            dm = self.dc.get_drive_mode()
            self.drive_mode_update(dm)
            
            if not self.velocity_slider.isSliderDown():
                velocity = self.dc.get_velocity()
                if velocity != self.velocity_slider.sliderPosition():
                    self.velocity_slider.setSliderPosition(velocity)
                    self.velocity_spin.setValue(velocity)
                 
            if not self.acceleration_slider.isSliderDown():
                acceleration = self.dc.get_acceleration()
                if acceleration != self.acceleration_slider.sliderPosition():
                    self.acceleration_slider.setSliderPosition(acceleration)
                    self.acceleration_spin.setValue(acceleration)
                    
            if not self.frequency_slider.isSliderDown():
                frequency = self.dc.get_pwm_frequency()
                if frequency != self.frequency_slider.sliderPosition():
                    self.frequency_slider.setSliderPosition(frequency)
                    self.frequency_spin.setValue(frequency)
    
            enabled = self.dc.is_enabled()
            if enabled:
                self.enable_checkbox.setCheckState(Qt.Checked)
            else:
                self.enable_checkbox.setCheckState(Qt.Unchecked)
        except ip_connection.Error:
            return
        
    def update_data(self):
        try:
            sv = self.dc.get_stack_input_voltage()
            ev = self.dc.get_external_input_voltage()
            mv = self.dc.get_minimum_voltage()
            cc = self.dc.get_current_consumption()
        except ip_connection.Error:
            return
        
        self.stack_input_voltage_update(sv)
        self.external_input_voltage_update(ev)
        self.minimum_voltage_update(mv)
        self.current_consumption_update(cc)
        
    def acceleration_slider_released(self):
        value = self.acceleration_slider.value()
        self.acceleration_spin.setValue(value)
        try:
            self.dc.set_acceleration(value)
        except ip_connection.Error:
            return
        
    def acceleration_spin_finished(self):
        value = self.acceleration_spin.value()
        self.acceleration_slider.setValue(value)
        try:
            self.dc.set_acceleration(value)
        except ip_connection.Error:
            return
        
    def velocity_slider_released(self):
        value = self.velocity_slider.value()
        self.velocity_spin.setValue(value)
        try:
            self.dc.set_velocity(value)
        except ip_connection.Error:
            return
        
    def velocity_spin_finished(self):
        value = self.velocity_spin.value()
        self.velocity_slider.setValue(value)
        try:
            self.dc.set_velocity(value)
        except ip_connection.Error:
            return
        
    def frequency_slider_released(self):
        value = self.frequency_slider.value()
        self.frequency_spin.setValue(value)
        try:
            self.dc.set_pwm_frequency(value)
        except ip_connection.Error:
            return
        
    def frequency_spin_finished(self):
        value = self.frequency_spin.value()
        self.frequency_slider.setValue(value)
        try:
            self.dc.set_pwm_frequency(value)
        except ip_connection.Error:
            return
예제 #31
0
파일: editor.py 프로젝트: pprofpc/pilas
class Editor(editor_base.EditorBase):
    """Representa el editor de texto que aparece en el panel derecho.

    El editor soporta autocompletado de código y resaltado de sintáxis.
    """

    # Señal es emitida cuando el Editor ejecuta codigo
    signal_ejecutando = QtCore.pyqtSignal()

    def __init__(self, main, interpreterLocals, consola_lanas, ventana_interprete):
        super(Editor, self).__init__()
        self.cantidad_ejecuciones = 0
        self.consola_lanas = consola_lanas
        self.ventana_interprete = ventana_interprete
        self.ruta_del_archivo_actual = None
        self.interpreterLocals = interpreterLocals
        self.setLineWrapMode(QTextEdit.NoWrap)
        self._cambios_sin_guardar = False
        self.main = main
        self.nombre_de_archivo_sugerido = ""
        self.watcher = pilasengine.watcher.Watcher(None, self.cuando_cambia_archivo_de_forma_externa)

    def crear_archivo_inicial(self):
        dirpath = tempfile.mkdtemp()
        archivo_temporal = os.path.join(dirpath, "mi_juego.py")
        archivo = codecs.open(archivo_temporal, "w", 'utf-8')
        archivo.write(CODIGO_INICIAL)
        archivo.close()
        #print("Creando el archivo " + str(archivo_temporal))
        self.abrir_archivo_del_proyecto(archivo_temporal)

    def es_archivo_iniciar_sin_guardar(self):
        return self.nombre_de_archivo_sugerido == ""

    def crear_y_seleccionar_archivo(self, nombre):
        # Quita la extension si llega a tenerla.
        nombre = nombre.replace('.py', '')
        nombre += ".py"
        nombre_de_archivo = nombre

        if self.ruta_del_archivo_actual:
            base_path = os.path.abspath(os.path.dirname(self.ruta_del_archivo_actual))
            ruta = os.path.join(base_path, unicode(nombre_de_archivo))
        else:
            ruta = unicode(nombre_de_archivo)

        if os.path.exists(ruta):
            self._tmp_dialog = QErrorMessage(self)
            self._tmp_dialog.showMessage("Ya existe un archivo con ese nombre")
        else:
            self._crear_archivo_nuevo_en(ruta)

            self.cargar_contenido_desde_archivo(ruta)
            self.ruta_del_archivo_actual = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()

    def _crear_archivo_nuevo_en(self, ruta):
        fo = open(ruta, "wb")
        fo.write("# contenido")
        fo.close()

    def obtener_archivos_del_proyecto(self):
        base_path = os.path.dirname(self.nombre_de_archivo_sugerido)
        listado = os.listdir(base_path)

        return [x for x in listado if x.endswith('.py')]

    def keyPressEvent(self, event):
        "Atiene el evento de pulsación de tecla."
        self._cambios_sin_guardar = True

        # Permite usar tab como seleccionador de la palabra actual
        # en el popup de autocompletado.
        if event.key() in [Qt.Key_Tab]:
            if self.completer and self.completer.popup().isVisible():
                event.ignore()
                nuevo_evento = QKeyEvent(QKeyEvent.KeyPress, Qt.Key_Return, Qt.NoModifier)
                try:
                    if self.autocomplete(nuevo_evento):
                        return None
                except UnicodeEncodeError:
                    pass
                return None


        if editor_base.EditorBase.keyPressEvent(self, event):
            return None

        # Elimina los pares de caracteres especiales si los encuentra
        if event.key() == Qt.Key_Backspace:
            self._eliminar_pares_de_caracteres()
            self._borrar_un_grupo_de_espacios(event)

        if self.autocomplete(event):
            return None


        if event.key() == Qt.Key_Return:
            cursor = self.textCursor()
            block = self.document().findBlockByNumber(cursor.blockNumber())
            whitespace = re.match(r"(\s*)", unicode(block.text())).group(1)

            linea_anterior = str(block.text()[:])
            cantidad_espacios = linea_anterior.count(' ') / 4

            if linea_anterior[-1:] == ':':
                whitespace = '    ' * (cantidad_espacios + 1)
            else:
                whitespace = '    ' * (cantidad_espacios)

            QTextEdit.keyPressEvent(self, event)
            return self.insertPlainText(whitespace)



        return QTextEdit.keyPressEvent(self, event)

    def _borrar_un_grupo_de_espacios(self, event):
        cursor = self.textCursor()
        block = self.document().findBlockByNumber(cursor.blockNumber())
        whitespace = re.match(r"(.*)", unicode(block.text())).group(1)

        if whitespace.endswith('    '):
            QTextEdit.keyPressEvent(self, event)
            QTextEdit.keyPressEvent(self, event)
            QTextEdit.keyPressEvent(self, event)

    def tiene_cambios_sin_guardar(self):
        return self._cambios_sin_guardar

    def _get_current_line(self):
        "Obtiene la linea en donde se encuentra el cursor."
        tc = self.textCursor()
        tc.select(QTextCursor.LineUnderCursor)
        return tc.selectedText()

    def _get_position_in_block(self):
        tc = self.textCursor()
        position = tc.positionInBlock() - 1
        return position

    def cargar_contenido_desde_archivo(self, ruta):
        "Carga todo el contenido del archivo indicado por ruta."
        with codecs.open(unicode(ruta), 'r', 'utf-8') as archivo:
            contenido = archivo.read()
        self.setText(contenido)

        self.nombre_de_archivo_sugerido = ruta
        self._cambios_sin_guardar = False

    def abrir_dialogo_cargar_archivo(self):
        return QFileDialog.getOpenFileName(self, "Abrir Archivo",
                                   self.nombre_de_archivo_sugerido,
                                   "Archivos python (*.py)",
                                   options=QFileDialog.DontUseNativeDialog)

    def abrir_archivo_del_proyecto(self, nombre_de_archivo):
        if self.tiene_cambios_sin_guardar():
            if self.mensaje_guardar_cambios_abrir():
                if not self.guardar_contenido_con_dialogo():
                    return
            else:
                return

        if self.ruta_del_archivo_actual:
            base_path = os.path.dirname(self.ruta_del_archivo_actual)
            ruta = os.path.join(base_path, unicode(nombre_de_archivo))
        else:
            ruta = unicode(nombre_de_archivo)

        self.cargar_contenido_desde_archivo(ruta)
        self.ruta_del_archivo_actual = ruta
        self.watcher.cambiar_archivo_a_observar(ruta)
        self.ejecutar()
        self.main.actualizar_el_listado_de_archivos()

    def abrir_archivo_con_dialogo(self):
        if self.tiene_cambios_sin_guardar():
            if self.mensaje_guardar_cambios_abrir():
                if not self.guardar_contenido_con_dialogo():
                    return
            else:
                return

        ruta = self.abrir_dialogo_cargar_archivo()

        if ruta:
            ruta = unicode(ruta)
            self.cargar_contenido_desde_archivo(ruta)
            self.ruta_del_archivo_actual = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()

    def cuando_cambia_archivo_de_forma_externa(self):
        self.recargar_archivo_actual()

    def recargar_archivo_actual(self):
        if self.ruta_del_archivo_actual:
            self.cargar_contenido_desde_archivo(self.ruta_del_archivo_actual)
            self.ejecutar()

    def mensaje_guardar_cambios_abrir(self):
        """Realizar una consulta usando un cuadro de dialogo simple
        se utiliza cuando hay cambios sin guardar y se desea abrir un archivo.
        Retorna True si el usuario presiona el boton *Guardar*,
        Retorna False si el usuario presiona *No*."""
        titulo = u"¿Deseas guardar el contenido antes de abrir un archivo?"
        mensaje = u"El contenido se perdera sino los guardas"

        mensaje = QMessageBox.question(self, titulo, mensaje, "Guardar", "No")

        return (not mensaje)

    def mensaje_guardar_cambios_salir(self):
        """Realizar una consulta usando un cuadro de dialogo simple
        se utiliza cuando hay cambios sin guardar y se desa salir del Editor.
        Retorna 0 si el usuario presiona el boton *Salir sin guardar*,
        Retorna 1 si el usuario presiona *Guardar*
        Retorna 2 si presiona *Cancelar*."""

        titulo = u"¿Deseas guardar el contenido antes de salir?"
        mensaje = u"El contenido se perdera sino los guardas"

        return QMessageBox.question(self, titulo, mensaje,
                                    "Salir sin guardar", "Guardar", "Cancelar")

    def marcar_error_en_la_linea(self, numero, descripcion):
        hi_selection = QTextEdit.ExtraSelection()

        hi_selection.format.setBackground(QColor(255, 220, 220))
        hi_selection.format.setProperty(QTextFormat.FullWidthSelection, QVariant(True))
        hi_selection.cursor = self.textCursor()
        posicion_linea = self.document().findBlockByLineNumber(numero).position()
        hi_selection.cursor.setPosition(posicion_linea)
        hi_selection.cursor.clearSelection()

        self.setExtraSelections([hi_selection])

    def guardar_contenido_con_dialogo(self):
        ruta = self.abrir_dialogo_guardar_archivo()

        if not ruta:
            return False

        ruta = unicode(ruta)

        if not ruta.endswith('.py'):
            ruta += '.py'

        if ruta:
            self.guardar_contenido_en_el_archivo(ruta)
            self._cambios_sin_guardar = False
            self.ruta_del_archivo_actual = ruta
            self.nombre_de_archivo_sugerido = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.cargar_contenido_desde_archivo(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()
            self.main.habilitar_boton_nuevo()
            return True

    def guardar_contenido_directamente(self):
        if self.nombre_de_archivo_sugerido:
            self.guardar_contenido_en_el_archivo(self.nombre_de_archivo_sugerido)
            self._cambios_sin_guardar = False
            self.main.actualizar_el_listado_de_archivos()
            self.prevenir_live_reload()
        else:
            self.guardar_contenido_con_dialogo()

    def prevenir_live_reload(self):
        self.watcher.prevenir_reinicio()

    def salir(self):
        """Retorna True si puede salir y False si no"""
        if self.tiene_cambios_sin_guardar():
            mensaje = self.mensaje_guardar_cambios_salir()
            if mensaje == 1:
                self.guardar_contenido_con_dialogo()
            elif mensaje == 2:
                return False

        return True

    def obtener_contenido(self):
        return unicode(self.document().toPlainText())

    def ejecutar(self):
        ruta_personalizada = os.path.dirname(self.ruta_del_archivo_actual)
        #print "ejecutando texto desde widget editor"
        texto = self.obtener_contenido()
        #texto = self.editor.obtener_texto_sanitizado(self)
        # elimina cabecera de encoding.
        contenido = re.sub('coding\s*:\s*', '', texto)
        contenido = contenido.replace('import pilasengine', '')
        contenido = contenido.replace('pilas = pilasengine.iniciar', 'pilas.reiniciar')

        for x in contenido.split('\n'):
            if "__file__" in x:
                contenido = contenido.replace(x, "# livecoding: " + x + "\n")

        sys.path.append(ruta_personalizada)
        self.interpreterLocals['sys'] = sys

        # Muchos códigos personalizados necesitan cargar imágenes o sonidos
        # desde el directorio que contiene al archivo. Para hacer esto posible,
        # se llama a la función "pilas.utils.agregar_ruta_personalizada" con el
        # path al directorio que representa el script. Así la función "obtener_ruta_al_recurso"
        # puede evaluar al directorio del script en busca de recursos también.
        if ruta_personalizada:
            ruta_personalizada = ruta_personalizada.replace('\\', '/')
            agregar_ruta_personalizada = 'pilas.utils.agregar_ruta_personalizada("%s")' %(ruta_personalizada)
            contenido = contenido.replace('pilas.reiniciar(', agregar_ruta_personalizada+'\n'+'pilas.reiniciar(')

        modulos_a_recargar = [x for x in self.interpreterLocals.values()
                                    if inspect.ismodule(x)
                                    and x.__name__ not in ['pilasengine', 'inspect']
                                    and 'pilasengine.' not in x.__name__]

        for m in modulos_a_recargar:
            reload(m)

        self.cantidad_ejecuciones += 1

        # Limpia la consola a partir de la primer ejecucion luego de iniciar.
        if self.cantidad_ejecuciones > 1:
            self.main.limpiar_interprete()

        try:
            exec(contenido, self.interpreterLocals)
        except Exception, e:
            self.consola_lanas.insertar_error_desde_exception(e)
            self.ventana_interprete.mostrar_el_interprete()
            #self.marcar_error_en_la_linea(10, "pepepe")

        self.signal_ejecutando.emit()
예제 #32
0
class Stepper(PluginBase, Ui_Stepper):
    qtcb_position_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)

    def __init__(self, *args):
        PluginBase.__init__(self, BrickStepper, *args)

        self.setupUi(self)

        self.stepper = self.device

        self.endis_all(False)

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.new_value = 0
        self.update_counter = 0

        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.decay_widget.hide()

        self.setting_sync_rect_checkbox = False

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.deceleration_syncer = SliderSpinSyncer(self.deceleration_slider,
                                                    self.deceleration_spin,
                                                    self.deceleration_changed)

        self.decay_syncer = SliderSpinSyncer(self.decay_slider,
                                             self.decay_spin,
                                             self.decay_changed)

        self.enable_checkbox.toggled.connect(self.enable_toggled)
        self.forward_button.clicked.connect(self.forward_clicked)
        self.stop_button.clicked.connect(self.stop_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.backward_button.clicked.connect(self.backward_clicked)
        self.to_button.clicked.connect(self.to_button_clicked)
        self.steps_button.clicked.connect(self.steps_button_clicked)
        self.motor_current_button.clicked.connect(
            self.motor_current_button_clicked)
        self.minimum_motor_voltage_button.clicked.connect(
            self.minimum_motor_voltage_button_clicked)
        self.sync_rect_checkbox.toggled.connect(self.sync_rect_toggled)

        self.mode_dropbox.currentIndexChanged.connect(self.mode_changed)

        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.stepper.register_callback(self.stepper.CALLBACK_POSITION_REACHED,
                                       self.qtcb_position_reached.emit)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.stepper.register_callback(self.stepper.CALLBACK_UNDER_VOLTAGE,
                                       self.qtcb_under_voltage.emit)

        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv = 0
        self.ev = 0
        self.mv = 0
        self.mod = 0

        if self.firmware_version >= (2, 3, 1):
            self.status_led_action = QAction('Status LED', self)
            self.status_led_action.setCheckable(True)
            self.status_led_action.toggled.connect(
                lambda checked: self.stepper.enable_status_led()
                if checked else self.stepper.disable_status_led())
            self.set_configs([(0, None, [self.status_led_action])])
        else:
            self.status_led_action = None

        if self.firmware_version >= (1, 1, 4):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.stepper.reset())
            self.set_actions([(0, None, [reset])])

    def start(self):
        if self.firmware_version >= (2, 3, 1):
            async_call(self.stepper.is_status_led_enabled, None,
                       self.status_led_action.setChecked,
                       self.increase_error_count)

        self.update_timer.start(100)
        self.update_start()

    def stop(self):
        self.update_timer.stop()

    def destroy(self):
        pass

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickStepper.DEVICE_IDENTIFIER

    def cb_position_reached(self, position):
        self.position_update(position)
        self.endis_all(True)

    def disable_list(self, button_list):
        for button in button_list:
            button.setEnabled(False)

    def endis_all(self, value):
        self.forward_button.setEnabled(value)
        self.stop_button.setEnabled(value)
        self.backward_button.setEnabled(value)
        self.to_button.setEnabled(value)
        self.steps_button.setEnabled(value)
        self.full_brake_button.setEnabled(value)

    def mode_changed(self, index):
        try:
            self.stepper.set_step_mode(1 << index)
            self.mod = 1 << index
        except ip_connection.Error:
            return

    def forward_clicked(self):
        try:
            self.stepper.drive_forward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])

    def backward_clicked(self):
        try:
            self.stepper.drive_backward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])

    def stop_clicked(self):
        try:
            self.stepper.stop()
        except ip_connection.Error:
            return
        self.endis_all(True)

    def full_brake_clicked(self):
        try:
            self.stepper.full_brake()
        except ip_connection.Error:
            return
        self.endis_all(True)

    def to_button_clicked(self):
        drive_to = self.to_spin.value()
        try:
            self.stepper.set_target_position(drive_to)
        except ip_connection.Error:
            return
        self.disable_list([
            self.to_button, self.steps_button, self.forward_button,
            self.backward_button
        ])

    def steps_button_clicked(self):
        drive_steps = self.steps_spin.value()
        try:
            self.stepper.set_steps(drive_steps)
        except ip_connection.Error:
            return
        self.disable_list([
            self.to_button, self.steps_button, self.forward_button,
            self.backward_button
        ])

    def motor_current_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(2500)
        qid.setIntStep(100)
        async_call(self.stepper.get_motor_current, None, qid.setIntValue,
                   self.increase_error_count)
        qid.intValueSelected.connect(self.motor_current_selected)
        qid.setLabelText("Choose motor current in mA.")
        #                         "<font color=red>Setting this too high can destroy your Motor.</font>")
        qid.open()

    def minimum_motor_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(40000)
        qid.setIntStep(100)
        async_call(self.stepper.get_minimum_voltage, None, qid.setIntValue,
                   self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_motor_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()

    def motor_current_selected(self, value):
        try:
            self.stepper.set_motor_current(value)
        except ip_connection.Error:
            return

    def minimum_motor_voltage_selected(self, value):
        try:
            self.stepper.set_minimum_voltage(value)
        except ip_connection.Error:
            return

    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV" % round(ov / 1000.0, 1)
        if not self.qem.isVisible():
            self.qem.showMessage(
                "Under Voltage: Output Voltage of " + ov_str +
                " is below minimum voltage of " + mv_str,
                "Stepper_UnderVoltage")

    def enable_toggled(self, checked):
        try:
            if checked:
                if not self.stepper.is_enabled():
                    self.endis_all(True)
                    self.stepper.enable()
            else:
                if self.stepper.is_enabled():
                    self.endis_all(False)
                    self.stepper.disable()
        except ip_connection.Error:
            return

    def sync_rect_toggled(self, checked):
        if not self.setting_sync_rect_checkbox and checked:
            rc = QMessageBox.warning(
                get_main_window(), 'Synchronous Rectification',
                'If you want to use high speeds (> 10000 steps/s) for a large stepper motor with a '
                +
                'large inductivity we strongly suggest that you do not enable synchronous rectification. '
                +
                'Otherwise the Brick may not be able to cope with the load and overheat.',
                QMessageBox.Ok | QMessageBox.Cancel)

            if rc != QMessageBox.Ok:
                self.sync_rect_checkbox.setChecked(False)
                return

        try:
            self.stepper.set_sync_rect(checked)
        except ip_connection.Error:
            return

        self.decay_widget.setVisible(checked)

    def stack_input_voltage_update(self, sv):
        sv_str = "%gV" % round(sv / 1000.0, 1)
        self.stack_voltage_label.setText(sv_str)

    def external_input_voltage_update(self, ev):
        ev_str = "%gV" % round(ev / 1000.0, 1)
        self.external_voltage_label.setText(ev_str)

    def minimum_voltage_update(self, mv):
        mv_str = "%gV" % round(mv / 1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)

    def maximum_current_update(self, cur):
        cur_str = "%gA" % round(cur / 1000.0, 1)
        self.maximum_current_label.setText(cur_str)

    def position_update(self, pos):
        pos_str = "%d" % pos
        self.position_label.setText(pos_str)

    def remaining_steps_update(self, ste):
        ste_str = "%d" % ste
        self.remaining_steps_label.setText(ste_str)

    def current_velocity_update(self, velocity):
        velocity_str = "%d" % velocity
        self.current_velocity_label.setText(velocity_str)
        self.speedometer.set_velocity(velocity)

    def mode_update(self, mod):
        if mod == 8:
            index = 3
        elif mod == 4:
            index = 2
        elif mod == 2:
            index = 1
        else:
            index = 0

        self.mode_dropbox.setCurrentIndex(index)

    def get_max_velocity_async(self, velocity):
        if not self.velocity_slider.isSliderDown():
            if velocity != self.velocity_slider.sliderPosition():
                self.velocity_slider.setSliderPosition(velocity)
                self.velocity_spin.setValue(velocity)

    def get_speed_ramping_async(self, ramp):
        acc, dec = ramp
        if not self.acceleration_slider.isSliderDown() and \
           not self.deceleration_slider.isSliderDown():
            if acc != self.acceleration_slider.sliderPosition():
                self.acceleration_slider.setSliderPosition(acc)
                self.acceleration_spin.setValue(acc)
            if dec != self.deceleration_slider.sliderPosition():
                self.deceleration_slider.setSliderPosition(dec)
                self.deceleration_spin.setValue(dec)

    def get_decay_async(self, decay):
        if not self.decay_slider.isSliderDown():
            if decay != self.decay_slider.sliderPosition():
                self.decay_slider.setSliderPosition(decay)
                self.decay_spin.setValue(decay)

    def is_enabled_async(self, enabled):
        if enabled:
            if not self.enable_checkbox.isChecked():
                self.endis_all(True)
                self.enable_checkbox.setChecked(True)
        else:
            if self.enable_checkbox.isChecked():
                self.endis_all(False)
                self.enable_checkbox.setChecked(False)

    def is_sync_rect_async(self, sync_rect):
        self.setting_sync_rect_checkbox = True
        self.sync_rect_checkbox.setChecked(sync_rect)
        self.setting_sync_rect_checkbox = False

    def update_start(self):
        async_call(self.stepper.get_max_velocity, None,
                   self.get_max_velocity_async, self.increase_error_count)
        async_call(self.stepper.get_speed_ramping, None,
                   self.get_speed_ramping_async, self.increase_error_count)
        async_call(self.stepper.get_decay, None, self.get_decay_async,
                   self.increase_error_count)
        async_call(self.stepper.is_enabled, None, self.is_enabled_async,
                   self.increase_error_count)
        async_call(self.stepper.is_sync_rect, None, self.is_sync_rect_async,
                   self.increase_error_count)

    def update_data(self):
        async_call(self.stepper.get_remaining_steps, None,
                   self.remaining_steps_update, self.increase_error_count)
        async_call(self.stepper.get_current_position, None,
                   self.position_update, self.increase_error_count)
        async_call(self.stepper.get_current_velocity, None,
                   self.current_velocity_update, self.increase_error_count)

        self.update_counter += 1
        if self.update_counter % 10 == 0:
            async_call(self.stepper.get_motor_current, None,
                       self.maximum_current_update, self.increase_error_count)
            async_call(self.stepper.get_stack_input_voltage, None,
                       self.stack_input_voltage_update,
                       self.increase_error_count)
            async_call(self.stepper.get_external_input_voltage, None,
                       self.external_input_voltage_update,
                       self.increase_error_count)
            async_call(self.stepper.get_minimum_voltage, None,
                       self.minimum_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_step_mode, None, self.mode_update,
                       self.increase_error_count)

    def velocity_changed(self, value):
        try:
            self.stepper.set_max_velocity(value)
        except ip_connection.Error:
            return

    def acceleration_changed(self, value):
        dec = self.deceleration_spin.value()
        try:
            self.stepper.set_speed_ramping(value, dec)
        except ip_connection.Error:
            return

    def deceleration_changed(self, value):
        acc = self.acceleration_slider.value()
        try:
            self.stepper.set_speed_ramping(acc, value)
        except ip_connection.Error:
            return

    def decay_changed(self, value):
        try:
            self.stepper.set_decay(value)
        except ip_connection.Error:
            return
예제 #33
0
    def __init__(self, *args):
        PluginBase.__init__(self, BrickServo, *args)

        self.setupUi(self)

        self.servo = self.device

        self.position_list = []
        self.velocity_list = []
        self.acceleration_list = []
        self.enable_list = []

        self.up_cur = 0
        self.up_siv = 0
        self.up_eiv = 0
        self.up_opv = 0
        self.up_mv = 0

        self.up_ena = [0] * 7
        self.up_pos = [0] * 7
        self.up_vel = [0] * 7
        self.up_acc = [0] * 7

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_apply)
        self.update_timer.setInterval(50)

        self.alive = True

        for i in range(1, 8):
            label = QLabel()
            label.setText('Off')
            self.enable_list.append(label)
            self.status_grid.addWidget(label, i, 1)

        for i in range(1, 8):
            pk = PositionKnob()
            self.position_list.append(pk)
            self.status_grid.addWidget(pk, i, 2)

        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.velocity_list.append(cb)
            self.status_grid.addWidget(cb, i, 3)

        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.acceleration_list.append(cb)
            self.status_grid.addWidget(cb, i, 4)

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.test_button.clicked.connect(self.test_button_clicked)
        self.output_voltage_button.clicked.connect(
            self.output_voltage_button_clicked)

        self.servo_dropbox.currentIndexChanged.connect(
            lambda x: self.update_servo_specific())
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)

        self.position_syncer = SliderSpinSyncer(self.position_slider,
                                                self.position_spin,
                                                self.position_changed)

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.period_syncer = SliderSpinSyncer(self.period_slider,
                                              self.period_spin,
                                              self.period_changed)

        self.pulse_width_min_spin.editingFinished.connect(
            self.pulse_width_spin_finished)
        self.pulse_width_max_spin.editingFinished.connect(
            self.pulse_width_spin_finished)
        self.degree_min_spin.editingFinished.connect(self.degree_spin_finished)
        self.degree_max_spin.editingFinished.connect(self.degree_spin_finished)

        self.minimum_voltage_button.clicked.connect(
            self.minimum_voltage_button_clicked)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.servo.register_callback(self.servo.CALLBACK_UNDER_VOLTAGE,
                                     self.qtcb_under_voltage.emit)

        class WorkerThread(QThread):
            def __init__(self, parent=None, func=None):
                QThread.__init__(self, parent)
                self.func = func

            def run(self):
                self.func()

        self.test_event = Event()
        self.test_thread_object = WorkerThread(self, self.test_thread)
        self.update_event = Event()
        self.update_thread_object = WorkerThread(self, self.update_thread)

        self.update_thread_first_time = False

        self.update_done_event = Event()
        self.update_done_event.set()

        if self.firmware_version >= (2, 3, 1):
            self.status_led_action = QAction('Status LED', self)
            self.status_led_action.setCheckable(True)
            self.status_led_action.toggled.connect(
                lambda checked: self.servo.enable_status_led()
                if checked else self.servo.disable_status_led())
            self.set_configs([(0, None, [self.status_led_action])])
        else:
            self.status_led_action = None

        if self.firmware_version >= (1, 1, 3):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.servo.reset())
            self.set_actions([(0, None, [reset])])
예제 #34
0
파일: gui.py 프로젝트: junzis/bluesky
    def __init__(self, navdb):
        super(Gui, self).__init__([])
        self.acdata          = ACDataEvent()
        self.navdb           = navdb
        self.radarwidget     = []
        self.command_history = []
        self.cmdargs         = []
        self.history_pos     = 0
        self.command_mem     = ''
        self.command_line    = ''
        self.prev_cmdline    = ''
        self.simevent_target = 0
        self.mousepos        = (0, 0)
        self.prevmousepos    = (0, 0)
        self.panzoomchanged  = False

        # Register our custom pan/zoom event
        for etype in [PanZoomEventType, ACDataEventType, SimInfoEventType,
                      StackTextEventType, ShowDialogEventType,
                      DisplayFlagEventType, RouteDataEventType,
                      DisplayShapeEventType]:
            reg_etype = QEvent.registerEventType(etype)
            if reg_etype != etype:
                print('Warning: Registered event type differs from requested type id (%d != %d)' % (reg_etype, etype))

        self.splash = Splash()
        self.splash.show()

        self.splash.showMessage('Constructing main window')
        self.processEvents()

        # Install error message handler
        handler = QErrorMessage.qtHandler()
        handler.setWindowFlags(Qt.WindowStaysOnTopHint)

        # Check and set OpenGL capabilities
        if not QGLFormat.hasOpenGL():
            raise RuntimeError('No OpenGL support detected for this system!')
        else:
            f = QGLFormat()
            f.setVersion(3, 3)
            f.setProfile(QGLFormat.CoreProfile)
            f.setDoubleBuffer(True)
            QGLFormat.setDefaultFormat(f)
            print('QGLWidget initialized for OpenGL version %d.%d' % (f.majorVersion(), f.minorVersion()))

        # Create the main window and related widgets
        self.radarwidget = RadarWidget(navdb)
        self.win = MainWindow(self, self.radarwidget)
        self.nd  = ND(shareWidget=self.radarwidget)

        # Enable HiDPI support (Qt5 only)
        if QT_VERSION == 5:
            self.setAttribute(Qt.AA_UseHighDpiPixmaps)

        timer = QTimer(self)
        timer.timeout.connect(self.radarwidget.updateGL)
        timer.timeout.connect(self.nd.updateGL)
        timer.start(50)

        # Load geo data
        if False:
            pb = QProgressDialog('Binary buffer file not found, or file out of date: Constructing vertex buffers from geo data.', 'Cancel', 0, 100)
            pb.setWindowFlags(Qt.WindowStaysOnTopHint)
            pb.show()
            for i in range(101):
                pb.setValue(i)
                self.processEvents()
                QThread.msleep(100)
            pb.close()
예제 #35
0
class Stepper(PluginBase, Ui_Stepper):
    qtcb_position_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)
    
    def __init__(self, ipcon, uid, version):
        PluginBase.__init__(self, ipcon, uid, 'Stepper Brick', version)
        
        self.setupUi(self)
     
        self.stepper = BrickStepper(uid, ipcon)
        self.device = self.stepper
     
        self.endis_all(False)
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(5, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")
        
        self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
        self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
        self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
        
        self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
        self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
        self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
        
        self.deceleration_slider.sliderReleased.connect(self.deceleration_slider_released)
        self.deceleration_slider.valueChanged.connect(self.deceleration_spin.setValue)
        self.deceleration_spin.editingFinished.connect(self.deceleration_spin_finished)
        
#        self.decay_slider.sliderReleased.connect(self.decay_slider_released)
#        self.decay_slider.valueChanged.connect(self.decay_spin.setValue)
#        self.decay_spin.editingFinished.connect(self.decay_spin_finished)
        
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        self.forward_button.pressed.connect(self.forward_pressed)
        self.stop_button.pressed.connect(self.stop_pressed)
        self.full_brake_button.pressed.connect(self.full_brake_pressed)
        self.backward_button.pressed.connect(self.backward_pressed)
        self.to_button.pressed.connect(self.to_button_pressed)
        self.steps_button.pressed.connect(self.steps_button_pressed)
        self.motor_current_button.pressed.connect(self.motor_current_button_pressed)
        self.minimum_motor_voltage_button.pressed.connect(self.minimum_motor_voltage_button_pressed)
        
        self.mode_dropbox.currentIndexChanged.connect(self.mode_changed)
        
        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.stepper.register_callback(self.stepper.CALLBACK_POSITION_REACHED, 
                                       self.qtcb_position_reached.emit)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.stepper.register_callback(self.stepper.CALLBACK_UNDER_VOLTAGE, 
                                       self.qtcb_under_voltage.emit)
        
        self.update_data_async_thread = None
        
        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv  = 0
        self.ev  = 0
        self.mv  = 0
        self.mod = 0
        
    def start(self):
        self.update_timer.start(100)
        self.update_start()
        
    def stop(self):
        self.update_timer.stop()

    def has_reset_device(self):
        return self.version >= (1, 1, 4)

    def reset_device(self):
        if self.has_reset_device():
            self.stepper.reset()

    def is_brick(self):
        return True

    def get_url_part(self):
        return 'stepper'

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickStepper.DEVICE_IDENTIFIER
    
    def cb_position_reached(self, position):
        self.position_update(position)
        self.endis_all(True)
            
    def disable_list(self, button_list):
        for button in button_list:
            button.setEnabled(False)
        
    def endis_all(self, value):
        self.forward_button.setEnabled(value)
        self.stop_button.setEnabled(value)
        self.backward_button.setEnabled(value)
        self.to_button.setEnabled(value)
        self.steps_button.setEnabled(value)
        self.full_brake_button.setEnabled(value)
        
    def mode_changed(self, index):
        try:
            self.stepper.set_step_mode(1 << index)
            self.mod = 1 << index
        except ip_connection.Error:
            return
        
    def forward_pressed(self):
        try:
            self.stepper.drive_forward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])
        
    def backward_pressed(self):
        try:
            self.stepper.drive_backward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])
        
    def stop_pressed(self):
        try:
            self.stepper.stop()
        except ip_connection.Error:
            return
        self.endis_all(True)
        
    def full_brake_pressed(self):
        try:
            self.stepper.full_brake()
        except ip_connection.Error:
            return
        self.endis_all(True)
        
    def to_button_pressed(self):
        drive_to = self.to_spin.value()
        try:
            self.stepper.set_target_position(drive_to)
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, 
                           self.steps_button, 
                           self.forward_button,
                           self.backward_button])
        
    def steps_button_pressed(self):
        drive_steps = self.steps_spin.value()
        try:
            self.stepper.set_steps(drive_steps)
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, 
                           self.steps_button, 
                           self.forward_button,
                           self.backward_button])
        
    def motor_current_button_pressed(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(2500)
        qid.setIntStep(100)
        async_call(self.stepper.get_motor_current, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.motor_current_selected)
        qid.setLabelText("Choose motor current in mA.")
#                         "<font color=red>Setting this too high can destroy your Motor.</font>")
        qid.open()
        
    def minimum_motor_voltage_button_pressed(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(40000)
        qid.setIntStep(100)
        async_call(self.stepper.get_minimum_voltage, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_motor_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()
        
    def motor_current_selected(self, value):
        try:
            self.stepper.set_motor_current(value)
        except ip_connection.Error:
            return
        
    def minimum_motor_voltage_selected(self, value):
        try:
            self.stepper.set_minimum_voltage(value)
        except ip_connection.Error:
            return
        
    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV"  % round(ov/1000.0, 1)
        if not self.qem.isVisible():
            self.qem.showMessage("Under Voltage: Output Voltage of " + ov_str +
                                 " is below minimum voltage of " + mv_str,
                                 "Stepper_UnderVoltage")
        
    def enable_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.endis_all(True)
                self.stepper.enable()
            elif state == Qt.Unchecked:
                self.endis_all(False)
                self.stepper.disable()
        except ip_connection.Error:
            return
        
    def stack_input_voltage_update(self, sv):
        sv_str = "%gV"  % round(sv/1000.0, 1)
        self.stack_voltage_label.setText(sv_str)
        
    def external_input_voltage_update(self, ev):
        ev_str = "%gV"  % round(ev/1000.0, 1)
        self.external_voltage_label.setText(ev_str)
        
    def minimum_voltage_update(self, mv):
        mv_str = "%gV"  % round(mv/1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)
        
    def maximum_current_update(self, cur):
        cur_str = "%gA"  % round(cur/1000.0, 1)
        self.maximum_current_label.setText(cur_str)
        
    def position_update(self, pos):
        pos_str = "%d" % pos
        self.position_label.setText(pos_str)
        
    def remaining_steps_update(self, ste):
        ste_str = "%d" % ste
        self.remaining_steps_label.setText(ste_str)
        
    def mode_update(self, mod):
        if mod == 8:
            index = 3
        elif mod == 4:
            index = 2
        elif mod == 2:
            index = 1
        else:
            index = 0
            
        self.mode_dropbox.setCurrentIndex(index)
        
    def get_max_velocity_async(self, velocity):
        if not self.velocity_slider.isSliderDown():
            if velocity != self.velocity_slider.sliderPosition():
                self.velocity_slider.setSliderPosition(velocity)
                self.velocity_spin.setValue(velocity)
        
    def get_speed_ramping_async(self, ramp):
        acc, dec = ramp
        if not self.acceleration_slider.isSliderDown() and \
           not self.deceleration_slider.isSliderDown():
            if acc != self.acceleration_slider.sliderPosition():
                self.acceleration_slider.setSliderPosition(acc)
                self.acceleration_spin.setValue(acc)
            if dec != self.deceleration_slider.sliderPosition():
                self.deceleration_slider.setSliderPosition(dec)
                self.deceleration_spin.setValue(dec)
        
    def is_enabled_async(self, enabled):
        if enabled:
            if self.enable_checkbox.checkState() != Qt.Checked:
                self.endis_all(True)
                self.enable_checkbox.setCheckState(Qt.Checked)
        else:
            if self.enable_checkbox.checkState() != Qt.Unchecked:
                self.endis_all(False)
                self.enable_checkbox.setCheckState(Qt.Unchecked)
        
    def update_start(self):
        async_call(self.stepper.get_max_velocity, None, self.get_max_velocity_async, self.increase_error_count)
        async_call(self.stepper.get_speed_ramping, None, self.get_speed_ramping_async, self.increase_error_count)
        async_call(self.stepper.is_enabled, None, self.is_enabled_async, self.increase_error_count)

    def update_data(self):
        async_call(self.stepper.get_remaining_steps, None, self.remaining_steps_update, self.increase_error_count)
        async_call(self.stepper.get_current_position, None, self.position_update, self.increase_error_count)
        async_call(self.stepper.get_current_velocity, None, self.speedometer.set_velocity, self.increase_error_count)

        self.update_counter += 1
        if self.update_counter % 10 == 0:
            async_call(self.stepper.get_motor_current, None, self.maximum_current_update, self.increase_error_count)
            async_call(self.stepper.get_stack_input_voltage, None, self.stack_input_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_external_input_voltage, None, self.external_input_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_minimum_voltage, None, self.minimum_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_step_mode, None, self.mode_update, self.increase_error_count)
        
    def velocity_slider_released(self):
        value = self.velocity_slider.value()
        self.velocity_spin.setValue(value)
        try:
            self.stepper.set_max_velocity(value)
        except ip_connection.Error:
            return
 
    def velocity_spin_finished(self):
        value = self.velocity_spin.value()
        self.velocity_slider.setValue(value)
        try:
            self.stepper.set_max_velocity(value)
        except ip_connection.Error:
            return
    
    def acceleration_slider_released(self):
        acc = self.acceleration_slider.value()
        dec = self.deceleration_slider.value()
        self.acceleration_spin.setValue(acc)
        try:
            self.stepper.set_speed_ramping(acc, dec)
        except ip_connection.Error:
            return
 
    def acceleration_spin_finished(self):
        acc = self.acceleration_spin.value()
        dec = self.deceleration_spin.value()
        self.acceleration_slider.setValue(acc)
        try:
            self.stepper.set_speed_ramping(acc, dec)
        except ip_connection.Error:
            return
            
    def deceleration_slider_released(self):
        acc = self.acceleration_slider.value()
        dec = self.deceleration_slider.value()
        self.deceleration_spin.setValue(dec)
        try:
            self.stepper.set_speed_ramping(acc, dec)
        except ip_connection.Error:
            return
 
    def deceleration_spin_finished(self):
        acc = self.acceleration_spin.value()
        dec = self.deceleration_spin.value()
        self.deceleration_slider.setValue(dec)
        try:
            self.stepper.set_speed_ramping(acc, dec)
        except ip_connection.Error:
            return
예제 #36
0
class SilentStepper(PluginBase, Ui_SilentStepper):
    qtcb_position_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)
    
    def __init__(self, *args):
        PluginBase.__init__(self, BrickSilentStepper, *args)

        self.setupUi(self)
     
        self.silent_stepper = self.device
     
        self.endis_all(False)
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(5, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.deceleration_syncer = SliderSpinSyncer(self.deceleration_slider,
                                                    self.deceleration_spin,
                                                    self.deceleration_changed)

        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        self.forward_button.clicked.connect(self.forward_clicked)
        self.stop_button.clicked.connect(self.stop_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.backward_button.clicked.connect(self.backward_clicked)
        self.to_button.clicked.connect(self.to_button_clicked)
        self.steps_button.clicked.connect(self.steps_button_clicked)
        self.motor_current_button.clicked.connect(self.motor_current_button_clicked)
        self.minimum_motor_voltage_button.clicked.connect(self.minimum_motor_voltage_button_clicked)

        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.silent_stepper.register_callback(self.silent_stepper.CALLBACK_POSITION_REACHED, 
                                              self.qtcb_position_reached.emit)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.silent_stepper.register_callback(self.silent_stepper.CALLBACK_UNDER_VOLTAGE, 
                                              self.qtcb_under_voltage.emit)
        
        # Step Configuration
        self.step_resolution_dropbox.currentIndexChanged.connect(self.step_configuration_changed)
        self.interpolate_checkbox.stateChanged.connect(self.step_configuration_changed)
        
        # Basic Configuration
        self.standstill_current_spin.valueChanged.connect(self.basic_configuration_changed)
        self.motor_run_current_spin.valueChanged.connect(self.basic_configuration_changed)
        self.standstill_delay_time_spin.valueChanged.connect(self.basic_configuration_changed)
        self.power_down_time_spin.valueChanged.connect(self.basic_configuration_changed)
        self.stealth_threshold_spin.valueChanged.connect(self.basic_configuration_changed)
        self.coolstep_threashold_spin.valueChanged.connect(self.basic_configuration_changed)
        self.classic_threshold_spin.valueChanged.connect(self.basic_configuration_changed)
        self.high_velocity_chopper_mode_checkbox.stateChanged.connect(self.basic_configuration_changed)
        
        # Spreadcycle Configuration
        self.slow_decay_duration_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.enable_random_slow_decay_checkbox.stateChanged.connect(self.spreadcycle_configuration_changed)
        self.fast_decay_duration_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.hysteresis_start_value_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.hysteresis_end_value_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.sinewave_offset_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.chopper_mode_combo.currentIndexChanged.connect(self.spreadcycle_configuration_changed)
        self.comperator_blank_time_combo.currentIndexChanged.connect(self.spreadcycle_configuration_changed)
        self.fast_decay_without_comperator_checkbox.stateChanged.connect(self.spreadcycle_configuration_changed)
        
        # Stealth Configuration
        self.enable_stealth_checkbox.stateChanged.connect(self.stealth_configuration_changed)
        self.amplitude_spin.valueChanged.connect(self.stealth_configuration_changed)
        self.gradient_spin.valueChanged.connect(self.stealth_configuration_changed)
        self.enable_autoscale_checkbox.stateChanged.connect(self.stealth_configuration_changed)
        self.force_symmetric_checkbox.stateChanged.connect(self.stealth_configuration_changed)
        self.freewheel_mode_combo.currentIndexChanged.connect(self.stealth_configuration_changed)
        
        # Coolstep Configuration
        self.minimum_stallguard_value_spin.valueChanged.connect(self.coolstep_configuration_changed)
        self.maximum_stallguard_value_spin.valueChanged.connect(self.coolstep_configuration_changed)
        self.current_up_step_width_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        self.current_down_step_width_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        self.minimum_current_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        self.stallguard_threshold_value_spin.valueChanged.connect(self.coolstep_configuration_changed)
        self.stallguard_mode_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        
        # Misc Configuration
        self.disable_short_to_ground_protection_checkbox.stateChanged.connect(self.misc_configuration_changed)
        self.synchronize_phase_frequency_spin.valueChanged.connect(self.misc_configuration_changed)
        
        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv  = 0
        self.ev  = 0
        self.mv  = 0
        self.mod = 0

        reset = QAction('Reset', self)
        reset.triggered.connect(lambda: self.silent_stepper.reset())
        self.set_actions(reset)
        
    def start(self):
        self.update_timer.start(100)
        self.update_start()
        
    def stop(self):
        self.update_timer.stop()

    def destroy(self):
        pass

    def get_url_part(self):
        return 'silent_stepper'

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickSilentStepper.DEVICE_IDENTIFIER
    
    def cb_position_reached(self, position):
        self.position_update(position)
        self.endis_all(True)
            
    def disable_list(self, button_list):
        for button in button_list:
            button.setEnabled(False)
        
    def endis_all(self, value):
        self.forward_button.setEnabled(value)
        self.stop_button.setEnabled(value)
        self.backward_button.setEnabled(value)
        self.to_button.setEnabled(value)
        self.steps_button.setEnabled(value)
        self.full_brake_button.setEnabled(value)
        
    def step_configuration_changed(self, _):
        step_resolution = self.step_resolution_dropbox.currentIndex()
        interpolation = self.interpolate_checkbox.isChecked()
        try:
            self.silent_stepper.set_step_configuration(step_resolution, interpolation)
        except ip_connection.Error:
            return
        
    def basic_configuration_changed(self, _):
        standstill_current = self.standstill_current_spin.value()
        motor_run_current = self.motor_run_current_spin.value()
        standstill_delay_time = self.standstill_delay_time_spin.value()
        power_down_time = self.power_down_time_spin.value()
        stealth_threshold = self.stealth_threshold_spin.value()
        coolstep_threshold = self.coolstep_threashold_spin.value()
        classic_threshold = self.classic_threshold_spin.value()
        high_velocity_chopper_mode = self.high_velocity_chopper_mode_checkbox.isChecked()
        
        try:
            self.silent_stepper.set_basic_configuration(standstill_current, motor_run_current, standstill_delay_time, power_down_time, stealth_threshold, coolstep_threshold, classic_threshold, high_velocity_chopper_mode)
        except ip_connection.Error:
            return

    def spreadcycle_configuration_changed(self, _):
        slow_decay_duration = self.slow_decay_duration_spin.value()
        enable_random_slow_decay = self.enable_random_slow_decay_checkbox.isChecked()
        fast_decay_duration = self.fast_decay_duration_spin.value()
        hysteresis_start_value = self.hysteresis_start_value_spin.value()
        hysteresis_end_value = self.hysteresis_end_value_spin.value()
        sinewave_offset = self.sinewave_offset_spin.value()
        chopper_mode = self.chopper_mode_combo.currentIndex()
        comperator_blank_time = self.comperator_blank_time_combo.currentIndex()
        fast_decay_without_comperator = self.fast_decay_without_comperator_checkbox.isChecked()
        
        try:
            self.silent_stepper.set_spreadcycle_configuration(slow_decay_duration, enable_random_slow_decay, fast_decay_duration, hysteresis_start_value, hysteresis_end_value, sinewave_offset, chopper_mode, comperator_blank_time, fast_decay_without_comperator)
        except ip_connection.Error:
            return
        
    def stealth_configuration_changed(self, _):
        enable_stealth = self.enable_stealth_checkbox.isChecked()
        amplitude = self.amplitude_spin.value()
        gradient = self.gradient_spin.value()
        enable_autoscale = self.enable_autoscale_checkbox.isChecked()
        force_symmetric = self.force_symmetric_checkbox.isChecked()
        freewheel_mode = self.freewheel_mode_combo.currentIndex()
        
        try:
            self.silent_stepper.set_stealth_configuration(enable_stealth, amplitude, gradient, enable_autoscale, force_symmetric, freewheel_mode)
        except ip_connection.Error:
            return
        
    def coolstep_configuration_changed(self, _):
        minimum_stallguard_value = self.minimum_stallguard_value_spin.value()
        maximum_stallguard_value = self.maximum_stallguard_value_spin.value()
        current_up_step_width = self.current_up_step_width_combo.currentIndex()
        current_down_step_width = self.current_down_step_width_combo.currentIndex()
        minimum_current = self.minimum_current_combo.currentIndex()
        stallguard_threshold_value = self.stallguard_threshold_value_spin.value()
        stallguard_mode = self.stallguard_mode_combo.currentIndex()
        
        try:
            self.silent_stepper.set_coolstep_configuration(minimum_stallguard_value, maximum_stallguard_value, current_up_step_width, current_down_step_width, minimum_current, stallguard_threshold_value, stallguard_mode)
        except ip_connection.Error:
            return
        
    def misc_configuration_changed(self, _):
        disable_short_to_ground_protection = self.disable_short_to_ground_protection_checkbox.isChecked()
        synchronize_phase_frequency = self.synchronize_phase_frequency_spin.value()
        
        try:
            self.silent_stepper.set_misc_configuration(disable_short_to_ground_protection, synchronize_phase_frequency)
        except ip_connection.Error:
            return
        
    def forward_clicked(self):
        try:
            self.silent_stepper.drive_forward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])
        
    def backward_clicked(self):
        try:
            self.silent_stepper.drive_backward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])
        
    def stop_clicked(self):
        try:
            self.silent_stepper.stop()
        except ip_connection.Error:
            return
        self.endis_all(True)
        
    def full_brake_clicked(self):
        try:
            self.silent_stepper.full_brake()
        except ip_connection.Error:
            return
        self.endis_all(True)
        
    def to_button_clicked(self):
        drive_to = self.to_spin.value()
        try:
            self.silent_stepper.set_target_position(drive_to)
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, 
                           self.steps_button, 
                           self.forward_button,
                           self.backward_button])
        
    def steps_button_clicked(self):
        drive_steps = self.steps_spin.value()
        try:
            self.silent_stepper.set_steps(drive_steps)
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, 
                           self.steps_button, 
                           self.forward_button,
                           self.backward_button])
        
    def motor_current_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(2500)
        qid.setIntStep(100)
        async_call(self.silent_stepper.get_motor_current, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.motor_current_selected)
        qid.setLabelText("Choose motor current in mA.")
        qid.open()
        
    def minimum_motor_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(40000)
        qid.setIntStep(100)
        async_call(self.silent_stepper.get_minimum_voltage, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_motor_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()
        
    def motor_current_selected(self, value):
        try:
            self.silent_stepper.set_motor_current(value)
        except ip_connection.Error:
            return
        
    def minimum_motor_voltage_selected(self, value):
        try:
            self.silent_stepper.set_minimum_voltage(value)
        except ip_connection.Error:
            return
        
    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV"  % round(ov/1000.0, 1)
        if not self.qem.isVisible():
            self.qem.showMessage("Under Voltage: Output Voltage of " + ov_str +
                                 " is below minimum voltage of " + mv_str,
                                 "SilentStepper_UnderVoltage")
        
    def enable_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.endis_all(True)
                self.silent_stepper.enable()
            elif state == Qt.Unchecked:
                self.endis_all(False)
                self.silent_stepper.disable()
        except ip_connection.Error:
            return
        
    def stack_input_voltage_update(self, sv):
        sv_str = "%gV"  % round(sv/1000.0, 1)
        self.stack_voltage_label.setText(sv_str)
        
    def external_input_voltage_update(self, ev):
        ev_str = "%gV"  % round(ev/1000.0, 1)
        self.external_voltage_label.setText(ev_str)
        
    def minimum_voltage_update(self, mv):
        mv_str = "%gV"  % round(mv/1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)
        
    def maximum_current_update(self, cur):
        cur_str = "%gA"  % round(cur/1000.0, 1)
        self.maximum_current_label.setText(cur_str)
        
    def position_update(self, pos):
        pos_str = "%d" % pos
        self.position_label.setText(pos_str)
        
    def remaining_steps_update(self, ste):
        ste_str = "%d" % ste
        self.remaining_steps_label.setText(ste_str)
        
    def driver_status_update(self, update):
        if update.open_load == 0:
            self.status_open_load.setText('No')
        elif update.open_load == 1:
            self.status_open_load.setText('Phase A')
        elif update.open_load == 2:
            self.status_open_load.setText('Phase B')
        elif update.open_load == 3:
            self.status_open_load.setText('Phase A and B')
        else:
            self.status_open_load.setText('Unkown')
            
        if update.short_to_ground == 0:
            self.status_short_to_ground.setText('No')
        elif update.short_to_ground == 1:
            self.status_short_to_ground.setText('Phase A')
        elif update.short_to_ground == 2:
            self.status_short_to_ground.setText('Phase B')
        elif update.short_to_ground == 3:
            self.status_short_to_ground.setText('Phase A and B')
        else:
            self.status_short_to_ground.setText('Unkown')
            
        if update.over_temperature == 0:
            self.status_over_temperature.setText('No')
        elif update.over_temperature == 1:
            self.status_over_temperature.setText('<font color=yellow>Warning</font>')
        elif update.over_temperature == 2:
            self.status_over_temperature.setText('<font color=red>Limit</font>')
        
        if update.motor_stalled:
            self.status_motor_stalled.setText('Yes')
        else:
            self.status_motor_stalled.setText('No')
            
        self.status_actual_motor_current.setText(str(update.actual_motor_current))
        
        if update.full_step_active:
            self.status_full_step_active.setText('Yes')
        else:
            self.status_full_step_active.setText('No')
            
        self.status_stallguard_result.setText(str(update.stallguard_result))
        self.status_stealth_voltage_amplitude.setText(str(update.stealth_voltage_amplitude))
            
    def get_max_velocity_async(self, velocity):
        if not self.velocity_slider.isSliderDown():
            if velocity != self.velocity_slider.sliderPosition():
                self.velocity_slider.setSliderPosition(velocity)
                self.velocity_spin.setValue(velocity)
        
    def get_speed_ramping_async(self, ramp):
        acc, dec = ramp
        if not self.acceleration_slider.isSliderDown() and \
           not self.deceleration_slider.isSliderDown():
            if acc != self.acceleration_slider.sliderPosition():
                self.acceleration_slider.setSliderPosition(acc)
                self.acceleration_spin.setValue(acc)
            if dec != self.deceleration_slider.sliderPosition():
                self.deceleration_slider.setSliderPosition(dec)
                self.deceleration_spin.setValue(dec)
        
    def is_enabled_async(self, enabled):
        if enabled:
            if not self.enable_checkbox.isChecked():
                self.endis_all(True)
                self.enable_checkbox.blockSignals(True)
                self.enable_checkbox.setChecked(True)
                self.enable_checkbox.blockSignals(False)
        else:
            if self.enable_checkbox.isChecked():
                self.endis_all(False)
                self.enable_checkbox.blockSignals(True)
                self.enable_checkbox.setChecked(False)
                self.enable_checkbox.blockSignals(False)
                        
    def get_step_configuration_async(self, conf):
        self.step_resolution_dropbox.blockSignals(True)
        self.step_resolution_dropbox.setCurrentIndex(conf.step_resolution)
        self.step_resolution_dropbox.blockSignals(False)
        
        self.interpolate_checkbox.blockSignals(True)
        self.interpolate_checkbox.setChecked(conf.interpolation)
        self.interpolate_checkbox.blockSignals(False)
        
    def get_basic_configuration_async(self, conf):
        self.standstill_current_spin.blockSignals(True)
        self.standstill_current_spin.setValue(conf.standstill_current)
        self.standstill_current_spin.blockSignals(False)

        self.motor_run_current_spin.blockSignals(True)
        self.motor_run_current_spin.setValue(conf.motor_run_current)
        self.motor_run_current_spin.blockSignals(False)
        
        self.standstill_delay_time_spin.blockSignals(True)
        self.standstill_delay_time_spin.setValue(conf.standstill_delay_time)
        self.standstill_delay_time_spin.blockSignals(False)
        
        self.power_down_time_spin.blockSignals(True)
        self.power_down_time_spin.setValue(conf.power_down_time)
        self.power_down_time_spin.blockSignals(False)
        
        self.stealth_threshold_spin.blockSignals(True)
        self.stealth_threshold_spin.setValue(conf.stealth_threshold)
        self.stealth_threshold_spin.blockSignals(False)
        
        self.coolstep_threashold_spin.blockSignals(True)
        self.coolstep_threashold_spin.setValue(conf.coolstep_threshold)
        self.coolstep_threashold_spin.blockSignals(False)
        
        self.classic_threshold_spin.blockSignals(True)
        self.classic_threshold_spin.setValue(conf.classic_threshold)
        self.classic_threshold_spin.blockSignals(False)
        
        self.high_velocity_chopper_mode_checkbox.blockSignals(True)
        self.high_velocity_chopper_mode_checkbox.setChecked(conf.high_velocity_chopper_mode)
        self.high_velocity_chopper_mode_checkbox.blockSignals(False)
    
    def get_spreadcycle_configuration_async(self, conf):
        self.slow_decay_duration_spin.blockSignals(True)
        self.slow_decay_duration_spin.setValue(conf.slow_decay_duration)
        self.slow_decay_duration_spin.blockSignals(False)
        
        self.enable_random_slow_decay_checkbox.blockSignals(True)
        self.enable_random_slow_decay_checkbox.setChecked(conf.enable_random_slow_decay)
        self.enable_random_slow_decay_checkbox.blockSignals(False)
        
        self.fast_decay_duration_spin.blockSignals(True)
        self.fast_decay_duration_spin.setValue(conf.fast_decay_duration)
        self.fast_decay_duration_spin.blockSignals(False)
        
        self.hysteresis_start_value_spin.blockSignals(True)
        self.hysteresis_start_value_spin.setValue(conf.hysteresis_start_value)
        self.hysteresis_start_value_spin.blockSignals(False)
        
        self.hysteresis_end_value_spin.blockSignals(True)
        self.hysteresis_end_value_spin.setValue(conf.hysteresis_end_value)
        self.hysteresis_end_value_spin.blockSignals(False)
        
        self.sinewave_offset_spin.blockSignals(True)
        self.sinewave_offset_spin.setValue(conf.sinewave_offset)
        self.sinewave_offset_spin.blockSignals(False)
        
        self.chopper_mode_combo.blockSignals(True)
        self.chopper_mode_combo.setCurrentIndex(conf.chopper_mode)
        self.chopper_mode_combo.blockSignals(False)
        
        self.standstill_current_spin.blockSignals(True)
        self.comperator_blank_time_combo.setCurrentIndex(conf.comperator_blank_time)
        self.standstill_current_spin.blockSignals(False)
        
        self.fast_decay_without_comperator_checkbox.blockSignals(True)
        self.fast_decay_without_comperator_checkbox.setChecked(conf.fast_decay_without_comperator)
        self.fast_decay_without_comperator_checkbox.blockSignals(False)
        
    
    def get_stealth_configuration_async(self, conf):
        self.enable_stealth_checkbox.blockSignals(True)
        self.enable_stealth_checkbox.setChecked(conf.enable_stealth)
        self.enable_stealth_checkbox.blockSignals(False)
        
        self.amplitude_spin.blockSignals(True)
        self.amplitude_spin.setValue(conf.amplitude)
        self.amplitude_spin.blockSignals(False)
        
        self.gradient_spin.blockSignals(True)
        self.gradient_spin.setValue(conf.gradient)
        self.gradient_spin.blockSignals(False)
        
        self.enable_autoscale_checkbox.blockSignals(True)
        self.enable_autoscale_checkbox.setChecked(conf.enable_autoscale)
        self.enable_autoscale_checkbox.blockSignals(False)
        
        self.force_symmetric_checkbox.blockSignals(True)
        self.force_symmetric_checkbox.setChecked(conf.force_symmetric)
        self.force_symmetric_checkbox.blockSignals(False)
        
        self.freewheel_mode_combo.blockSignals(True)
        self.freewheel_mode_combo.setCurrentIndex(conf.freewheel_mode)
        self.freewheel_mode_combo.blockSignals(False)
    
    def get_coolstep_configuration_async(self, conf):
        self.minimum_stallguard_value_spin.blockSignals(True)
        self.minimum_stallguard_value_spin.setValue(conf.minimum_stallguard_value)
        self.minimum_stallguard_value_spin.blockSignals(False)
    
        self.maximum_stallguard_value_spin.blockSignals(True)
        self.maximum_stallguard_value_spin.setValue(conf.maximum_stallguard_value)
        self.maximum_stallguard_value_spin.blockSignals(False)
    
        self.current_up_step_width_combo.blockSignals(True)
        self.current_up_step_width_combo.setCurrentIndex(conf.current_up_step_width)
        self.current_up_step_width_combo.blockSignals(False)
    
        self.current_down_step_width_combo.blockSignals(True)
        self.current_down_step_width_combo.setCurrentIndex(conf.current_down_step_width)
        self.current_down_step_width_combo.blockSignals(False)
    
        self.minimum_current_combo.blockSignals(True)
        self.minimum_current_combo.setCurrentIndex(conf.minimum_current)
        self.minimum_current_combo.blockSignals(False)
    
        self.stallguard_threshold_value_spin.blockSignals(True)
        self.stallguard_threshold_value_spin.setValue(conf.stallguard_threshold_value)
        self.stallguard_threshold_value_spin.blockSignals(False)
    
        self.stallguard_mode_combo.blockSignals(True)
        self.stallguard_mode_combo.setCurrentIndex(conf.stallguard_mode)
        self.stallguard_mode_combo.blockSignals(False)
        
    def get_misc_configuration_async(self, conf):
        self.disable_short_to_ground_protection_checkbox.blockSignals(True)
        self.disable_short_to_ground_protection_checkbox.setChecked(conf.disable_short_to_ground_protection)
        self.disable_short_to_ground_protection_checkbox.blockSignals(False)
        
        self.synchronize_phase_frequency_spin.blockSignals(True)
        self.synchronize_phase_frequency_spin.setValue(conf.synchronize_phase_frequency)
        self.synchronize_phase_frequency_spin.blockSignals(False)
        
    def update_start(self):
        async_call(self.silent_stepper.get_max_velocity, None, self.get_max_velocity_async, self.increase_error_count)
        async_call(self.silent_stepper.get_speed_ramping, None, self.get_speed_ramping_async, self.increase_error_count)
        async_call(self.silent_stepper.is_enabled, None, self.is_enabled_async, self.increase_error_count)
        async_call(self.silent_stepper.get_step_configuration, None, self.get_step_configuration_async, self.increase_error_count)
        async_call(self.silent_stepper.get_basic_configuration, None, self.get_basic_configuration_async, self.increase_error_count)
        async_call(self.silent_stepper.get_spreadcycle_configuration, None, self.get_spreadcycle_configuration_async, self.increase_error_count)
        async_call(self.silent_stepper.get_stealth_configuration, None, self.get_stealth_configuration_async, self.increase_error_count)
        async_call(self.silent_stepper.get_coolstep_configuration, None, self.get_coolstep_configuration_async, self.increase_error_count)
        async_call(self.silent_stepper.get_misc_configuration, None, self.get_misc_configuration_async, self.increase_error_count)

    def update_data(self):
        async_call(self.silent_stepper.get_remaining_steps, None, self.remaining_steps_update, self.increase_error_count)
        async_call(self.silent_stepper.get_current_position, None, self.position_update, self.increase_error_count)
        async_call(self.silent_stepper.get_current_velocity, None, self.speedometer.set_velocity, self.increase_error_count)

        self.update_counter += 1
        if self.update_counter % 10 == 0:
            async_call(self.silent_stepper.get_motor_current, None, self.maximum_current_update, self.increase_error_count)
            async_call(self.silent_stepper.get_stack_input_voltage, None, self.stack_input_voltage_update, self.increase_error_count)
            async_call(self.silent_stepper.get_external_input_voltage, None, self.external_input_voltage_update, self.increase_error_count)
            async_call(self.silent_stepper.get_minimum_voltage, None, self.minimum_voltage_update, self.increase_error_count)
            async_call(self.silent_stepper.get_driver_status, None, self.driver_status_update, self.increase_error_count)

    def velocity_changed(self, value):
        try:
            self.silent_stepper.set_max_velocity(value)
        except ip_connection.Error:
            return

    def acceleration_changed(self, value):
        dec = self.deceleration_spin.value()
        try:
            self.silent_stepper.set_speed_ramping(value, dec)
        except ip_connection.Error:
            return
            
    def deceleration_changed(self, value):
        acc = self.acceleration_slider.value()
        try:
            self.silent_stepper.set_speed_ramping(acc, value)
        except ip_connection.Error:
            return
예제 #37
0
def main():
    """
    Main entry point into the application.
    """
    global args, mainWindow, splash, restartArgs
    
    sys.excepthook = excepthook
    
    options = [\
        ("--config=configDir", 
         "use the given directory as the one containing the config files"), 
        ("--debug", "activate debugging output to the console"), 
        ("--nosplash", "don't show the splash screen"),
        ("--noopen", "don't open anything at startup except that given in command"), 
        ("--nokde" , "don't use KDE widgets"),
        ("--plugin=plugin-file", "load the given plugin file (plugin development)"), 
        ("--start-session", "load the global session file"), 
        ("--", "indicate that there are options for the program to be debugged"),
        ("", "(everything after that is considered arguments for this program)")
    ]
    kqOptions = [\
        ("config \\", "use the given directory as the one containing the config files"), 
        ("debug", "activate debugging output to the console"), 
        ("nosplash", "don't show the splash screen"),
        ("noopen", "don't open anything at startup except that given in command"), 
        ("nokde" , "don't use KDE widgets"),
        ("plugin \\", "load the given plugin file (plugin development)"), 
        ("start-session", "load the global session file"), 
        ("!+file", "")
    ]
    appinfo = Startup.makeAppInfo(sys.argv,
                                  "Eric4",
                                  "[project | files... [--] [debug-options]]",
                                  "A Python IDE",
                                  options)
    ddindex = Startup.handleArgs(sys.argv, appinfo)
    
    if not Utilities.checkBlacklistedVersions():
        sys.exit(100)
    
    app = KQApplication(sys.argv, kqOptions)
    
    if Preferences.getUI("SingleApplicationMode"):
        handleSingleApplication(ddindex)
    
    # set the library paths for plugins
    Startup.setLibraryPaths()
    
    # set the search path for icons
    Startup.initializeResourceSearchPath()

    # generate and show a splash window, if not suppressed
    if "--nosplash" in sys.argv and sys.argv.index("--nosplash") < ddindex:
        del sys.argv[sys.argv.index("--nosplash")]
        splash = NoneSplashScreen()
    elif not Preferences.getUI("ShowSplash"):
        splash = NoneSplashScreen()
    else:
        splash = SplashScreen()
    
    # modify the executable search path for the PyQt4 installer
    if Utilities.isWindowsPlatform():
        pyqtDataDir = Utilities.getPyQt4ModulesDirectory()
        if os.path.exists(os.path.join(pyqtDataDir, "bin")):
            path = os.path.join(pyqtDataDir, "bin") + os.pathsep + os.environ["PATH"]
        else:
            path = pyqtDataDir + os.pathsep + os.environ["PATH"]
        os.environ["PATH"] = path
    
    pluginFile = None
    noopen = False
    if "--noopen" in sys.argv and sys.argv.index("--noopen") < ddindex:
        del sys.argv[sys.argv.index("--noopen")]
        noopen = True
    for arg in sys.argv:
        if arg.startswith("--plugin=") and sys.argv.index(arg) < ddindex:
            # extract the plugin development option
            pluginFile = arg.replace("--plugin=", "").replace('"', "")
            sys.argv.remove(arg)
            pluginFile = os.path.expanduser(pluginFile)
            pluginFile = Utilities.normabspath(pluginFile)
            break
    
    # is there a set of filenames or options on the command line,
    # if so, pass them to the UI
    if len(sys.argv) > 1:
        args = sys.argv[1:]
    
    # Set the applications string encoding
    try:
        sys.setappdefaultencoding(str(Preferences.getSystem("StringEncoding")))
    except AttributeError:
        pass
    
    # get the Qt4 translations directory
    qt4TransDir = Preferences.getQt4TranslationsDir()
    if not qt4TransDir:
        qt4TransDir = QLibraryInfo.location(QLibraryInfo.TranslationsPath)
    
    # Load translation files and install them
    loc = Startup.loadTranslators(qt4TransDir, app, ("qscintilla",))
    
    QTextCodec.setCodecForCStrings(QTextCodec.codecForName(\
        str(Preferences.getSystem("StringEncoding"))))
    
    splash.showMessage(QApplication.translate("eric4", "Importing packages..."))
    # We can only import these after creating the KQApplication because they
    # make Qt calls that need the KQApplication to exist.
    from UI.UserInterface import UserInterface

    splash.showMessage(QApplication.translate("eric4", "Generating Main Window..."))
    try:
        mainWindow = UserInterface(app, loc, splash, pluginFile, noopen, restartArgs)
        app.connect(app, SIGNAL("lastWindowClosed()"), app, SLOT("quit()"))
        mainWindow.show()
        
        QTimer.singleShot(0, uiStartUp)
        
        # generate a graphical error handler
        eMsg = QErrorMessage.qtHandler()
        eMsg.setMinimumSize(600, 400)
        
        # start the event loop
        res = app.exec_()
        logging.debug("Shutting down, result %d" % res)
        logging.shutdown()
        sys.exit(res)
    except Exception, err:
        raise err
예제 #38
0
class ImagesWidget(QWidget, Ui_Images):
    images = None

    def __init__(self, parent, app):
        super(QWidget, self).__init__()
        self.app = app

        self.setupUi(self)

        self.error_msg = QErrorMessage()
        self.error_msg.setWindowTitle("Starter Kit: Blinkenlights Demo " + config.DEMO_VERSION)

        self.slider_frame_rate.valueChanged.connect(self.slider_frame_rate_changed)
        self.spinbox_frame_rate.valueChanged.connect(self.spinbox_frame_rate_changed)
        self.button_choose.pressed.connect(self.choose_pressed)
        self.button_show.pressed.connect(self.show_pressed)
        self.button_default.pressed.connect(self.default_pressed)

        self.update_frame_rate_timer = QTimer(self)
        self.update_frame_rate_timer.timeout.connect(self.update_frame_rate)

        self.default_pressed()

    def start(self):
        self.images = Images(self.app.ipcon)

        self.update_frame_rate()

        self.images.frame_rendered(0)

    def stop(self):
        if self.images:
            self.images.stop_rendering()
            self.images = None

    def spinbox_frame_rate_changed(self, frame_rate):
        self.slider_frame_rate.setValue(frame_rate)
        self.update_frame_rate_timer.start(100)

    def slider_frame_rate_changed(self, frame_rate):
        self.spinbox_frame_rate.setValue(frame_rate)

    def show_pressed(self):
        if self.images:
            files = unicode(self.text_edit_files.toPlainText()).strip()

            if len(files) > 0:
                new_images = files.split('\n')

                try:
                    self.images.set_new_images(new_images)
                except Exception as e:
                    self.error_msg.showMessage(str(e))

                self.images.frame_prepare_next()
                self.images.frame_rendered(0)

    def choose_pressed(self):
        for filename in QFileDialog.getOpenFileNames(self, 'Choose Images', QDir.homePath()):
            self.text_edit_files.append(filename)

    def default_pressed(self):
        self.spinbox_frame_rate.setValue(1)

    def update_frame_rate(self):
        self.update_frame_rate_timer.stop()

        config.IMAGES_FRAME_RATE = self.spinbox_frame_rate.value()

        if self.images:
            self.images.update_frame_rate()
예제 #39
0
    def __init__(self, *args):
        PluginBase.__init__(self, BrickSilentStepper, *args)

        self.setupUi(self)
     
        self.silent_stepper = self.device
     
        self.endis_all(False)
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(5, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.deceleration_syncer = SliderSpinSyncer(self.deceleration_slider,
                                                    self.deceleration_spin,
                                                    self.deceleration_changed)

        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        self.forward_button.clicked.connect(self.forward_clicked)
        self.stop_button.clicked.connect(self.stop_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.backward_button.clicked.connect(self.backward_clicked)
        self.to_button.clicked.connect(self.to_button_clicked)
        self.steps_button.clicked.connect(self.steps_button_clicked)
        self.motor_current_button.clicked.connect(self.motor_current_button_clicked)
        self.minimum_motor_voltage_button.clicked.connect(self.minimum_motor_voltage_button_clicked)

        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.silent_stepper.register_callback(self.silent_stepper.CALLBACK_POSITION_REACHED, 
                                              self.qtcb_position_reached.emit)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.silent_stepper.register_callback(self.silent_stepper.CALLBACK_UNDER_VOLTAGE, 
                                              self.qtcb_under_voltage.emit)
        
        # Step Configuration
        self.step_resolution_dropbox.currentIndexChanged.connect(self.step_configuration_changed)
        self.interpolate_checkbox.stateChanged.connect(self.step_configuration_changed)
        
        # Basic Configuration
        self.standstill_current_spin.valueChanged.connect(self.basic_configuration_changed)
        self.motor_run_current_spin.valueChanged.connect(self.basic_configuration_changed)
        self.standstill_delay_time_spin.valueChanged.connect(self.basic_configuration_changed)
        self.power_down_time_spin.valueChanged.connect(self.basic_configuration_changed)
        self.stealth_threshold_spin.valueChanged.connect(self.basic_configuration_changed)
        self.coolstep_threashold_spin.valueChanged.connect(self.basic_configuration_changed)
        self.classic_threshold_spin.valueChanged.connect(self.basic_configuration_changed)
        self.high_velocity_chopper_mode_checkbox.stateChanged.connect(self.basic_configuration_changed)
        
        # Spreadcycle Configuration
        self.slow_decay_duration_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.enable_random_slow_decay_checkbox.stateChanged.connect(self.spreadcycle_configuration_changed)
        self.fast_decay_duration_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.hysteresis_start_value_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.hysteresis_end_value_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.sinewave_offset_spin.valueChanged.connect(self.spreadcycle_configuration_changed)
        self.chopper_mode_combo.currentIndexChanged.connect(self.spreadcycle_configuration_changed)
        self.comperator_blank_time_combo.currentIndexChanged.connect(self.spreadcycle_configuration_changed)
        self.fast_decay_without_comperator_checkbox.stateChanged.connect(self.spreadcycle_configuration_changed)
        
        # Stealth Configuration
        self.enable_stealth_checkbox.stateChanged.connect(self.stealth_configuration_changed)
        self.amplitude_spin.valueChanged.connect(self.stealth_configuration_changed)
        self.gradient_spin.valueChanged.connect(self.stealth_configuration_changed)
        self.enable_autoscale_checkbox.stateChanged.connect(self.stealth_configuration_changed)
        self.force_symmetric_checkbox.stateChanged.connect(self.stealth_configuration_changed)
        self.freewheel_mode_combo.currentIndexChanged.connect(self.stealth_configuration_changed)
        
        # Coolstep Configuration
        self.minimum_stallguard_value_spin.valueChanged.connect(self.coolstep_configuration_changed)
        self.maximum_stallguard_value_spin.valueChanged.connect(self.coolstep_configuration_changed)
        self.current_up_step_width_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        self.current_down_step_width_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        self.minimum_current_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        self.stallguard_threshold_value_spin.valueChanged.connect(self.coolstep_configuration_changed)
        self.stallguard_mode_combo.currentIndexChanged.connect(self.coolstep_configuration_changed)
        
        # Misc Configuration
        self.disable_short_to_ground_protection_checkbox.stateChanged.connect(self.misc_configuration_changed)
        self.synchronize_phase_frequency_spin.valueChanged.connect(self.misc_configuration_changed)
        
        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv  = 0
        self.ev  = 0
        self.mv  = 0
        self.mod = 0

        reset = QAction('Reset', self)
        reset.triggered.connect(lambda: self.silent_stepper.reset())
        self.set_actions(reset)
예제 #40
0
class WeatherStation(QApplication):
    HOST = "localhost"
    PORT = 4223

    ipcon = None
    lcd = None
    al = None
    al_v2 = None
    hum = None
    baro = None

    projects = []
    active_project = None

    error_msg = None

    def __init__(self, args):
        super(QApplication, self).__init__(args)

        self.error_msg = QErrorMessage()
        self.ipcon = IPConnection()

        signal.signal(signal.SIGINT, self.exit_demo)
        signal.signal(signal.SIGTERM, self.exit_demo)

        timer = QTimer(self)
        timer.setSingleShot(True)
        timer.timeout.connect(self.connect)
        timer.start(1)

        self.lcd_timer = QTimer(self)
        self.lcd_timer.timeout.connect(self.mute_lcd)
        self.lcd_timer.start(10000)

    def exit_demo(self, signl=None, frme=None):
        try:
            self.ipcon.disconnect()
            self.timer.stop()
            self.tabs.destroy()
        except:
            pass

        sys.exit()

    def open_gui(self):
        self.main = MainWindow(self)
        self.main.setFixedSize(930, 530)
        self.main.setWindowIcon(
            QIcon(load_pixmap('starter_kit_weather_station_demo-icon.png')))

        self.tabs = QTabWidget()

        widget = QWidget()
        layout = QVBoxLayout()
        layout.addWidget(self.tabs)
        widget.setLayout(layout)

        self.main.setCentralWidget(widget)

        self.projects.append(ProjectEnvDisplay(self.tabs, self))
        self.projects.append(ProjectStatistics(self.tabs, self))
        self.projects.append(ProjectXively(self.tabs, self))

        self.tabs.addTab(self.projects[0], "Display Environment Measurements")
        self.tabs.addTab(self.projects[1],
                         "Show Statistics with Button Control")
        self.tabs.addTab(self.projects[2], "Connect to Xively")

        self.active_project = self.projects[0]

        self.tabs.currentChanged.connect(self.tabChangedSlot)
        self.tabs.setCurrentIndex(1)

        self.main.setWindowTitle("Starter Kit: Weather Station Demo " +
                                 DEMO_VERSION)
        self.main.show()

    def connect(self):
        try:
            self.ipcon.connect(WeatherStation.HOST, WeatherStation.PORT)
        except Error as e:
            self.error_msg.showMessage('Connection Error: ' +
                                       str(e.description) +
                                       "\nBrickd installed and running?")
            return
        except socket.error as e:
            self.error_msg.showMessage('Socket error: ' + str(e) +
                                       "\nBrickd installed and running?")
            return

        self.ipcon.register_callback(IPConnection.CALLBACK_ENUMERATE,
                                     self.cb_enumerate)
        self.ipcon.register_callback(IPConnection.CALLBACK_CONNECTED,
                                     self.cb_connected)

        try:
            self.ipcon.enumerate()
        except Error as e:
            self.error_msg.showMessage('Enumerate Error: ' +
                                       str(e.description))
            return

        self.open_gui()

    def tabChangedSlot(self, tabIndex):

        if self.lcd is not None:
            self.lcd.clear_display()

        self.active_project = self.projects[tabIndex]

    def cb_illuminance(self, illuminance):
        for p in self.projects:
            p.update_illuminance(illuminance / 10.0)

    def cb_illuminance_v2(self, illuminance):
        for p in self.projects:
            p.update_illuminance(illuminance / 100.0)

    def cb_humidity(self, humidity):
        for p in self.projects:
            p.update_humidity(humidity / 10.0)

    def cb_air_pressure(self, air_pressure):
        for p in self.projects:
            p.update_air_pressure(air_pressure / 1000.0)

        try:
            temperature = self.baro.get_chip_temperature()
        except Error as e:
            print('Could not get temperature: ' + str(e.description))
            return

        for p in self.projects:
            p.update_temperature(temperature / 100.0)

    def configure_custom_chars(self):
        c = [[0x00 for x in range(8)] for y in range(8)]

        c[0] = [0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff]
        c[1] = [0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff]
        c[2] = [0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff]
        c[3] = [0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff]
        c[4] = [0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff]
        c[5] = [0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]
        c[6] = [0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]
        c[7] = [0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]

        for i in range(len(c)):
            self.lcd.set_custom_character(i, c[i])

    def cb_button_pressed(self, button):
        if self.lcd.is_backlight_on():
            for p in self.projects:
                p.button_pressed(button)
        else:
            self.lcd.backlight_on()
            self.lcd_timer.start()

    def mute_lcd(self):
        self.lcd.backlight_off()

    def cb_enumerate(self, uid, connected_uid, position, hardware_version,
                     firmware_version, device_identifier, enumeration_type):
        if enumeration_type == IPConnection.ENUMERATION_TYPE_CONNECTED or \
           enumeration_type == IPConnection.ENUMERATION_TYPE_AVAILABLE:
            if device_identifier == LCD20x4.DEVICE_IDENTIFIER:
                try:
                    self.lcd = LCD20x4(uid, self.ipcon)
                    self.lcd.clear_display()
                    self.lcd.backlight_on()
                    self.lcd.register_callback(
                        self.lcd.CALLBACK_BUTTON_PRESSED,
                        self.cb_button_pressed)
                    self.configure_custom_chars()
                except Error as e:
                    self.error_msg.showMessage('LCD 20x4 init failed: ' +
                                               str(e.description))
                    self.lcd = None
            elif device_identifier == AmbientLight.DEVICE_IDENTIFIER:
                try:
                    self.al = AmbientLight(uid, self.ipcon)
                    self.al.set_illuminance_callback_period(1000)
                    self.al.register_callback(self.al.CALLBACK_ILLUMINANCE,
                                              self.cb_illuminance)
                except Error as e:
                    self.error_msg.showMessage('Ambient Light init failed: ' +
                                               str(e.description))
                    self.al = None
            elif device_identifier == AmbientLightV2.DEVICE_IDENTIFIER:
                try:
                    self.al_v2 = AmbientLightV2(uid, self.ipcon)
                    self.al_v2.set_configuration(
                        AmbientLightV2.ILLUMINANCE_RANGE_64000LUX,
                        AmbientLightV2.INTEGRATION_TIME_200MS)
                    self.al_v2.set_illuminance_callback_period(1000)
                    self.al_v2.register_callback(
                        self.al_v2.CALLBACK_ILLUMINANCE,
                        self.cb_illuminance_v2)
                except Error as e:
                    self.error_msg.showMessage(
                        'Ambient Light 2.0 init failed: ' + str(e.description))
                    self.al = None
            elif device_identifier == Humidity.DEVICE_IDENTIFIER:
                try:
                    self.hum = Humidity(uid, self.ipcon)
                    self.hum.set_humidity_callback_period(1000)
                    self.hum.register_callback(self.hum.CALLBACK_HUMIDITY,
                                               self.cb_humidity)
                except Error as e:
                    self.error_msg.showMessage('Humidity init failed: ' +
                                               str(e.description))
                    self.hum = None
            elif device_identifier == Barometer.DEVICE_IDENTIFIER:
                try:
                    self.baro = Barometer(uid, self.ipcon)
                    self.baro.set_air_pressure_callback_period(1000)
                    self.baro.register_callback(
                        self.baro.CALLBACK_AIR_PRESSURE, self.cb_air_pressure)
                except Error as e:
                    self.error_msg.showMessage('Barometer init failed: ' +
                                               str(e.description))
                    self.baro = None

    def cb_connected(self, connected_reason):
        if connected_reason == IPConnection.CONNECT_REASON_AUTO_RECONNECT:

            while True:
                try:
                    self.ipcon.enumerate()
                    break
                except Error as e:
                    self.error_msg.showMessage('Enumerate Error: ' +
                                               str(e.description))
                    time.sleep(1)
예제 #41
0
    def __init__(self, *args):
        PluginBase.__init__(self, BrickStepper, *args)

        self.setupUi(self)

        self.stepper = self.device

        self.endis_all(False)

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.new_value = 0
        self.update_counter = 0

        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.decay_widget.hide()

        self.setting_sync_rect_checkbox = False

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.deceleration_syncer = SliderSpinSyncer(self.deceleration_slider,
                                                    self.deceleration_spin,
                                                    self.deceleration_changed)

        self.decay_syncer = SliderSpinSyncer(self.decay_slider,
                                             self.decay_spin,
                                             self.decay_changed)

        self.enable_checkbox.toggled.connect(self.enable_toggled)
        self.forward_button.clicked.connect(self.forward_clicked)
        self.stop_button.clicked.connect(self.stop_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.backward_button.clicked.connect(self.backward_clicked)
        self.to_button.clicked.connect(self.to_button_clicked)
        self.steps_button.clicked.connect(self.steps_button_clicked)
        self.motor_current_button.clicked.connect(
            self.motor_current_button_clicked)
        self.minimum_motor_voltage_button.clicked.connect(
            self.minimum_motor_voltage_button_clicked)
        self.sync_rect_checkbox.toggled.connect(self.sync_rect_toggled)

        self.mode_dropbox.currentIndexChanged.connect(self.mode_changed)

        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.stepper.register_callback(self.stepper.CALLBACK_POSITION_REACHED,
                                       self.qtcb_position_reached.emit)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.stepper.register_callback(self.stepper.CALLBACK_UNDER_VOLTAGE,
                                       self.qtcb_under_voltage.emit)

        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv = 0
        self.ev = 0
        self.mv = 0
        self.mod = 0

        if self.firmware_version >= (2, 3, 1):
            self.status_led_action = QAction('Status LED', self)
            self.status_led_action.setCheckable(True)
            self.status_led_action.toggled.connect(
                lambda checked: self.stepper.enable_status_led()
                if checked else self.stepper.disable_status_led())
            self.set_configs([(0, None, [self.status_led_action])])
        else:
            self.status_led_action = None

        if self.firmware_version >= (1, 1, 4):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.stepper.reset())
            self.set_actions([(0, None, [reset])])
예제 #42
0
class WeatherStation(QApplication):
    HOST = "localhost"
    PORT = 4223

    ipcon = None
    lcd = None
    al = None
    hum = None
    baro = None

    projects = []
    active_project = None

    error_msg = None

    def __init__(self, args):
        super(QApplication, self).__init__(args)

        self.error_msg = QErrorMessage()
        self.ipcon = IPConnection()

        signal.signal(signal.SIGINT, self.exit_demo)
        signal.signal(signal.SIGTERM, self.exit_demo)

        timer = QTimer(self)
        timer.setSingleShot(True)
        timer.timeout.connect(self.connect)
        timer.start(1)

    def exit_demo(self, signl=None, frme=None):
        try:
            self.ipcon.disconnect()
            self.timer.stop()
            self.tabs.destroy()
        except:
            pass

        sys.exit()

    def open_gui(self):
        self.main = MainWindow(self)
        self.main.setFixedSize(730, 430)
        self.main.setWindowIcon(QIcon(os.path.join(ProgramPath.program_path(), "demo-icon.png")))
        
        self.tabs = QTabWidget()
        
        widget = QWidget()
        layout = QVBoxLayout()
        layout.addWidget(self.tabs)
        widget.setLayout(layout)

        self.main.setCentralWidget(widget)
        
        self.projects.append(ProjectEnvDisplay(self.tabs, self))
        self.projects.append(ProjectStatistics(self.tabs, self))
        self.projects.append(ProjectXively(self.tabs, self))

        self.tabs.addTab(self.projects[0], "Display Environment Measurements")
        self.tabs.addTab(self.projects[1], "Show Statistics with Button Control")
        self.tabs.addTab(self.projects[2], "Connect to Xively")

        self.active_project = self.projects[0]

        self.tabs.currentChanged.connect(self.tabChangedSlot)

        self.main.setWindowTitle("Starter Kit: Weather Station Demo " + config.DEMO_VERSION)
        self.main.show()

    def connect(self):
        try:
            self.ipcon.connect(WeatherStation.HOST, WeatherStation.PORT)
        except Error as e:
            self.error_msg.showMessage('Connection Error: ' + str(e.description) + "\nBrickd installed and running?")
            return
        except socket.error as e:
            self.error_msg.showMessage('Socket error: ' + str(e) + "\nBrickd installed and running?")
            return

        self.ipcon.register_callback(IPConnection.CALLBACK_ENUMERATE,
                                     self.cb_enumerate)
        self.ipcon.register_callback(IPConnection.CALLBACK_CONNECTED,
                                     self.cb_connected)

        try:
            self.ipcon.enumerate()
        except Error as e:
            self.error_msg.showMessage('Enumerate Error: ' + str(e.description))
            return

        self.open_gui()

    def tabChangedSlot(self, tabIndex):

        if self.lcd is not None:
            self.lcd.clear_display()

        self.active_project = self.projects[tabIndex]

    def cb_illuminance(self, illuminance):
        for p in self.projects:
            p.update_illuminance(illuminance)

    def cb_humidity(self, humidity):
        for p in self.projects:
            p.update_humidity(humidity)

    def cb_air_pressure(self, air_pressure):
        for p in self.projects:
            p.update_air_pressure(air_pressure)

        try:
            temperature = self.baro.get_chip_temperature()
        except Error as e:
            print('Could not get temperature: ' + str(e.description))
            return

        for p in self.projects:
            p.update_temperature(temperature)

    def configure_custom_chars(self):
        c = [[0x00 for x in range(8)] for y in range(8)]
	
        c[0] = [0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff]
        c[1] = [0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff]
        c[2] = [0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff]
        c[3] = [0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff]
        c[4] = [0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff]
        c[5] = [0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]
        c[6] = [0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]
        c[7] = [0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]

        for i in range(len(c)):
            self.lcd.set_custom_character(i, c[i]);

    def cb_button_pressed(self, button):
        for p in self.projects:
            p.button_pressed(button)

    def cb_enumerate(self, uid, connected_uid, position, hardware_version,
                     firmware_version, device_identifier, enumeration_type):
        if enumeration_type == IPConnection.ENUMERATION_TYPE_CONNECTED or \
           enumeration_type == IPConnection.ENUMERATION_TYPE_AVAILABLE:
            if device_identifier == LCD20x4.DEVICE_IDENTIFIER:
                try:
                    self.lcd = LCD20x4(uid, self.ipcon)
                    self.lcd.clear_display()
                    self.lcd.backlight_on()
                    self.lcd.register_callback(self.lcd.CALLBACK_BUTTON_PRESSED, self.cb_button_pressed)
                    self.configure_custom_chars()

                except Error as e:
                    self.error_msg.showMessage('LCD 20x4 init failed: ' + str(e.description))
                    self.lcd = None
            elif device_identifier == AmbientLight.DEVICE_IDENTIFIER:
                try:
                    self.al = AmbientLight(uid, self.ipcon)
                    self.al.set_illuminance_callback_period(1000)
                    self.al.register_callback(self.al.CALLBACK_ILLUMINANCE,
                                              self.cb_illuminance)
                except Error as e:
                    self.error_msg.showMessage('Ambient Light init failed: ' + str(e.description))
                    self.al = None
            elif device_identifier == Humidity.DEVICE_IDENTIFIER:
                try:
                    self.hum = Humidity(uid, self.ipcon)
                    self.hum.set_humidity_callback_period(1000)
                    self.hum.register_callback(self.hum.CALLBACK_HUMIDITY,
                                               self.cb_humidity)
                except Error as e:
                    self.error_msg.showMessage('Humidity init failed: ' + str(e.description))
                    self.hum = None
            elif device_identifier == Barometer.DEVICE_IDENTIFIER:
                try:
                    self.baro = Barometer(uid, self.ipcon)
                    self.baro.set_air_pressure_callback_period(1000)
                    self.baro.register_callback(self.baro.CALLBACK_AIR_PRESSURE,
                                                self.cb_air_pressure)
                except Error as e:
                    self.error_msg.showMessage('Barometer init failed: ' + str(e.description))
                    self.baro = None

    def cb_connected(self, connected_reason):
        if connected_reason == IPConnection.CONNECT_REASON_AUTO_RECONNECT:

            while True:
                try:
                    self.ipcon.enumerate()
                    break
                except Error as e:
                    self.error_msg.showMessage('Enumerate Error: ' + str(e.description))
                    time.sleep(1)
예제 #43
0
class Editor(editor_base.EditorBase):
    """Representa el editor de texto que aparece en el panel derecho.

    El editor soporta autocompletado de código y resaltado de sintáxis.
    """

    # Señal es emitida cuando el Editor ejecuta codigo
    signal_ejecutando = QtCore.pyqtSignal()

    def __init__(self, main, interpreterLocals, consola_lanas,
                 ventana_interprete):
        super(Editor, self).__init__()
        self.cantidad_ejecuciones = 0
        self.consola_lanas = consola_lanas
        self.ventana_interprete = ventana_interprete
        self.ruta_del_archivo_actual = None
        self.interpreterLocals = interpreterLocals
        self.setLineWrapMode(QTextEdit.NoWrap)
        self._cambios_sin_guardar = False
        self.main = main
        self.nombre_de_archivo_sugerido = ""
        self.watcher = pilasengine.watcher.Watcher(
            None, self.cuando_cambia_archivo_de_forma_externa)

    def crear_archivo_inicial(self):
        dirpath = tempfile.mkdtemp()
        archivo_temporal = os.path.join(dirpath, "mi_juego.py")
        archivo = codecs.open(archivo_temporal, "w", 'utf-8')
        archivo.write(CODIGO_INICIAL)
        archivo.close()
        #print("Creando el archivo " + str(archivo_temporal))
        self.abrir_archivo_del_proyecto(archivo_temporal)

    def es_archivo_iniciar_sin_guardar(self):
        return self.nombre_de_archivo_sugerido == ""

    def crear_y_seleccionar_archivo(self, nombre):
        # Quita la extension si llega a tenerla.
        nombre = nombre.replace('.py', '')
        nombre += ".py"
        nombre_de_archivo = nombre

        if self.ruta_del_archivo_actual:
            base_path = os.path.abspath(
                os.path.dirname(self.ruta_del_archivo_actual))
            ruta = os.path.join(base_path, unicode(nombre_de_archivo))
        else:
            ruta = unicode(nombre_de_archivo)

        if os.path.exists(ruta):
            self._tmp_dialog = QErrorMessage(self)
            self._tmp_dialog.showMessage("Ya existe un archivo con ese nombre")
        else:
            self._crear_archivo_nuevo_en(ruta)

            self.cargar_contenido_desde_archivo(ruta)
            self.ruta_del_archivo_actual = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()

    def _crear_archivo_nuevo_en(self, ruta):
        fo = open(ruta, "wb")
        fo.write("# contenido")
        fo.close()

    def obtener_archivos_del_proyecto(self):
        base_path = os.path.dirname(self.nombre_de_archivo_sugerido)
        listado = os.listdir(base_path)

        return [x for x in listado if x.endswith('.py')]

    def keyPressEvent(self, event):
        "Atiene el evento de pulsación de tecla."
        self._cambios_sin_guardar = True

        # Permite usar tab como seleccionador de la palabra actual
        # en el popup de autocompletado.
        if event.key() in [Qt.Key_Tab]:
            if self.completer and self.completer.popup().isVisible():
                event.ignore()
                nuevo_evento = QKeyEvent(QKeyEvent.KeyPress, Qt.Key_Return,
                                         Qt.NoModifier)
                try:
                    if self.autocomplete(nuevo_evento):
                        return None
                except UnicodeEncodeError:
                    pass
                return None

        if editor_base.EditorBase.keyPressEvent(self, event):
            return None

        # Elimina los pares de caracteres especiales si los encuentra
        if event.key() == Qt.Key_Backspace:
            self._eliminar_pares_de_caracteres()
            self._borrar_un_grupo_de_espacios(event)

        if self.autocomplete(event):
            return None

        if event.key() == Qt.Key_Return:
            cursor = self.textCursor()
            block = self.document().findBlockByNumber(cursor.blockNumber())
            whitespace = re.match(r"(\s*)", unicode(block.text())).group(1)

            linea_anterior = str(block.text()[:])
            cantidad_espacios = linea_anterior.count(' ') / 4

            if linea_anterior[-1:] == ':':
                whitespace = '    ' * (cantidad_espacios + 1)
            else:
                whitespace = '    ' * (cantidad_espacios)

            QTextEdit.keyPressEvent(self, event)
            return self.insertPlainText(whitespace)

        return QTextEdit.keyPressEvent(self, event)

    def _borrar_un_grupo_de_espacios(self, event):
        cursor = self.textCursor()
        block = self.document().findBlockByNumber(cursor.blockNumber())
        whitespace = re.match(r"(.*)", unicode(block.text())).group(1)

        if whitespace.endswith('    '):
            QTextEdit.keyPressEvent(self, event)
            QTextEdit.keyPressEvent(self, event)
            QTextEdit.keyPressEvent(self, event)

    def tiene_cambios_sin_guardar(self):
        return self._cambios_sin_guardar

    def _get_current_line(self):
        "Obtiene la linea en donde se encuentra el cursor."
        tc = self.textCursor()
        tc.select(QTextCursor.LineUnderCursor)
        return tc.selectedText()

    def _get_position_in_block(self):
        tc = self.textCursor()
        position = tc.positionInBlock() - 1
        return position

    def cargar_contenido_desde_archivo(self, ruta):
        "Carga todo el contenido del archivo indicado por ruta."
        with codecs.open(unicode(ruta), 'r', 'utf-8') as archivo:
            contenido = archivo.read()
        self.setText(contenido)

        self.nombre_de_archivo_sugerido = ruta
        self._cambios_sin_guardar = False

    def abrir_dialogo_cargar_archivo(self):
        return QFileDialog.getOpenFileName(
            self,
            "Abrir Archivo",
            self.nombre_de_archivo_sugerido,
            "Archivos python (*.py)",
            options=QFileDialog.DontUseNativeDialog)

    def abrir_archivo_del_proyecto(self, nombre_de_archivo):
        if self.tiene_cambios_sin_guardar():
            if self.mensaje_guardar_cambios_abrir():
                if not self.guardar_contenido_con_dialogo():
                    return
            else:
                return

        if self.ruta_del_archivo_actual:
            base_path = os.path.dirname(self.ruta_del_archivo_actual)
            ruta = os.path.join(base_path, unicode(nombre_de_archivo))
        else:
            ruta = unicode(nombre_de_archivo)

        self.cargar_contenido_desde_archivo(ruta)
        self.ruta_del_archivo_actual = ruta
        self.watcher.cambiar_archivo_a_observar(ruta)
        self.ejecutar()
        self.main.actualizar_el_listado_de_archivos()

    def abrir_archivo_con_dialogo(self):
        if self.tiene_cambios_sin_guardar():
            if self.mensaje_guardar_cambios_abrir():
                if not self.guardar_contenido_con_dialogo():
                    return
            else:
                return

        ruta = self.abrir_dialogo_cargar_archivo()

        if ruta:
            ruta = unicode(ruta)
            self.cargar_contenido_desde_archivo(ruta)
            self.ruta_del_archivo_actual = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()

    def cuando_cambia_archivo_de_forma_externa(self):
        self.recargar_archivo_actual()

    def recargar_archivo_actual(self):
        if self.ruta_del_archivo_actual:
            self.cargar_contenido_desde_archivo(self.ruta_del_archivo_actual)
            self.ejecutar()

    def mensaje_guardar_cambios_abrir(self):
        """Realizar una consulta usando un cuadro de dialogo simple
        se utiliza cuando hay cambios sin guardar y se desea abrir un archivo.
        Retorna True si el usuario presiona el boton *Guardar*,
        Retorna False si el usuario presiona *No*."""
        titulo = u"¿Deseas guardar el contenido antes de abrir un archivo?"
        mensaje = u"El contenido se perdera sino los guardas"

        mensaje = QMessageBox.question(self, titulo, mensaje, "Guardar", "No")

        return (not mensaje)

    def mensaje_guardar_cambios_salir(self):
        """Realizar una consulta usando un cuadro de dialogo simple
        se utiliza cuando hay cambios sin guardar y se desa salir del Editor.
        Retorna 0 si el usuario presiona el boton *Salir sin guardar*,
        Retorna 1 si el usuario presiona *Guardar*
        Retorna 2 si presiona *Cancelar*."""

        titulo = u"¿Deseas guardar el contenido antes de salir?"
        mensaje = u"El contenido se perdera sino los guardas"

        return QMessageBox.question(self, titulo, mensaje, "Salir sin guardar",
                                    "Guardar", "Cancelar")

    def marcar_error_en_la_linea(self, numero, descripcion):
        hi_selection = QTextEdit.ExtraSelection()

        hi_selection.format.setBackground(QColor(255, 220, 220))
        hi_selection.format.setProperty(QTextFormat.FullWidthSelection,
                                        QVariant(True))
        hi_selection.cursor = self.textCursor()
        posicion_linea = self.document().findBlockByLineNumber(
            numero).position()
        hi_selection.cursor.setPosition(posicion_linea)
        hi_selection.cursor.clearSelection()

        self.setExtraSelections([hi_selection])

    def guardar_contenido_con_dialogo(self):
        ruta = self.abrir_dialogo_guardar_archivo()

        if not ruta:
            return False

        ruta = unicode(ruta)

        if not ruta.endswith('.py'):
            ruta += '.py'

        if ruta:
            self.guardar_contenido_en_el_archivo(ruta)
            self._cambios_sin_guardar = False
            self.ruta_del_archivo_actual = ruta
            self.nombre_de_archivo_sugerido = ruta
            self.watcher.cambiar_archivo_a_observar(ruta)
            self.cargar_contenido_desde_archivo(ruta)
            self.ejecutar()
            self.main.actualizar_el_listado_de_archivos()
            self.main.habilitar_boton_nuevo()
            return True

    def guardar_contenido_directamente(self):
        if self.nombre_de_archivo_sugerido:
            self.guardar_contenido_en_el_archivo(
                self.nombre_de_archivo_sugerido)
            self._cambios_sin_guardar = False
            self.main.actualizar_el_listado_de_archivos()
            self.prevenir_live_reload()
        else:
            self.guardar_contenido_con_dialogo()

    def prevenir_live_reload(self):
        self.watcher.prevenir_reinicio()

    def salir(self):
        """Retorna True si puede salir y False si no"""
        if self.tiene_cambios_sin_guardar():
            mensaje = self.mensaje_guardar_cambios_salir()
            if mensaje == 1:
                self.guardar_contenido_con_dialogo()
            elif mensaje == 2:
                return False

        return True

    def obtener_contenido(self):
        return unicode(self.document().toPlainText())

    def ejecutar(self):
        ruta_personalizada = os.path.dirname(self.ruta_del_archivo_actual)
        #print "ejecutando texto desde widget editor"
        texto = self.obtener_contenido()
        #texto = self.editor.obtener_texto_sanitizado(self)
        # elimina cabecera de encoding.
        contenido = re.sub('coding\s*:\s*', '', texto)
        contenido = contenido.replace('import pilasengine', '')
        contenido = contenido.replace('pilas = pilasengine.iniciar',
                                      'pilas.reiniciar')

        for x in contenido.split('\n'):
            if "__file__" in x:
                contenido = contenido.replace(x, "# livecoding: " + x + "\n")

        sys.path.append(ruta_personalizada)
        self.interpreterLocals['sys'] = sys

        # Muchos códigos personalizados necesitan cargar imágenes o sonidos
        # desde el directorio que contiene al archivo. Para hacer esto posible,
        # se llama a la función "pilas.utils.agregar_ruta_personalizada" con el
        # path al directorio que representa el script. Así la función "obtener_ruta_al_recurso"
        # puede evaluar al directorio del script en busca de recursos también.
        if ruta_personalizada:
            ruta_personalizada = ruta_personalizada.replace('\\', '/')
            agregar_ruta_personalizada = 'pilas.utils.agregar_ruta_personalizada("%s")' % (
                ruta_personalizada)
            contenido = contenido.replace(
                'pilas.reiniciar(',
                agregar_ruta_personalizada + '\n' + 'pilas.reiniciar(')

        modulos_a_recargar = [
            x for x in self.interpreterLocals.values()
            if inspect.ismodule(x) and x.__name__ not in
            ['pilasengine', 'inspect'] and 'pilasengine.' not in x.__name__
        ]

        for m in modulos_a_recargar:
            reload(m)

        self.cantidad_ejecuciones += 1

        # Limpia la consola a partir de la primer ejecucion luego de iniciar.
        if self.cantidad_ejecuciones > 1:
            self.main.limpiar_interprete()

        try:
            exec(contenido, self.interpreterLocals)
        except Exception, e:
            self.consola_lanas.insertar_error_desde_exception(e)
            self.ventana_interprete.mostrar_el_interprete()
            #self.marcar_error_en_la_linea(10, "pepepe")

        self.signal_ejecutando.emit()
예제 #44
0
class Stepper(PluginBase, Ui_Stepper):
    qtcb_position_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)
    
    def __init__(self, *args):
        PluginBase.__init__(self, BrickStepper, *args)

        self.setupUi(self)
     
        self.stepper = self.device
     
        self.endis_all(False)
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.decay_widget.hide()

        self.setting_sync_rect_checkbox = False

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.deceleration_syncer = SliderSpinSyncer(self.deceleration_slider,
                                                    self.deceleration_spin,
                                                    self.deceleration_changed)

        self.decay_syncer = SliderSpinSyncer(self.decay_slider,
                                             self.decay_spin,
                                             self.decay_changed)

        self.enable_checkbox.toggled.connect(self.enable_toggled)
        self.forward_button.clicked.connect(self.forward_clicked)
        self.stop_button.clicked.connect(self.stop_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.backward_button.clicked.connect(self.backward_clicked)
        self.to_button.clicked.connect(self.to_button_clicked)
        self.steps_button.clicked.connect(self.steps_button_clicked)
        self.motor_current_button.clicked.connect(self.motor_current_button_clicked)
        self.minimum_motor_voltage_button.clicked.connect(self.minimum_motor_voltage_button_clicked)
        self.sync_rect_checkbox.toggled.connect(self.sync_rect_toggled)
        
        self.mode_dropbox.currentIndexChanged.connect(self.mode_changed)
        
        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.stepper.register_callback(self.stepper.CALLBACK_POSITION_REACHED, 
                                       self.qtcb_position_reached.emit)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.stepper.register_callback(self.stepper.CALLBACK_UNDER_VOLTAGE, 
                                       self.qtcb_under_voltage.emit)

        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv  = 0
        self.ev  = 0
        self.mv  = 0
        self.mod = 0

        if self.firmware_version >= (1, 1, 4):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.stepper.reset())
            self.set_actions(reset)
        
    def start(self):
        self.update_timer.start(100)
        self.update_start()
        
    def stop(self):
        self.update_timer.stop()

    def destroy(self):
        pass

    def get_url_part(self):
        return 'stepper'

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickStepper.DEVICE_IDENTIFIER
    
    def cb_position_reached(self, position):
        self.position_update(position)
        self.endis_all(True)
            
    def disable_list(self, button_list):
        for button in button_list:
            button.setEnabled(False)
        
    def endis_all(self, value):
        self.forward_button.setEnabled(value)
        self.stop_button.setEnabled(value)
        self.backward_button.setEnabled(value)
        self.to_button.setEnabled(value)
        self.steps_button.setEnabled(value)
        self.full_brake_button.setEnabled(value)
        
    def mode_changed(self, index):
        try:
            self.stepper.set_step_mode(1 << index)
            self.mod = 1 << index
        except ip_connection.Error:
            return
        
    def forward_clicked(self):
        try:
            self.stepper.drive_forward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])
        
    def backward_clicked(self):
        try:
            self.stepper.drive_backward()
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, self.steps_button])
        
    def stop_clicked(self):
        try:
            self.stepper.stop()
        except ip_connection.Error:
            return
        self.endis_all(True)
        
    def full_brake_clicked(self):
        try:
            self.stepper.full_brake()
        except ip_connection.Error:
            return
        self.endis_all(True)
        
    def to_button_clicked(self):
        drive_to = self.to_spin.value()
        try:
            self.stepper.set_target_position(drive_to)
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, 
                           self.steps_button, 
                           self.forward_button,
                           self.backward_button])
        
    def steps_button_clicked(self):
        drive_steps = self.steps_spin.value()
        try:
            self.stepper.set_steps(drive_steps)
        except ip_connection.Error:
            return
        self.disable_list([self.to_button, 
                           self.steps_button, 
                           self.forward_button,
                           self.backward_button])
        
    def motor_current_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(2500)
        qid.setIntStep(100)
        async_call(self.stepper.get_motor_current, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.motor_current_selected)
        qid.setLabelText("Choose motor current in mA.")
#                         "<font color=red>Setting this too high can destroy your Motor.</font>")
        qid.open()
        
    def minimum_motor_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(0)
        qid.setIntMaximum(40000)
        qid.setIntStep(100)
        async_call(self.stepper.get_minimum_voltage, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_motor_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()
        
    def motor_current_selected(self, value):
        try:
            self.stepper.set_motor_current(value)
        except ip_connection.Error:
            return
        
    def minimum_motor_voltage_selected(self, value):
        try:
            self.stepper.set_minimum_voltage(value)
        except ip_connection.Error:
            return
        
    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV" % round(ov/1000.0, 1)
        if not self.qem.isVisible():
            self.qem.showMessage("Under Voltage: Output Voltage of " + ov_str +
                                 " is below minimum voltage of " + mv_str,
                                 "Stepper_UnderVoltage")

    def enable_toggled(self, checked):
        try:
            if checked:
                if not self.stepper.is_enabled():
                    self.endis_all(True)
                    self.stepper.enable()
            else:
                if self.stepper.is_enabled():
                    self.endis_all(False)
                    self.stepper.disable()
        except ip_connection.Error:
            return

    def sync_rect_toggled(self, checked):
        if not self.setting_sync_rect_checkbox and checked:
            rc = QMessageBox.warning(get_main_window(), 'Synchronous Rectification',
                                     'If you want to use high speeds (> 10000 steps/s) for a large stepper motor with a ' +
                                     'large inductivity we strongly suggest that you do not enable synchronous rectification. ' +
                                     'Otherwise the Brick may not be able to cope with the load and overheat.',
                                     QMessageBox.Ok | QMessageBox.Cancel)

            if rc != QMessageBox.Ok:
                self.sync_rect_checkbox.setChecked(False)
                return

        try:
            self.stepper.set_sync_rect(checked)
        except ip_connection.Error:
            return

        self.decay_widget.setVisible(checked)

    def stack_input_voltage_update(self, sv):
        sv_str = "%gV"  % round(sv/1000.0, 1)
        self.stack_voltage_label.setText(sv_str)
        
    def external_input_voltage_update(self, ev):
        ev_str = "%gV"  % round(ev/1000.0, 1)
        self.external_voltage_label.setText(ev_str)
        
    def minimum_voltage_update(self, mv):
        mv_str = "%gV"  % round(mv/1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)
        
    def maximum_current_update(self, cur):
        cur_str = "%gA"  % round(cur/1000.0, 1)
        self.maximum_current_label.setText(cur_str)
        
    def position_update(self, pos):
        pos_str = "%d" % pos
        self.position_label.setText(pos_str)
        
    def remaining_steps_update(self, ste):
        ste_str = "%d" % ste
        self.remaining_steps_label.setText(ste_str)
        
    def current_velocity_update(self, velocity):
        velocity_str = "%d" % velocity
        self.current_velocity_label.setText(velocity_str)
        self.speedometer.set_velocity(velocity)

    def mode_update(self, mod):
        if mod == 8:
            index = 3
        elif mod == 4:
            index = 2
        elif mod == 2:
            index = 1
        else:
            index = 0
            
        self.mode_dropbox.setCurrentIndex(index)
        
    def get_max_velocity_async(self, velocity):
        if not self.velocity_slider.isSliderDown():
            if velocity != self.velocity_slider.sliderPosition():
                self.velocity_slider.setSliderPosition(velocity)
                self.velocity_spin.setValue(velocity)
        
    def get_speed_ramping_async(self, ramp):
        acc, dec = ramp
        if not self.acceleration_slider.isSliderDown() and \
           not self.deceleration_slider.isSliderDown():
            if acc != self.acceleration_slider.sliderPosition():
                self.acceleration_slider.setSliderPosition(acc)
                self.acceleration_spin.setValue(acc)
            if dec != self.deceleration_slider.sliderPosition():
                self.deceleration_slider.setSliderPosition(dec)
                self.deceleration_spin.setValue(dec)

    def get_decay_async(self, decay):
        if not self.decay_slider.isSliderDown():
            if decay != self.decay_slider.sliderPosition():
                self.decay_slider.setSliderPosition(decay)
                self.decay_spin.setValue(decay)
        
    def is_enabled_async(self, enabled):
        if enabled:
            if not self.enable_checkbox.isChecked():
                self.endis_all(True)
                self.enable_checkbox.setChecked(True)
        else:
            if self.enable_checkbox.isChecked():
                self.endis_all(False)
                self.enable_checkbox.setChecked(False)

    def is_sync_rect_async(self, sync_rect):
        self.setting_sync_rect_checkbox = True
        self.sync_rect_checkbox.setChecked(sync_rect)
        self.setting_sync_rect_checkbox = False

    def update_start(self):
        async_call(self.stepper.get_max_velocity, None, self.get_max_velocity_async, self.increase_error_count)
        async_call(self.stepper.get_speed_ramping, None, self.get_speed_ramping_async, self.increase_error_count)
        async_call(self.stepper.get_decay, None, self.get_decay_async, self.increase_error_count)
        async_call(self.stepper.is_enabled, None, self.is_enabled_async, self.increase_error_count)
        async_call(self.stepper.is_sync_rect, None, self.is_sync_rect_async, self.increase_error_count)

    def update_data(self):
        async_call(self.stepper.get_remaining_steps, None, self.remaining_steps_update, self.increase_error_count)
        async_call(self.stepper.get_current_position, None, self.position_update, self.increase_error_count)
        async_call(self.stepper.get_current_velocity, None, self.current_velocity_update, self.increase_error_count)

        self.update_counter += 1
        if self.update_counter % 10 == 0:
            async_call(self.stepper.get_motor_current, None, self.maximum_current_update, self.increase_error_count)
            async_call(self.stepper.get_stack_input_voltage, None, self.stack_input_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_external_input_voltage, None, self.external_input_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_minimum_voltage, None, self.minimum_voltage_update, self.increase_error_count)
            async_call(self.stepper.get_step_mode, None, self.mode_update, self.increase_error_count)

    def velocity_changed(self, value):
        try:
            self.stepper.set_max_velocity(value)
        except ip_connection.Error:
            return

    def acceleration_changed(self, value):
        dec = self.deceleration_spin.value()
        try:
            self.stepper.set_speed_ramping(value, dec)
        except ip_connection.Error:
            return
            
    def deceleration_changed(self, value):
        acc = self.acceleration_slider.value()
        try:
            self.stepper.set_speed_ramping(acc, value)
        except ip_connection.Error:
            return

    def decay_changed(self, value):
        try:
            self.stepper.set_decay(value)
        except ip_connection.Error:
            return
예제 #45
0
class Servo(PluginBase, Ui_Servo):
    qtcb_under_voltage = pyqtSignal(int)

    def __init__(self, *args):
        PluginBase.__init__(self, BrickServo, *args)

        self.setupUi(self)

        self.servo = self.device

        self.position_list = []
        self.velocity_list = []
        self.acceleration_list = []
        self.enable_list = []

        self.up_cur = 0
        self.up_siv = 0
        self.up_eiv = 0
        self.up_opv = 0
        self.up_mv = 0

        self.up_ena = [0] * 7
        self.up_pos = [0] * 7
        self.up_vel = [0] * 7
        self.up_acc = [0] * 7

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_apply)
        self.update_timer.setInterval(50)

        self.alive = True

        for i in range(1, 8):
            label = QLabel()
            label.setText('Off')
            self.enable_list.append(label)
            self.status_grid.addWidget(label, i, 1)

        for i in range(1, 8):
            pk = PositionKnob()
            self.position_list.append(pk)
            self.status_grid.addWidget(pk, i, 2)

        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.velocity_list.append(cb)
            self.status_grid.addWidget(cb, i, 3)

        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.acceleration_list.append(cb)
            self.status_grid.addWidget(cb, i, 4)

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.test_button.clicked.connect(self.test_button_clicked)
        self.output_voltage_button.clicked.connect(
            self.output_voltage_button_clicked)

        self.servo_dropbox.currentIndexChanged.connect(
            lambda x: self.update_servo_specific())
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)

        self.position_syncer = SliderSpinSyncer(self.position_slider,
                                                self.position_spin,
                                                self.position_changed)

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.period_syncer = SliderSpinSyncer(self.period_slider,
                                              self.period_spin,
                                              self.period_changed)

        self.pulse_width_min_spin.editingFinished.connect(
            self.pulse_width_spin_finished)
        self.pulse_width_max_spin.editingFinished.connect(
            self.pulse_width_spin_finished)
        self.degree_min_spin.editingFinished.connect(self.degree_spin_finished)
        self.degree_max_spin.editingFinished.connect(self.degree_spin_finished)

        self.minimum_voltage_button.clicked.connect(
            self.minimum_voltage_button_clicked)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.servo.register_callback(self.servo.CALLBACK_UNDER_VOLTAGE,
                                     self.qtcb_under_voltage.emit)

        class WorkerThread(QThread):
            def __init__(self, parent=None, func=None):
                QThread.__init__(self, parent)
                self.func = func

            def run(self):
                self.func()

        self.test_event = Event()
        self.test_thread_object = WorkerThread(self, self.test_thread)
        self.update_event = Event()
        self.update_thread_object = WorkerThread(self, self.update_thread)

        self.update_thread_first_time = False

        self.update_done_event = Event()
        self.update_done_event.set()

        if self.firmware_version >= (2, 3, 1):
            self.status_led_action = QAction('Status LED', self)
            self.status_led_action.setCheckable(True)
            self.status_led_action.toggled.connect(
                lambda checked: self.servo.enable_status_led()
                if checked else self.servo.disable_status_led())
            self.set_configs([(0, None, [self.status_led_action])])
        else:
            self.status_led_action = None

        if self.firmware_version >= (1, 1, 3):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.servo.reset())
            self.set_actions([(0, None, [reset])])

    def start(self):
        if self.firmware_version >= (2, 3, 1):
            async_call(self.servo.is_status_led_enabled, None,
                       self.status_led_action.setChecked,
                       self.increase_error_count)

        self.alive = True
        self.test_event.clear()
        self.update_done_event.set()
        self.update_event.set()

        if not self.test_thread_object.isRunning():
            self.test_thread_object.start()

        if not self.update_thread_object.isRunning():
            self.update_thread_object.start()

        self.update_servo_specific()

        self.update_timer.start()

    def stop(self):
        if self.test_button.text() == "Stop Test":
            self.test_button_clicked()

        self.update_timer.stop()

        self.update_event.clear()
        self.alive = False
        self.update_done_event.wait()

    def destroy(self):
        self.test_event.set()
        self.update_event.set()

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickServo.DEVICE_IDENTIFIER

    def get_period_async(self, per):
        self.period_spin.setValue(per)
        self.period_slider.setValue(per)

    def is_enabled_async(self, ena):
        self.enable_checkbox.setChecked(ena)

    def get_position_async(self, pos):
        self.position_spin.setValue(pos)
        self.position_slider.setValue(pos)

    def get_velocity_async(self, vel):
        self.velocity_spin.setValue(vel)
        self.velocity_slider.setValue(vel)

    def get_acceleration_async(self, acc):
        self.acceleration_spin.setValue(acc)
        self.acceleration_slider.setValue(acc)

    def get_degree_async(self, deg, i):
        deg_min, deg_max = deg

        self.degree_min_spin.setValue(deg_min)
        self.degree_max_spin.setValue(deg_max)

        self.position_slider.setMinimum(deg_min)
        self.position_slider.setMaximum(deg_max)
        self.position_spin.setMinimum(deg_min)
        self.position_spin.setMaximum(deg_max)

        self.position_list[i].set_total_angle((deg_max - deg_min) / 100)
        self.position_list[i].set_range(deg_min / 100, deg_max / 100)

    def get_pulse_width_async(self, pulse):
        pulse_min, pulse_max = pulse
        self.pulse_width_min_spin.setValue(pulse_min)
        self.pulse_width_max_spin.setValue(pulse_max)

    def update_servo_specific(self):
        i = self.selected_servo()
        if i == 255:
            self.enable_checkbox.setChecked(False)
            return

        async_call(self.servo.get_position, i, self.get_position_async,
                   self.increase_error_count)
        async_call(self.servo.get_velocity, i, self.get_velocity_async,
                   self.increase_error_count)
        async_call(self.servo.get_acceleration, i, self.get_acceleration_async,
                   self.increase_error_count)
        async_call(self.servo.get_period, i, self.get_period_async,
                   self.increase_error_count)
        async_call(self.servo.is_enabled, i, self.is_enabled_async,
                   self.increase_error_count)

        def get_lambda_deg(i):
            return lambda x: self.get_degree_async(x, i)

        async_call(self.servo.get_degree, i, get_lambda_deg(i),
                   self.increase_error_count)
        async_call(self.servo.get_pulse_width, i, self.get_pulse_width_async,
                   self.increase_error_count)

    def error_handler(self, error):
        pass

    def servo_current_update(self, value):
        self.current_label.setText(str(value) + "mA")

    def stack_input_voltage_update(self, sv):
        sv_str = "%gV" % round(sv / 1000.0, 1)
        self.stack_voltage_label.setText(sv_str)

    def external_input_voltage_update(self, ev):
        ev_str = "%gV" % round(ev / 1000.0, 1)
        self.external_voltage_label.setText(ev_str)

    def output_voltage_update(self, ov):
        ov_str = "%gV" % round(ov / 1000.0, 1)
        self.output_voltage_label.setText(ov_str)

    def minimum_voltage_update(self, mv):
        mv_str = "%gV" % round(mv / 1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)

    def position_update(self, i, pos):
        self.position_list[i].set_value(pos / 100)

    def velocity_update(self, i, vel):
        self.velocity_list[i].set_height(vel * 100 / 0xFFFF)

    def acceleration_update(self, i, acc):
        self.acceleration_list[i].set_height(acc * 100 / 0xFFFF)

    def deactivate_servo(self, i):
        if self.enable_list[i].text() != 'Off':
            self.velocity_list[i].grey()
            self.acceleration_list[i].grey()

    def activate_servo(self, i):
        if self.enable_list[i].text() != 'On':
            self.velocity_list[i].color()
            self.acceleration_list[i].color()

    def selected_servo(self):
        try:
            return int(self.servo_dropbox.currentText()[-1:])
        except:
            return 255

    def enable_state_changed(self, state):
        s = self.selected_servo()
        try:
            if state == Qt.Checked:
                self.servo.enable(s)
            elif state == Qt.Unchecked:
                self.servo.disable(s)
        except ip_connection.Error:
            return

    def update_apply(self):
        if not self.update_thread_first_time:
            return

        self.servo_current_update(self.up_cur)
        self.stack_input_voltage_update(self.up_siv)
        self.external_input_voltage_update(self.up_eiv)
        self.output_voltage_update(self.up_opv)
        self.minimum_voltage_update(self.up_mv)
        for i in range(7):
            if self.up_ena[i]:
                self.activate_servo(i)

                self.position_update(i, self.up_pos[i])
                self.velocity_update(i, self.up_vel[i])
                self.acceleration_update(i, self.up_acc[i])

                self.enable_list[i].setText('On')
            else:
                self.deactivate_servo(i)
                self.enable_list[i].setText('Off')

    def update_thread(self):
        while self.alive:
            time.sleep(0.1)

            try:
                servo = self.selected_servo()
                if servo == 255:
                    self.up_cur = self.servo.get_overall_current()
                else:
                    self.up_cur = self.servo.get_servo_current(servo)

                self.up_siv = self.servo.get_stack_input_voltage()
                self.up_eiv = self.servo.get_external_input_voltage()
                self.up_opv = self.servo.get_output_voltage()
                self.up_mv = self.servo.get_minimum_voltage()

                for i in range(7):
                    self.up_ena[i] = self.servo.is_enabled(i)
                    if self.up_ena[i]:
                        self.activate_servo(i)
                        self.up_pos[i] = self.servo.get_current_position(i)
                        self.up_vel[i] = self.servo.get_current_velocity(i)
                        self.up_acc[i] = self.servo.get_acceleration(i)

                #self.update_apply()

                self.update_done_event.set()
                self.update_event.wait()
                self.update_done_event.clear()
            except ip_connection.Error:
                pass

            self.update_thread_first_time = True

        self.update_done_event.set()

    def test_thread(self):
        def test(num, ena, acc, vel, pos):
            if not self.alive:
                return

            try:
                if ena:
                    self.servo.enable(num)
                else:
                    self.servo.disable(num)
                self.servo.set_acceleration(num, acc)
                self.servo.set_velocity(num, vel)
                self.servo.set_position(num, pos)
            except ip_connection.Error:
                return

        def random_test():
            for i in range(7):
                test(i, random.randrange(0, 2), random.randrange(0, 65536),
                     random.randrange(0, 65536), random.randrange(-9000, 9001))

        while self.alive:
            self.test_event.wait()
            if not self.alive:
                return

            # Full Speed left for 2 seconds
            for i in range(7):
                test(i, True, 65535, 65535, 9000)
            time.sleep(2)
            self.test_event.wait()
            if not self.alive:
                return

            # Full Speed right for 2 seconds
            for i in range(7):
                test(i, True, 65535, 65535, -9000)
            time.sleep(2)
            self.test_event.wait()
            if not self.alive:
                return

            # Test different speeds
            for i in range(19):
                for j in range(7):
                    test(j, True, 65535, 65535 * i / 18, -9000 + i * 1000)
                time.sleep(0.1)
                self.test_event.wait()
                if not self.alive:
                    return
            time.sleep(1)
            self.test_event.wait()
            if not self.alive:
                return

            # Test acceleration
            for i in range(7):
                test(i, True, 100, 65535, -9000)

            time.sleep(3)
            self.test_event.wait()
            if not self.alive:
                return

            # Random for 3 seconds
            random_test()
            time.sleep(3)

    def test_button_clicked(self):
        if self.test_button.text() == "Start Test":
            self.test_button.setText("Stop Test")
            self.test_event.set()
        else:
            self.test_button.setText("Start Test")
            self.test_event.clear()

    def output_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(2000)
        qid.setIntMaximum(9000)
        qid.setIntStep(100)
        async_call(self.servo.get_output_voltage, None, qid.setIntValue,
                   self.increase_error_count)
        qid.intValueSelected.connect(self.output_voltage_selected)
        qid.setLabelText("Choose Output Voltage in mV.")
        #                         "<font color=red>Setting this too high can destroy your servo.</font>")
        qid.open()

    def output_voltage_selected(self, value):
        try:
            self.servo.set_output_voltage(value)
        except ip_connection.Error:
            return

    def position_changed(self, value):
        try:
            self.servo.set_position(self.selected_servo(), value)
        except ip_connection.Error:
            return

    def velocity_changed(self, value):
        try:
            self.servo.set_velocity(self.selected_servo(), value)
        except ip_connection.Error:
            return

    def acceleration_changed(self, value):
        try:
            self.servo.set_acceleration(self.selected_servo(), value)
        except ip_connection.Error:
            return

    def period_changed(self, value):
        try:
            self.servo.set_period(self.selected_servo(), value)
        except ip_connection.Error:
            return

    def pulse_width_spin_finished(self):
        try:
            self.servo.set_pulse_width(self.selected_servo(),
                                       self.pulse_width_min_spin.value(),
                                       self.pulse_width_max_spin.value())
        except ip_connection.Error:
            return

    def degree_spin_finished(self):
        min = self.degree_min_spin.value()
        max = self.degree_max_spin.value()
        servo = self.selected_servo()

        self.position_slider.setMinimum(min)
        self.position_slider.setMaximum(max)
        self.position_spin.setMinimum(min)
        self.position_spin.setMaximum(max)
        if servo == 255:
            for i in range(7):
                self.position_list[i].set_total_angle((max - min) / 100)
                self.position_list[i].set_range(min / 100, max / 100)
        else:
            self.position_list[servo].set_total_angle((max - min) / 100)
            self.position_list[servo].set_range(min / 100, max / 100)

        try:
            self.servo.set_degree(servo, min, max)
        except ip_connection.Error:
            return

    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV" % round(ov / 1000.0, 1)
        if not self.qem.isVisible():
            self.qem.showMessage(
                "Under Voltage: Output Voltage of " + ov_str +
                " is below minimum voltage of " + mv_str, "Servo_UnterVoltage")

    def minimum_voltage_selected(self, value):
        try:
            self.servo.set_minimum_voltage(value)
        except ip_connection.Error:
            return

    def minimum_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(5000)
        qid.setIntMaximum(0xFFFF)
        qid.setIntStep(100)
        async_call(self.servo.get_minimum_voltage, None, qid.setIntValue,
                   self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_voltage_selected)
        qid.setLabelText("Choose minimum servo voltage in mV.")
        qid.open()
예제 #46
0
파일: servo.py 프로젝트: smunix/brickv
    def __init__(self, ipcon, uid):
        PluginBase.__init__(self, ipcon, uid)
        self.setupUi(self)

        self.servo = brick_servo.Servo(self.uid)
        self.device = self.servo
        self.ipcon.add_device(self.servo)
        self.version = '.'.join(map(str, self.servo.get_version()[1]))

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_apply)
        self.update_timer.setInterval(0)
        self.update_timer.setSingleShot(True)

        layout = QVBoxLayout(self)
        layout.addWidget(QLabel('Servo'))
        self.position_list = []
        self.velocity_list = []
        self.acceleration_list = []
        self.enable_list = []

        self.up_ena = [0] * 7
        self.up_pos = [0] * 7
        self.up_vel = [0] * 7
        self.up_acc = [0] * 7

        self.alive = True

        for i in range(1, 8):
            label = QLabel()
            label.setText('Off')
            self.enable_list.append(label)
            self.status_grid.addWidget(label, i, 1)

        for i in range(1, 8):
            pk = PositionKnob()
            self.position_list.append(pk)
            self.status_grid.addWidget(pk, i, 2)

        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.velocity_list.append(cb)
            self.status_grid.addWidget(cb, i, 3)

        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.acceleration_list.append(cb)
            self.status_grid.addWidget(cb, i, 4)

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.test_button.clicked.connect(self.test_button_clicked)
        self.output_voltage_button.clicked.connect(
            self.output_voltage_button_clicked)

        self.servo_dropbox.currentIndexChanged.connect(
            lambda x: self.update_servo_specific())
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)

        self.position_slider.sliderReleased.connect(
            self.position_slider_released)
        self.position_slider.valueChanged.connect(self.position_spin.setValue)
        self.position_spin.editingFinished.connect(self.position_spin_finished)

        self.velocity_slider.sliderReleased.connect(
            self.velocity_slider_released)
        self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
        self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)

        self.acceleration_slider.sliderReleased.connect(
            self.acceleration_slider_released)
        self.acceleration_slider.valueChanged.connect(
            self.acceleration_spin.setValue)
        self.acceleration_spin.editingFinished.connect(
            self.acceleration_spin_finished)

        self.period_slider.sliderReleased.connect(self.period_slider_released)
        self.period_slider.valueChanged.connect(self.period_spin.setValue)
        self.period_spin.editingFinished.connect(self.period_spin_finished)

        self.pulse_width_min_spin.editingFinished.connect(
            self.pulse_width_spin_finished)
        self.pulse_width_max_spin.editingFinished.connect(
            self.pulse_width_spin_finished)
        self.degree_min_spin.editingFinished.connect(self.degree_spin_finished)
        self.degree_max_spin.editingFinished.connect(self.degree_spin_finished)

        self.minimum_voltage_button.pressed.connect(
            self.minimum_voltage_button_pressed)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.servo.register_callback(self.servo.CALLBACK_UNDER_VOLTAGE,
                                     self.qtcb_under_voltage.emit)

        class WorkerThread(QThread):
            def __init__(self, parent=None, func=None):
                QThread.__init__(self, parent)
                self.func = func

            def run(self):
                self.func()

        self.test_event = Event()
        self.test_thread_object = WorkerThread(self, self.test_thread)
        self.update_event = Event()
        self.update_thread_object = WorkerThread(self, self.update_thread)

        self.update_done_event = Event()
        self.update_done_event.set()
예제 #47
0
파일: main.py 프로젝트: NoxDineen/calibre
    except socket.error:  # Good si is correct (on UNIX)
        otherinstance = True
    else:
        # On windows only singleinstance can be trusted
        otherinstance = True if iswindows else False
    if not otherinstance and not opts.shutdown_running_calibre:
        return run_gui(opts, args, listener, app, gui_debug=gui_debug)

    communicate(opts, args)

    return 0


if __name__ == "__main__":
    try:
        sys.exit(main())
    except Exception as err:
        if not iswindows:
            raise
        tb = traceback.format_exc()
        from PyQt4.QtGui import QErrorMessage

        logfile = os.path.join(os.path.expanduser("~"), "calibre.log")
        if os.path.exists(logfile):
            log = open(logfile).read().decode("utf-8", "ignore")
            d = QErrorMessage()
            d.showMessage(
                ("<b>Error:</b>%s<br><b>Traceback:</b><br>" "%s<b>Log:</b><br>%s")
                % (unicode(err), unicode(tb).replace("\n", "<br>"), log.replace("\n", "<br>"))
            )
예제 #48
0
파일: servo.py 프로젝트: smunix/brickv
class Servo(PluginBase, Ui_Servo):
    qtcb_under_voltage = pyqtSignal(int)
    
    def __init__ (self, ipcon, uid):
        PluginBase.__init__(self, ipcon, uid)
        self.setupUi(self)
        
        self.servo = brick_servo.Servo(self.uid)
        self.device = self.servo
        self.ipcon.add_device(self.servo)
        self.version = '.'.join(map(str, self.servo.get_version()[1]))
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_apply)
        self.update_timer.setInterval(0)
        self.update_timer.setSingleShot(True)
        
        layout = QVBoxLayout(self)
        layout.addWidget(QLabel('Servo'))
        self.position_list = []
        self.velocity_list = []
        self.acceleration_list = []
        self.enable_list = []
        
        self.up_ena = [0]*7
        self.up_pos = [0]*7
        self.up_vel = [0]*7
        self.up_acc = [0]*7
        
        self.alive = True
        
        for i in range(1, 8):
            label = QLabel()
            label.setText('Off')
            self.enable_list.append(label)
            self.status_grid.addWidget(label, i, 1)
            
        for i in range(1, 8):
            pk = PositionKnob()
            self.position_list.append(pk)
            self.status_grid.addWidget(pk, i, 2)
            
        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.velocity_list.append(cb)
            self.status_grid.addWidget(cb, i, 3)
            
        for i in range(1, 8):
            cb = ColorBar(Qt.Vertical)
            self.acceleration_list.append(cb)
            self.status_grid.addWidget(cb, i, 4)
            
        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")
            
        self.test_button.clicked.connect(self.test_button_clicked)
        self.output_voltage_button.clicked.connect(self.output_voltage_button_clicked)
            
        self.servo_dropbox.currentIndexChanged.connect(lambda x: self.update_servo_specific())
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        
        self.position_slider.sliderReleased.connect(self.position_slider_released)
        self.position_slider.valueChanged.connect(self.position_spin.setValue)
        self.position_spin.editingFinished.connect(self.position_spin_finished)
        
        self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
        self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
        self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
        
        self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
        self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
        self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
        
        self.period_slider.sliderReleased.connect(self.period_slider_released)
        self.period_slider.valueChanged.connect(self.period_spin.setValue)
        self.period_spin.editingFinished.connect(self.period_spin_finished)
        
        self.pulse_width_min_spin.editingFinished.connect(self.pulse_width_spin_finished)
        self.pulse_width_max_spin.editingFinished.connect(self.pulse_width_spin_finished)
        self.degree_min_spin.editingFinished.connect(self.degree_spin_finished)
        self.degree_max_spin.editingFinished.connect(self.degree_spin_finished)
        
        self.minimum_voltage_button.pressed.connect(self.minimum_voltage_button_pressed)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.servo.register_callback(self.servo.CALLBACK_UNDER_VOLTAGE,
                                     self.qtcb_under_voltage.emit) 
        
        class WorkerThread(QThread):
            def __init__(self, parent = None, func = None):
                QThread.__init__(self, parent)
                self.func = func
                
            def run(self):
                self.func()
        
        
        self.test_event = Event()
        self.test_thread_object = WorkerThread(self, self.test_thread)
        self.update_event = Event()
        self.update_thread_object = WorkerThread(self, self.update_thread)
        
        self.update_done_event = Event()
        self.update_done_event.set()

    def stop(self):
        if self.test_button.text() == "Stop Test":
            self.test_button_clicked()
        self.update_event.clear()
        self.alive = False
        self.update_done_event.wait()
        
    def start(self):
        self.alive = True
        self.test_event.clear()
        self.update_done_event.set()
        self.update_event.set()
        
        if not self.test_thread_object.isRunning():
            self.test_thread_object.start()
            
        if not self.update_thread_object.isRunning():
            self.update_thread_object.start() 
            
        self.update_servo_specific()
        
    def destroy(self):
        self.test_event.set()
        self.update_event.set()
    
    @staticmethod
    def has_name(name):
        return 'Servo Brick' in name 
    
    def update_servo_specific(self):
        i = self.selected_servo()
        if i == 255:
            self.enable_checkbox.setCheckState(Qt.Unchecked)
            return
        
        try:
            pos = self.servo.get_position(i);
            vel = self.servo.get_velocity(i);
            acc = self.servo.get_acceleration(i);
            per = self.servo.get_period(i)
            ena = self.servo.is_enabled(i)
            deg_min, deg_max = self.servo.get_degree(i)
            pulse_min, pulse_max = self.servo.get_pulse_width(i)
        except ip_connection.Error:
            return
        
        self.position_spin.setValue(pos)
        self.velocity_spin.setValue(vel)
        self.acceleration_spin.setValue(acc)
        self.period_spin.setValue(per)
        self.position_slider.setValue(pos)
        self.velocity_slider.setValue(vel)
        self.acceleration_slider.setValue(acc)
        self.period_slider.setValue(per)
        if ena:
            self.enable_checkbox.setCheckState(Qt.Checked)
        else:
            self.enable_checkbox.setCheckState(Qt.Unchecked)
    
        self.pulse_width_min_spin.setValue(pulse_min)
        self.pulse_width_max_spin.setValue(pulse_max)
        self.degree_min_spin.setValue(deg_min)
        self.degree_max_spin.setValue(deg_max)
        
        self.position_slider.setMinimum(deg_min)
        self.position_slider.setMaximum(deg_max)
        self.position_spin.setMinimum(deg_min)
        self.position_spin.setMaximum(deg_max)
        self.position_list[i].setTotalAngle((deg_max - deg_min)/100)
        self.position_list[i].setRange(deg_min/100, deg_max/100)
        
    def error_handler(self, error):
        pass
        
    def servo_current_update(self, value):
        self.current_label.setText(str(value) + "mA")
    
    def stack_input_voltage_update(self, sv):
        sv_str = "%gV"  % round(sv/1000.0, 1)
        self.stack_voltage_label.setText(sv_str)
        
    def external_input_voltage_update(self, ev):
        ev_str = "%gV"  % round(ev/1000.0, 1)
        self.external_voltage_label.setText(ev_str)
        
    def output_voltage_update(self, ov):
        ov_str = "%gV"  % round(ov/1000.0, 1)
        self.output_voltage_label.setText(ov_str)
        
    def minimum_voltage_update(self, mv):
        mv_str = "%gV"  % round(mv/1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)
        
    def position_update(self, i, pos):
        self.position_list[i].setValue(pos/100)
    
    def velocity_update(self, i, vel):
        self.velocity_list[i].set_height(vel*100/0xFFFF)

    def acceleration_update(self, i, acc):
        self.acceleration_list[i].set_height(acc*100/0xFFFF)
    
    def deactivate_servo(self, i):
        if self.enable_list[i].text() != 'Off':
            self.velocity_list[i].grey()
            self.acceleration_list[i].grey()
            
    def activate_servo(self, i):
        if self.enable_list[i].text() != 'On':
            self.velocity_list[i].color()
            self.acceleration_list[i].color()
        
    def selected_servo(self):
        try:
            return int(self.servo_dropbox.currentText()[-1:])
        except:
            return 255

    def enable_state_changed(self, state):
        s = self.selected_servo()
        try:
            if state == Qt.Checked:
                self.servo.enable(s)
            elif state == Qt.Unchecked:
                self.servo.disable(s)
        except ip_connection.Error:
            return
            
    def update_apply(self):
        self.servo_current_update(self.up_cur)
        self.stack_input_voltage_update(self.up_siv)
        self.external_input_voltage_update(self.up_eiv)
        self.output_voltage_update(self.up_opv)
        self.minimum_voltage_update(self.up_mv)
        for i in range(7):
            if self.up_ena[i]:
                self.activate_servo(i)
                
                self.position_update(i, self.up_pos[i])
                self.velocity_update(i, self.up_vel[i])
                self.acceleration_update(i, self.up_acc[i])
                
                self.enable_list[i].setText('On')
            else:
                self.deactivate_servo(i)
                self.enable_list[i].setText('Off')
                
    def update_thread(self):
        while self.alive:
            time.sleep(0.1)
            
            try:
                servo = self.selected_servo()
                if servo == 255:
                    self.up_cur = self.servo.get_overall_current()
                else:
                    self.up_cur = self.servo.get_servo_current(servo)
                    
                self.up_siv = self.servo.get_stack_input_voltage()
                self.up_eiv = self.servo.get_external_input_voltage()
                self.up_opv = self.servo.get_output_voltage()
                self.up_mv = self.servo.get_minimum_voltage()
                
                for i in range(7):
                    self.up_ena[i] = self.servo.is_enabled(i)
                    if self.up_ena[i]:
                        self.activate_servo(i)
                        self.up_pos[i] = self.servo.get_current_position(i)
                        self.up_vel[i] = self.servo.get_current_velocity(i)
                        self.up_acc[i] = self.servo.get_acceleration(i)
    
                self.update_timer.start()
                #self.update_apply()
                
                self.update_done_event.set()
                self.update_event.wait()
                self.update_done_event.clear()
            except ip_connection.Error:
                pass
        self.update_done_event.set()
            
    def test_thread(self):
        def test(num, ena, acc, vel, pos):
            if not self.alive:
                return

            try:
                if ena:
                    self.servo.enable(num)
                else:
                    self.servo.disable(num)
                self.servo.set_acceleration(num, acc)
                self.servo.set_velocity(num, vel)
                self.servo.set_position(num, pos)
            except ip_connection.Error:
                return
        
        def random_test():
            for i in range(7):
                test(i,
                     random.randrange(0, 2),
                     random.randrange(0, 65536),
                     random.randrange(0, 65536),
                     random.randrange(-9000, 9001))
            
        while self.alive:
            self.test_event.wait()
            if not self.alive:
                return
            
            # Full Speed left for 2 seconds
            for i in range(7):
                test(i, True, 65535, 65535, 9000)
            time.sleep(2)
            self.test_event.wait()
            if not self.alive:
                return
            
            # Full Speed right for 2 seconds
            for i in range(7):
                test(i, True, 65535, 65535, -9000)
            time.sleep(2)
            self.test_event.wait()
            if not self.alive:
                return
            
            # Test different speeds
            for i in range(19):
                for j in range(7):
                    test(j, True, 65535, 65535*i/18, -9000+i*1000)
                time.sleep(0.1)
                self.test_event.wait()  
                if not self.alive:
                    return
            time.sleep(1)
            self.test_event.wait()
            if not self.alive:
                return
            
            # Test acceleration
            for i in range(7):
                test(i, True, 100, 65535, -9000)
                
            time.sleep(3)
            self.test_event.wait()
            if not self.alive:
                return
            
            # Random for 3 seconds
            random_test()
            time.sleep(3)
    
    def test_button_clicked(self):
        if self.test_button.text() == "Start Test":
            self.test_button.setText("Stop Test")
            self.test_event.set()
        else:
            self.test_button.setText("Start Test")        
            self.test_event.clear()
    
    def output_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(5000)
        qid.setIntMaximum(27000)
        qid.setIntStep(100)
        try:
            qid.setIntValue(self.servo.get_output_voltage())
        except ip_connection.Error:
            return
        qid.intValueSelected.connect(self.output_voltage_selected)
        qid.setLabelText("Choose Output Voltage in mV.")
#                         "<font color=red>Setting this too high can destroy your servo.</font>")
        qid.open()
        
    def output_voltage_selected(self, value):
        try:
            self.servo.set_output_voltage(value)
        except ip_connection.Error:
            return
        
    def position_slider_released(self):
        value = self.position_slider.value()
        self.position_spin.setValue(value)
        try:
            self.servo.set_position(self.selected_servo(), value)
        except ip_connection.Error:
            return
 
    def position_spin_finished(self):
        value = self.position_spin.value()
        self.position_slider.setValue(value)
        try:
            self.servo.set_position(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def velocity_slider_released(self):
        value = self.velocity_slider.value()
        self.velocity_spin.setValue(value)
        try:
            self.servo.set_velocity(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def velocity_spin_finished(self):
        value = self.velocity_spin.value()
        self.velocity_slider.setValue(value)
        try:
            self.servo.set_velocity(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def acceleration_slider_released(self):
        value = self.acceleration_slider.value()
        self.acceleration_spin.setValue(value)
        try:
            self.servo.set_acceleration(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def acceleration_spin_finished(self):
        value = self.acceleration_spin.value()
        self.acceleration_slider.setValue(value)
        try:
            self.servo.set_acceleration(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def period_slider_released(self):
        value = self.period_slider.value()
        self.period_spin.setValue(value)
        try:
            self.servo.set_period(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def period_spin_finished(self):
        value = self.period_spin.value()
        self.period_slider.setValue(value)
        try:
            self.servo.set_period(self.selected_servo(), value)
        except ip_connection.Error:
            return
        
    def pulse_width_spin_finished(self):
        try:
            self.servo.set_pulse_width(self.selected_servo(), 
                                       self.pulse_width_min_spin.value(), 
                                       self.pulse_width_max_spin.value())
        except ip_connection.Error:
            return
    
    def degree_spin_finished(self):
        min = self.degree_min_spin.value()
        max = self.degree_max_spin.value()
        servo = self.selected_servo()
        
        self.position_slider.setMinimum(min)
        self.position_slider.setMaximum(max)
        self.position_spin.setMinimum(min)
        self.position_spin.setMaximum(max)
        self.position_list[servo].setTotalAngle((max - min)/100)
        self.position_list[servo].setRange(min/100, max/100)
        
        try:
            self.servo.set_degree(servo, min, max)
        except ip_connection.Error:
            return
        
    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV"  % round(ov/1000.0, 1)
        if not self.qem.isVisible():
            self.qem.showMessage("Under Voltage: Output Voltage of " + ov_str +
                                 " is below minimum voltage of " + mv_str)
            
    def minimum_voltage_selected(self, value):
        try:
            self.servo.set_minimum_voltage(value)
        except ip_connection.Error:
            return

    def minimum_voltage_button_pressed(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(5000)
        qid.setIntMaximum(0xFFFF)
        qid.setIntStep(100)
        try:
            qid.setIntValue(self.servo.get_minimum_voltage())
        except ip_connection.Error:
            return
        qid.intValueSelected.connect(self.minimum_voltage_selected)
        qid.setLabelText("Choose minimum servo voltage in mV.")
        qid.open()
예제 #49
0
파일: main.py 프로젝트: Pipeliner/calibre
        otherinstance = True
    else:
        # On windows only singleinstance can be trusted
        otherinstance = True if iswindows else False
    if not otherinstance and not opts.shutdown_running_calibre:
        return run_gui(opts, args, actions, listener, app, gui_debug=gui_debug)

    communicate(opts, args)

    return 0


if __name__ == '__main__':
    try:
        sys.exit(main())
    except Exception as err:
        if not iswindows:
            raise
        tb = traceback.format_exc()
        from PyQt4.QtGui import QErrorMessage
        logfile = os.path.join(os.path.expanduser('~'), 'calibre.log')
        if os.path.exists(logfile):
            log = open(logfile).read().decode('utf-8', 'ignore')
            d = QErrorMessage()
            d.showMessage(('<b>Error:</b>%s<br><b>Traceback:</b><br>'
                '%s<b>Log:</b><br>%s')%(unicode(err),
                    unicode(tb).replace('\n', '<br>'),
                    log.replace('\n', '<br>')))


예제 #50
0
파일: servo.py 프로젝트: smunix/brickv
 def __init__ (self, ipcon, uid):
     PluginBase.__init__(self, ipcon, uid)
     self.setupUi(self)
     
     self.servo = brick_servo.Servo(self.uid)
     self.device = self.servo
     self.ipcon.add_device(self.servo)
     self.version = '.'.join(map(str, self.servo.get_version()[1]))
     
     self.update_timer = QTimer()
     self.update_timer.timeout.connect(self.update_apply)
     self.update_timer.setInterval(0)
     self.update_timer.setSingleShot(True)
     
     layout = QVBoxLayout(self)
     layout.addWidget(QLabel('Servo'))
     self.position_list = []
     self.velocity_list = []
     self.acceleration_list = []
     self.enable_list = []
     
     self.up_ena = [0]*7
     self.up_pos = [0]*7
     self.up_vel = [0]*7
     self.up_acc = [0]*7
     
     self.alive = True
     
     for i in range(1, 8):
         label = QLabel()
         label.setText('Off')
         self.enable_list.append(label)
         self.status_grid.addWidget(label, i, 1)
         
     for i in range(1, 8):
         pk = PositionKnob()
         self.position_list.append(pk)
         self.status_grid.addWidget(pk, i, 2)
         
     for i in range(1, 8):
         cb = ColorBar(Qt.Vertical)
         self.velocity_list.append(cb)
         self.status_grid.addWidget(cb, i, 3)
         
     for i in range(1, 8):
         cb = ColorBar(Qt.Vertical)
         self.acceleration_list.append(cb)
         self.status_grid.addWidget(cb, i, 4)
         
     self.qem = QErrorMessage(self)
     self.qem.setWindowTitle("Under Voltage")
         
     self.test_button.clicked.connect(self.test_button_clicked)
     self.output_voltage_button.clicked.connect(self.output_voltage_button_clicked)
         
     self.servo_dropbox.currentIndexChanged.connect(lambda x: self.update_servo_specific())
     self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
     
     self.position_slider.sliderReleased.connect(self.position_slider_released)
     self.position_slider.valueChanged.connect(self.position_spin.setValue)
     self.position_spin.editingFinished.connect(self.position_spin_finished)
     
     self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
     self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
     self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
     
     self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
     self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
     self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
     
     self.period_slider.sliderReleased.connect(self.period_slider_released)
     self.period_slider.valueChanged.connect(self.period_spin.setValue)
     self.period_spin.editingFinished.connect(self.period_spin_finished)
     
     self.pulse_width_min_spin.editingFinished.connect(self.pulse_width_spin_finished)
     self.pulse_width_max_spin.editingFinished.connect(self.pulse_width_spin_finished)
     self.degree_min_spin.editingFinished.connect(self.degree_spin_finished)
     self.degree_max_spin.editingFinished.connect(self.degree_spin_finished)
     
     self.minimum_voltage_button.pressed.connect(self.minimum_voltage_button_pressed)
     
     self.qtcb_under_voltage.connect(self.cb_under_voltage)
     self.servo.register_callback(self.servo.CALLBACK_UNDER_VOLTAGE,
                                  self.qtcb_under_voltage.emit) 
     
     class WorkerThread(QThread):
         def __init__(self, parent = None, func = None):
             QThread.__init__(self, parent)
             self.func = func
             
         def run(self):
             self.func()
     
     
     self.test_event = Event()
     self.test_thread_object = WorkerThread(self, self.test_thread)
     self.update_event = Event()
     self.update_thread_object = WorkerThread(self, self.update_thread)
     
     self.update_done_event = Event()
     self.update_done_event.set()
예제 #51
0
파일: stepper.py 프로젝트: fscherwi/brickv
    def __init__(self, *args):
        PluginBase.__init__(self, BrickStepper, *args)

        self.setupUi(self)
     
        self.stepper = self.device
     
        self.endis_all(False)
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(5, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.deceleration_syncer = SliderSpinSyncer(self.deceleration_slider,
                                                    self.deceleration_spin,
                                                    self.deceleration_changed)

#        self.decay_syncer = SliderSpinSyncer(self.decay_slider,
#                                             self.decay_spin,
#                                             self.decay_changed)

        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        self.forward_button.clicked.connect(self.forward_clicked)
        self.stop_button.clicked.connect(self.stop_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.backward_button.clicked.connect(self.backward_clicked)
        self.to_button.clicked.connect(self.to_button_clicked)
        self.steps_button.clicked.connect(self.steps_button_clicked)
        self.motor_current_button.clicked.connect(self.motor_current_button_clicked)
        self.minimum_motor_voltage_button.clicked.connect(self.minimum_motor_voltage_button_clicked)
        
        self.mode_dropbox.currentIndexChanged.connect(self.mode_changed)
        
        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.stepper.register_callback(self.stepper.CALLBACK_POSITION_REACHED, 
                                       self.qtcb_position_reached.emit)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.stepper.register_callback(self.stepper.CALLBACK_UNDER_VOLTAGE, 
                                       self.qtcb_under_voltage.emit)

        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv  = 0
        self.ev  = 0
        self.mv  = 0
        self.mod = 0

        if self.firmware_version >= (1, 1, 4):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.stepper.reset())
            self.set_actions(reset)
예제 #52
0
파일: dc.py 프로젝트: fscherwi/brickv
class DC(PluginBase, Ui_DC):
    qtcb_velocity_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)
    qtcb_emergency_shutdown = pyqtSignal()

    def __init__(self, *args):
        PluginBase.__init__(self, BrickDC, *args)

        self.setupUi(self)

        self.dc = self.device

        self.encoder_hide_all()

        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(4, self.speedometer)

        self.new_value = 0
        self.update_counter = 0

        self.full_brake_time = 0

        self.velocity_syncer = SliderSpinSyncer(self.velocity_slider,
                                                self.velocity_spin,
                                                self.velocity_changed)

        self.acceleration_syncer = SliderSpinSyncer(self.acceleration_slider,
                                                    self.acceleration_spin,
                                                    self.acceleration_changed)

        self.frequency_syncer = SliderSpinSyncer(self.frequency_slider,
                                                 self.frequency_spin,
                                                 self.frequency_changed)

        self.radio_mode_brake.toggled.connect(self.brake_value_changed)
        self.radio_mode_coast.toggled.connect(self.coast_value_changed)

        self.minimum_voltage_button.clicked.connect(
            self.minimum_voltage_button_clicked)
        self.full_brake_button.clicked.connect(self.full_brake_clicked)
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)

        self.emergency_signal = None
        self.under_signal = None
        self.current_velocity_signal = None
        self.velocity_reached_signal = None

        self.qem = QErrorMessage(self)

        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.dc.register_callback(self.dc.CALLBACK_UNDER_VOLTAGE,
                                  self.qtcb_under_voltage.emit)

        self.qtcb_emergency_shutdown.connect(self.cb_emergency_shutdown)
        self.dc.register_callback(self.dc.CALLBACK_EMERGENCY_SHUTDOWN,
                                  self.qtcb_emergency_shutdown.emit)

        self.qtcb_velocity_reached.connect(self.update_velocity)
        self.dc.register_callback(self.dc.CALLBACK_VELOCITY_REACHED,
                                  self.qtcb_velocity_reached.emit)

        self.cbe_current_velocity = CallbackEmulator(
            self.dc.get_current_velocity, self.update_velocity,
            self.increase_error_count)

        if self.firmware_version >= (1, 1, 3):
            reset = QAction('Reset', self)
            reset.triggered.connect(lambda: self.dc.reset())
            self.set_actions(reset)

#        if self.firmware_version >= (2, 0, 1):
#            self.enable_encoder_checkbox.stateChanged.connect(self.enable_encoder_state_changed)
#            self.encoder_show()
#        else:
#            self.enable_encoder_checkbox.setText('Enable Encoder (FW Version >= 2.0.1 required)')
#            self.enable_encoder_checkbox.setEnabled(False)

    def start(self):
        self.update_timer.start(1000)
        self.cbe_current_velocity.set_period(100)
        self.update_start()
        self.update_data()

    def stop(self):
        self.update_timer.stop()
        self.cbe_current_velocity.set_period(0)

    def destroy(self):
        pass

    def get_url_part(self):
        return 'dc'

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickDC.DEVICE_IDENTIFIER

    def cb_emergency_shutdown(self):
        if not self.qem.isVisible():
            self.qem.setWindowTitle("Emergency Shutdown")
            self.qem.showMessage(
                "Emergency Shutdown: Short-Circuit or Over-Temperature")

    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV" % round(ov / 1000.0, 1)
        if not self.qem.isVisible():
            self.qem.setWindowTitle("Under Voltage")
            self.qem.showMessage(
                "Under Voltage: Output Voltage of " + ov_str +
                " is below minimum voltage of " + mv_str, "DC_UnderVoltage")

    def encoder_hide_all(self):
        self.enable_encoder_checkbox.hide()
        self.encoder_hide()

    def encoder_hide(self):
        self.p_label.hide()
        self.p_spinbox.hide()
        self.i_label.hide()
        self.i_spinbox.hide()
        self.d_label.hide()
        self.d_spinbox.hide()
        self.st_label.hide()
        self.st_spinbox.hide()
        self.cpr_label.hide()
        self.cpr_spinbox.hide()
        self.encoder_spacer.hide()

    def encoder_show(self):
        self.p_label.show()
        self.p_spinbox.show()
        self.i_label.show()
        self.i_spinbox.show()
        self.d_label.show()
        self.d_spinbox.show()
        self.st_label.show()
        self.st_spinbox.show()
        self.cpr_label.show()
        self.cpr_spinbox.show()
        self.encoder_spacer.show()

    def enable_encoder_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.dc.enable_encoder()
                self.update_encoder()
            elif state == Qt.Unchecked:
                self.dc.disable_encoder()

        except ip_connection.Error:
            return

    def enable_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.dc.enable()
            elif state == Qt.Unchecked:
                self.dc.disable()
        except ip_connection.Error:
            return

    def brake_value_changed(self, checked):
        if checked:
            try:
                self.dc.set_drive_mode(0)
            except ip_connection.Error:
                return

    def coast_value_changed(self, checked):
        if checked:
            try:
                self.dc.set_drive_mode(1)
            except ip_connection.Error:
                return

    def full_brake_clicked(self):
        try:
            self.dc.full_brake()
        except ip_connection.Error:
            return

    def minimum_voltage_selected(self, value):
        try:
            self.dc.set_minimum_voltage(value)
        except ip_connection.Error:
            return

    def minimum_voltage_button_clicked(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(5000)
        qid.setIntMaximum(0xFFFF)
        qid.setIntStep(100)
        async_call(self.dc.get_minimum_voltage, None, qid.setIntValue,
                   self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()

    def stack_input_voltage_update(self, sv):
        sv_str = "%gV" % round(sv / 1000.0, 1)
        self.stack_voltage_label.setText(sv_str)

    def external_input_voltage_update(self, ev):
        ev_str = "%gV" % round(ev / 1000.0, 1)
        self.external_voltage_label.setText(ev_str)

    def minimum_voltage_update(self, mv):
        mv_str = "%gV" % round(mv / 1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)

    def drive_mode_update(self, dm):
        if dm == 0:
            self.radio_mode_brake.setChecked(True)
            self.radio_mode_coast.setChecked(False)
        else:
            self.radio_mode_brake.setChecked(False)
            self.radio_mode_coast.setChecked(True)

    def current_consumption_update(self, cc):
        if cc >= 1000:
            cc_str = "%gA" % round(cc / 1000.0, 1)
        else:
            cc_str = "%gmA" % cc

        self.current_label.setText(cc_str)

    def update_velocity(self, value):
        self.speedometer.set_velocity(value)

    def get_velocity_async(self, velocity):
        if not self.velocity_slider.isSliderDown():
            if velocity != self.velocity_slider.sliderPosition():
                self.velocity_slider.setSliderPosition(velocity)
                self.velocity_spin.setValue(velocity)

        self.speedometer.set_velocity(velocity)

    def get_acceleration_async(self, acceleration):
        if not self.acceleration_slider.isSliderDown():
            if acceleration != self.acceleration_slider.sliderPosition():
                self.acceleration_slider.setSliderPosition(acceleration)
                self.acceleration_spin.setValue(acceleration)

    def get_pwm_frequency_async(self, frequency):
        if not self.frequency_slider.isSliderDown():
            if frequency != self.frequency_slider.sliderPosition():
                self.frequency_slider.setSliderPosition(frequency)
                self.frequency_spin.setValue(frequency)

    def is_enabled_async(self, enabled):
        self.enable_checkbox.setChecked(enabled)

    def is_encoder_enabled_async(self, enabled):
        self.enable_encoder_checkbox.setChecked(enabled)

    def get_encoder_config_async(self, cpr):
        self.cpr_spinbox.setValue(cpr)

    def get_encoder_pid_config_async(self, pid_config):
        self.p_spinbox.setValue(pid_config.p)
        self.i_spinbox.setValue(pid_config.i)
        self.d_spinbox.setValue(pid_config.d)
        self.st_spinbox.setValue(pid_config.sample_time)

    def update_encoder(self):
        async_call(self.dc.get_encoder_config, None,
                   self.get_encoder_config_async, self.increase_error_count)
        async_call(self.dc.get_encoder_pid_config, None,
                   self.get_encoder_pid_config_async,
                   self.increase_error_count)
        async_call(self.dc.is_encoder_enabled, None,
                   self.is_encoder_enabled_async, self.increase_error_count)

    def update_start(self):
        async_call(self.dc.get_drive_mode, None, self.drive_mode_update,
                   self.increase_error_count)
        async_call(self.dc.get_velocity, None, self.get_velocity_async,
                   self.increase_error_count)
        async_call(self.dc.get_acceleration, None, self.get_acceleration_async,
                   self.increase_error_count)
        async_call(self.dc.get_pwm_frequency, None,
                   self.get_pwm_frequency_async, self.increase_error_count)
        async_call(self.dc.is_enabled, None, self.is_enabled_async,
                   self.increase_error_count)
#        if self.firmware_version >= (2, 0, 1):
#            self.update_encoder()

    def update_data(self):
        async_call(self.dc.get_stack_input_voltage, None,
                   self.stack_input_voltage_update, self.increase_error_count)
        async_call(self.dc.get_external_input_voltage, None,
                   self.external_input_voltage_update,
                   self.increase_error_count)
        async_call(self.dc.get_minimum_voltage, None,
                   self.minimum_voltage_update, self.increase_error_count)
        async_call(self.dc.get_current_consumption, None,
                   self.current_consumption_update, self.increase_error_count)

    def acceleration_changed(self, value):
        try:
            self.dc.set_acceleration(value)
        except ip_connection.Error:
            return

    def velocity_changed(self, value):
        try:
            self.dc.set_velocity(value)
        except ip_connection.Error:
            return

    def frequency_changed(self, value):
        try:
            self.dc.set_pwm_frequency(value)
        except ip_connection.Error:
            return
예제 #53
0
class ProjectXively(QWidget):
    qtcb_update_illuminance = pyqtSignal(float)
    qtcb_update_air_pressure = pyqtSignal(float)
    qtcb_update_temperature = pyqtSignal(float)
    qtcb_update_humidity = pyqtSignal(float)
    qtcb_button_pressed = pyqtSignal(int)

    lcdwidget = None

    xively_host = "api.xively.com"
    xively_agent = "Tinkerforge Starter Kit Weather Station Demo"
    xively_channel = "Enter Feed ID here"
    xively_api_key = "Enter API Key here"

    xively_items = {}
    xively_headers = None
    xively_params = ""
    xively_update_rate = 5  # in minutes

    text_agent = None
    text_channel = None
    text_api_key = None
    number_update_rate = None

    save_button = None

    xively_timer = None

    error_message = None

    label_upload_active = None

    last_upload = None

    def __init__(self, parent, app):
        super(QWidget, self).__init__()

        self.lcdwidget = LCDWidget(self, app)
        self.lcdwidget.hide()

        self.text_agent = QLineEdit(self)
        self.text_agent.setText(self.xively_agent)

        self.text_channel = QLineEdit(self)
        self.text_channel.setText(self.xively_channel)

        self.text_api_key = QLineEdit(self)
        self.text_api_key.setText(self.xively_api_key)

        self.number_update_rate = QSpinBox(self)
        self.number_update_rate.setRange(1, 1440)
        self.number_update_rate.setSuffix(' min')
        self.number_update_rate.setValue(self.xively_update_rate)

        layout1 = QHBoxLayout()
        layout2 = QVBoxLayout()

        layout1.addStretch()
        layout1.addLayout(layout2)
        layout1.addStretch()

        layout2.addSpacerItem(QSpacerItem(LCDWidget.FIXED_WIDGTH, 0))

        label = QLabel(self)
        label.setText(
            "Project: <b>Connect to Xively</b>. This project uploads the measured values to Xively. Please find documentation how to configure it and program sources in Python <a href=\"http://www.tinkerforge.com/en/doc/Kits/WeatherStation/WeatherStation.html#connect-to-xively\">here</a>.<br>"
        )
        label.setTextFormat(Qt.RichText)
        label.setTextInteractionFlags(Qt.TextBrowserInteraction)
        label.setOpenExternalLinks(True)
        label.setWordWrap(True)
        label.setAlignment(Qt.AlignJustify)

        layout2.addSpacing(10)
        layout2.addWidget(label)
        layout2.addSpacing(10)

        layout3a = QHBoxLayout()
        label = QLabel("Agent Description:")
        label.setMinimumWidth(150)
        layout3a.addWidget(label)
        layout3a.addWidget(self.text_agent, 1)

        layout2.addLayout(layout3a)
        layout2.addSpacing(10)

        layout3b = QHBoxLayout()
        label = QLabel("Feed:")
        label.setMinimumWidth(150)
        layout3b.addWidget(label)
        layout3b.addWidget(self.text_channel, 1)

        layout2.addLayout(layout3b)
        layout2.addSpacing(10)

        layout3c = QHBoxLayout()
        label = QLabel("API Key:")
        label.setMinimumWidth(150)
        layout3c.addWidget(label)
        layout3c.addWidget(self.text_api_key, 1)

        layout2.addLayout(layout3c)
        layout2.addSpacing(10)

        layout3d = QHBoxLayout()
        label = QLabel("Update Rate:")
        label.setMinimumWidth(150)
        layout3d.addWidget(label)
        layout3d.addWidget(self.number_update_rate, 1)

        layout2.addLayout(layout3d)
        layout2.addSpacing(10)

        self.label_upload_active = QLabel("Not Active", self)
        self.label_upload_active.setMinimumWidth(150)
        font = QFont()
        font.setPixelSize(20)
        self.label_upload_active.setFont(font)
        self.set_active_label(False)

        self.save_button = QPushButton("Save/Activate")

        layout4 = QHBoxLayout()
        layout4.addWidget(self.label_upload_active)
        layout4.addWidget(self.save_button, 1)

        layout2.addLayout(layout4)
        layout2.addStretch()

        self.setLayout(layout1)

        self.qtcb_update_illuminance.connect(self.update_illuminance_data_slot)
        self.qtcb_update_air_pressure.connect(
            self.update_air_pressure_data_slot)
        self.qtcb_update_temperature.connect(self.update_temperature_data_slot)
        self.qtcb_update_humidity.connect(self.update_humidity_data_slot)
        self.qtcb_button_pressed.connect(self.button_pressed_slot)
        self.save_button.clicked.connect(self.save_configuration)

        self.lcdwidget.clear(self)

        self.error_message = QErrorMessage(self)

    def set_active_label(self, value):
        palette = self.label_upload_active.palette()
        if value:
            palette.setColor(self.foregroundRole(), Qt.darkGreen)
            self.label_upload_active.setText("Active")
        else:
            palette.setColor(self.foregroundRole(), Qt.red)
            self.label_upload_active.setText("Not Active")

        self.label_upload_active.setPalette(palette)

    def save_configuration(self):
        try:
            self.xively_agent = str(self.text_agent.text()).decode('ascii')
            self.xively_channel = str(self.text_channel.text()).decode('ascii')
            self.xively_api_key = str(self.text_api_key.text()).decode('ascii')
        except:
            self.error_message.showMessage(
                'Agent, Feed and API Key can only contain ASCII characters')
            return

        self.xively_update_rate = self.number_update_rate.value()

        self.xively_headers = {
            "Content-Type": "application/x-www-form-urlencoded",
            "X-ApiKey": self.xively_api_key,
            "User-Agent": self.xively_agent,
        }
        self.xively_params = "/v2/feeds/" + self.xively_channel

        if self.xively_timer is None:
            self.xively_timer = QTimer(self)
            self.xively_timer.timeout.connect(self.update_xively)
            self.xively_timer.start(self.xively_update_rate * 60 * 1000)

        self.set_active_label(True)
        self.update_xively()

    def write_lcd(self):
        if self.last_upload == None:
            tmp = "Last: Never"
        else:
            tmp = "Last: " + self.last_upload

        self.lcdwidget.write_line(0, 0, "Xively Upload", self)
        self.lcdwidget.write_line(2, 0, tmp, self)

    def update_xively(self):
        if len(self.xively_items) == 0:
            return

        stream_items = []
        for identifier, value in self.xively_items.items():
            stream_items.append({
                'id': identifier,
                'current_value': value[0],
                'min_value': value[1],
                'max_value': value[2]
            })

        data = {'version': '1.0.0', 'datastreams': stream_items}
        self.xively_items = {}
        body = json.dumps(data)

        try:
            http = httplib.HTTPSConnection(self.xively_host)
            http.request('PUT', self.xively_params, body, self.xively_headers)
            response = http.getresponse()
            http.close()

            if response.status != 200:
                self.error_message.showMessage(
                    'Could not upload to xively -> Response:' +
                    str(response.status) + ': ' + response.reason +
                    '. Check your configuration.')
                self.xively_timer.stop()
                self.xively_timer = None
                self.set_active_label(False)
                return
        except Exception as e:
            self.error_message.showMessage('HTTP error: ' + str(e))
            self.xively_timer.stop()
            self.xively_timer = None
            self.set_active_label(False)
            return

        # set upload time if upload was a success
        self.last_upload = time.strftime("%H:%M:%S")

    def put(self, identifier, value):
        self.write_lcd()
        try:
            _, min_value, max_value = self.xively_items[identifier]
            if value < min_value:
                min_value = value
            if value > max_value:
                max_value = value
            self.xively_items[identifier] = (value, min_value, max_value)
        except:
            self.xively_items[identifier] = (value, value, value)

    def update_illuminance_data_slot(self, illuminance):
        self.put('AmbientLight', illuminance)

    def update_illuminance(self, illuminance):
        self.qtcb_update_illuminance.emit(illuminance)

    def update_humidity_data_slot(self, humidity):
        self.put('Humidity', humidity)

    def update_humidity(self, humidity):
        self.qtcb_update_humidity.emit(humidity)

    def update_air_pressure_data_slot(self, air_pressure):
        self.put('AirPressure', air_pressure)

    def update_air_pressure(self, air_pressure):
        self.qtcb_update_air_pressure.emit(air_pressure)

    def update_temperature_data_slot(self, temperature):
        self.put('Temperature', temperature)

    def update_temperature(self, temperature):
        self.qtcb_update_temperature.emit(temperature)

    def button_pressed_slot(self, button):
        pass

    def button_pressed(self, button):
        self.qtcb_button_pressed.emit(button)
예제 #54
0
    def __init__(self, parent, app):
        super(QWidget, self).__init__()

        self.lcdwidget = LCDWidget(self, app)
        self.lcdwidget.hide()

        self.text_agent = QLineEdit(self)
        self.text_agent.setText(self.xively_agent)
        
        self.text_channel = QLineEdit(self)
        self.text_channel.setText(self.xively_channel)
        
        self.text_api_key = QLineEdit(self)
        self.text_api_key.setText(self.xively_api_key)
        
        self.number_update_rate = QSpinBox(self)
        self.number_update_rate.setRange(1, 1440)
        self.number_update_rate.setSuffix(' min')
        self.number_update_rate.setValue(self.xively_update_rate)

        layout1 = QHBoxLayout()
        layout2 = QVBoxLayout()
        
        layout1.addStretch()
        layout1.addLayout(layout2)
        layout1.addStretch()
        
        layout2.addSpacerItem(QSpacerItem(LCDWidget.FIXED_WIDGTH, 0))

        label = QLabel(self)
        label.setText("Project: <b>Connect to Xively</b>. This project uploads the measured values to Xively. Please find documentation how to configure it and program sources in Python <a href=\"http://www.tinkerforge.com/en/doc/Kits/WeatherStation/WeatherStation.html#connect-to-xively\">here</a>.<br>")
        label.setTextFormat(Qt.RichText)
        label.setTextInteractionFlags(Qt.TextBrowserInteraction)
        label.setOpenExternalLinks(True)
        label.setWordWrap(True)
        label.setAlignment(Qt.AlignJustify)

        layout2.addSpacing(10)
        layout2.addWidget(label)
        layout2.addSpacing(10)

        layout3a = QHBoxLayout()
        label = QLabel("Agent Description:")
        label.setMinimumWidth(150)
        layout3a.addWidget(label)
        layout3a.addWidget(self.text_agent, 1)

        layout2.addLayout(layout3a)
        layout2.addSpacing(10)

        layout3b = QHBoxLayout()
        label = QLabel("Feed:")
        label.setMinimumWidth(150)
        layout3b.addWidget(label)
        layout3b.addWidget(self.text_channel, 1)

        layout2.addLayout(layout3b)
        layout2.addSpacing(10)

        layout3c = QHBoxLayout()
        label = QLabel("API Key:")
        label.setMinimumWidth(150)
        layout3c.addWidget(label)
        layout3c.addWidget(self.text_api_key, 1)

        layout2.addLayout(layout3c)
        layout2.addSpacing(10)

        layout3d = QHBoxLayout()
        label = QLabel("Update Rate:")
        label.setMinimumWidth(150)
        layout3d.addWidget(label)
        layout3d.addWidget(self.number_update_rate, 1)

        layout2.addLayout(layout3d)
        layout2.addSpacing(10)

        self.label_upload_active = QLabel("Not Active", self)
        self.label_upload_active.setMinimumWidth(150)
        font = QFont()
        font.setPixelSize(20)
        self.label_upload_active.setFont(font)
        self.set_active_label(False)

        self.save_button = QPushButton("Save/Activate")

        layout4 = QHBoxLayout()
        layout4.addWidget(self.label_upload_active)
        layout4.addWidget(self.save_button, 1)

        layout2.addLayout(layout4)
        layout2.addStretch()

        self.setLayout(layout1)

        self.qtcb_update_illuminance.connect(self.update_illuminance_data_slot)
        self.qtcb_update_air_pressure.connect(self.update_air_pressure_data_slot)
        self.qtcb_update_temperature.connect(self.update_temperature_data_slot)
        self.qtcb_update_humidity.connect(self.update_humidity_data_slot)
        self.qtcb_button_pressed.connect(self.button_pressed_slot)
        self.save_button.clicked.connect(self.save_configuration)

        self.lcdwidget.clear(self)

        self.error_message = QErrorMessage(self)
예제 #55
0
    def __init__(self, ipcon, uid, version):
        PluginBase.__init__(self, ipcon, uid, 'Stepper Brick', version)
        
        self.setupUi(self)
     
        self.stepper = BrickStepper(uid, ipcon)
        self.device = self.stepper
     
        self.endis_all(False)
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)

        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(5, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0

        self.qem = QErrorMessage(self)
        self.qem.setWindowTitle("Under Voltage")
        
        self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
        self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
        self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
        
        self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
        self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
        self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
        
        self.deceleration_slider.sliderReleased.connect(self.deceleration_slider_released)
        self.deceleration_slider.valueChanged.connect(self.deceleration_spin.setValue)
        self.deceleration_spin.editingFinished.connect(self.deceleration_spin_finished)
        
#        self.decay_slider.sliderReleased.connect(self.decay_slider_released)
#        self.decay_slider.valueChanged.connect(self.decay_spin.setValue)
#        self.decay_spin.editingFinished.connect(self.decay_spin_finished)
        
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        self.forward_button.pressed.connect(self.forward_pressed)
        self.stop_button.pressed.connect(self.stop_pressed)
        self.full_brake_button.pressed.connect(self.full_brake_pressed)
        self.backward_button.pressed.connect(self.backward_pressed)
        self.to_button.pressed.connect(self.to_button_pressed)
        self.steps_button.pressed.connect(self.steps_button_pressed)
        self.motor_current_button.pressed.connect(self.motor_current_button_pressed)
        self.minimum_motor_voltage_button.pressed.connect(self.minimum_motor_voltage_button_pressed)
        
        self.mode_dropbox.currentIndexChanged.connect(self.mode_changed)
        
        self.qtcb_position_reached.connect(self.cb_position_reached)
        self.stepper.register_callback(self.stepper.CALLBACK_POSITION_REACHED, 
                                       self.qtcb_position_reached.emit)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.stepper.register_callback(self.stepper.CALLBACK_UNDER_VOLTAGE, 
                                       self.qtcb_under_voltage.emit)
        
        self.update_data_async_thread = None
        
        self.ste = 0
        self.pos = 0
        self.current_velocity = 0
        self.cur = 0
        self.sv  = 0
        self.ev  = 0
        self.mv  = 0
        self.mod = 0
예제 #56
0
    def __init__(self, parent, app):
        super(QWidget, self).__init__()

        self.lcdwidget = LCDWidget(self, app)
        self.lcdwidget.hide()

        self.text_agent = QLineEdit(self)
        self.text_agent.setText(self.xively_agent)

        self.text_channel = QLineEdit(self)
        self.text_channel.setText(self.xively_channel)

        self.text_api_key = QLineEdit(self)
        self.text_api_key.setText(self.xively_api_key)

        self.number_update_rate = QSpinBox(self)
        self.number_update_rate.setRange(1, 1440)
        self.number_update_rate.setSuffix(' min')
        self.number_update_rate.setValue(self.xively_update_rate)

        layout1 = QHBoxLayout()
        layout2 = QVBoxLayout()

        layout1.addStretch()
        layout1.addLayout(layout2)
        layout1.addStretch()

        layout2.addSpacerItem(QSpacerItem(LCDWidget.FIXED_WIDGTH, 0))

        label = QLabel(self)
        label.setText(
            "Project: <b>Connect to Xively</b>. This project uploads the measured values to Xively. Please find documentation how to configure it and program sources in Python <a href=\"http://www.tinkerforge.com/en/doc/Kits/WeatherStation/WeatherStation.html#connect-to-xively\">here</a>.<br>"
        )
        label.setTextFormat(Qt.RichText)
        label.setTextInteractionFlags(Qt.TextBrowserInteraction)
        label.setOpenExternalLinks(True)
        label.setWordWrap(True)
        label.setAlignment(Qt.AlignJustify)

        layout2.addSpacing(10)
        layout2.addWidget(label)
        layout2.addSpacing(10)

        layout3a = QHBoxLayout()
        label = QLabel("Agent Description:")
        label.setMinimumWidth(150)
        layout3a.addWidget(label)
        layout3a.addWidget(self.text_agent, 1)

        layout2.addLayout(layout3a)
        layout2.addSpacing(10)

        layout3b = QHBoxLayout()
        label = QLabel("Feed:")
        label.setMinimumWidth(150)
        layout3b.addWidget(label)
        layout3b.addWidget(self.text_channel, 1)

        layout2.addLayout(layout3b)
        layout2.addSpacing(10)

        layout3c = QHBoxLayout()
        label = QLabel("API Key:")
        label.setMinimumWidth(150)
        layout3c.addWidget(label)
        layout3c.addWidget(self.text_api_key, 1)

        layout2.addLayout(layout3c)
        layout2.addSpacing(10)

        layout3d = QHBoxLayout()
        label = QLabel("Update Rate:")
        label.setMinimumWidth(150)
        layout3d.addWidget(label)
        layout3d.addWidget(self.number_update_rate, 1)

        layout2.addLayout(layout3d)
        layout2.addSpacing(10)

        self.label_upload_active = QLabel("Not Active", self)
        self.label_upload_active.setMinimumWidth(150)
        font = QFont()
        font.setPixelSize(20)
        self.label_upload_active.setFont(font)
        self.set_active_label(False)

        self.save_button = QPushButton("Save/Activate")

        layout4 = QHBoxLayout()
        layout4.addWidget(self.label_upload_active)
        layout4.addWidget(self.save_button, 1)

        layout2.addLayout(layout4)
        layout2.addStretch()

        self.setLayout(layout1)

        self.qtcb_update_illuminance.connect(self.update_illuminance_data_slot)
        self.qtcb_update_air_pressure.connect(
            self.update_air_pressure_data_slot)
        self.qtcb_update_temperature.connect(self.update_temperature_data_slot)
        self.qtcb_update_humidity.connect(self.update_humidity_data_slot)
        self.qtcb_button_pressed.connect(self.button_pressed_slot)
        self.save_button.clicked.connect(self.save_configuration)

        self.lcdwidget.clear(self)

        self.error_message = QErrorMessage(self)
예제 #57
0
파일: dc.py 프로젝트: karstenerhardt/brickv
class DC(PluginBase, Ui_DC):
    qtcb_position_reached = pyqtSignal(int)
    qtcb_under_voltage = pyqtSignal(int)
    qtcb_emergency_shutdown = pyqtSignal()
    
    def __init__(self, ipcon, uid, version):
        PluginBase.__init__(self, ipcon, uid, 'DC Brick', version)
        
        self.setupUi(self)
        self.encoder_hide_all()
        
        self.dc = BrickDC(uid, ipcon)
        self.device = self.dc
        
        self.update_timer = QTimer()
        self.update_timer.timeout.connect(self.update_data)
        
        self.speedometer = SpeedoMeter()
        self.vertical_layout_right.insertWidget(4, self.speedometer)
        
        self.new_value = 0
        self.update_counter = 0
        
        self.full_brake_time = 0
        
        self.velocity_slider.sliderReleased.connect(self.velocity_slider_released)
        self.velocity_slider.valueChanged.connect(self.velocity_spin.setValue)
        self.velocity_spin.editingFinished.connect(self.velocity_spin_finished)
        
        self.acceleration_slider.sliderReleased.connect(self.acceleration_slider_released)
        self.acceleration_slider.valueChanged.connect(self.acceleration_spin.setValue)
        self.acceleration_spin.editingFinished.connect(self.acceleration_spin_finished)
        
        self.frequency_slider.sliderReleased.connect(self.frequency_slider_released)
        self.frequency_slider.valueChanged.connect(self.frequency_spin.setValue)
        self.frequency_spin.editingFinished.connect(self.frequency_spin_finished)
        
        self.radio_mode_brake.toggled.connect(self.brake_value_changed)
        self.radio_mode_coast.toggled.connect(self.coast_value_changed)
        
        self.minimum_voltage_button.pressed.connect(self.minimum_voltage_button_pressed)
        self.full_brake_button.pressed.connect(self.full_brake_pressed)
        self.enable_checkbox.stateChanged.connect(self.enable_state_changed)
        
        self.emergency_signal = None
        self.under_signal = None
        self.current_velocity_signal = None
        self.velocity_reached_signal = None
        
        self.qem = QErrorMessage(self)
        
        self.qtcb_under_voltage.connect(self.cb_under_voltage)
        self.dc.register_callback(self.dc.CALLBACK_UNDER_VOLTAGE,
                                  self.qtcb_under_voltage.emit) 
        
        self.qtcb_emergency_shutdown.connect(self.cb_emergency_shutdown)
        self.dc.register_callback(self.dc.CALLBACK_EMERGENCY_SHUTDOWN,
                                  self.qtcb_emergency_shutdown.emit) 
        
        self.qtcb_position_reached.connect(self.update_velocity)
        self.dc.register_callback(self.dc.CALLBACK_VELOCITY_REACHED,
                                  self.qtcb_position_reached.emit) 
        self.dc.register_callback(self.dc.CALLBACK_CURRENT_VELOCITY,
                                  self.qtcb_position_reached.emit)
        
#        if self.version >= (2, 0, 1):
#            self.enable_encoder_checkbox.stateChanged.connect(self.enable_encoder_state_changed)
#            self.encoder_show()
#        else:
#            self.enable_encoder_checkbox.setText('Enable Encoder (Firmware >= 2.01 required)')
#            self.enable_encoder_checkbox.setEnabled(False)
    
    def start(self):
        self.update_timer.start(1000)
        async_call(self.dc.set_current_velocity_period, 100, None, self.increase_error_count)
        self.update_start()
        self.update_data()
        
    def stop(self):
        self.update_timer.stop()
        async_call(self.dc.set_current_velocity_period, 0, None, self.increase_error_count)

    def has_reset_device(self):
        return self.version >= (1, 1, 3)

    def reset_device(self):
        if self.has_reset_device():
            self.dc.reset()

    def is_brick(self):
        return True

    def get_url_part(self):
        return 'dc'

    @staticmethod
    def has_device_identifier(device_identifier):
        return device_identifier == BrickDC.DEVICE_IDENTIFIER
        
    def cb_emergency_shutdown(self):
        if not self.qem.isVisible():
            self.qem.setWindowTitle("Emergency Shutdown")
            self.qem.showMessage("Emergency Shutdown: Short-Circuit or Over-Temperature")
        
    def cb_under_voltage(self, ov):
        mv_str = self.minimum_voltage_label.text()
        ov_str = "%gV"  % round(ov/1000.0, 1)
        if not self.qem.isVisible():
            self.qem.setWindowTitle("Under Voltage")
            self.qem.showMessage("Under Voltage: Output Voltage of " + ov_str +
                                 " is below minimum voltage of " + mv_str,
                                 "DC_UnderVoltage")
            
    def encoder_hide_all(self):
        self.enable_encoder_checkbox.hide()
        self.encoder_hide()
            
    def encoder_hide(self):
        self.p_label.hide()
        self.p_spinbox.hide()
        self.i_label.hide()
        self.i_spinbox.hide()
        self.d_label.hide()
        self.d_spinbox.hide()
        self.st_label.hide()
        self.st_spinbox.hide()
        self.cpr_label.hide()
        self.cpr_spinbox.hide()
        self.encoder_spacer.hide()
        
    def encoder_show(self):
        self.p_label.show()
        self.p_spinbox.show()
        self.i_label.show()
        self.i_spinbox.show()
        self.d_label.show()
        self.d_spinbox.show()
        self.st_label.show()
        self.st_spinbox.show()
        self.cpr_label.show()
        self.cpr_spinbox.show()
        self.encoder_spacer.show()          
         
    def enable_encoder_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.dc.enable_encoder()
                self.update_encoder()
            elif state == Qt.Unchecked:
                self.dc.disable_encoder()

        except ip_connection.Error:
            return
        
    def enable_state_changed(self, state):
        try:
            if state == Qt.Checked:
                self.dc.enable()
            elif state == Qt.Unchecked:
                self.dc.disable()
        except ip_connection.Error:
            return
            
    def brake_value_changed(self, checked):
        if checked:
            try:
                self.dc.set_drive_mode(0)
            except ip_connection.Error:
                return
        
    def coast_value_changed(self, checked):
        if checked:
            try:
                self.dc.set_drive_mode(1)
            except ip_connection.Error:
                return
        
    def full_brake_pressed(self):
        try:
            self.dc.full_brake()
        except ip_connection.Error:
            return
        
    def minimum_voltage_selected(self, value):
        try:
            self.dc.set_minimum_voltage(value)
        except ip_connection.Error:
            return
        
    def minimum_voltage_button_pressed(self):
        qid = QInputDialog(self)
        qid.setInputMode(QInputDialog.IntInput)
        qid.setIntMinimum(5000)
        qid.setIntMaximum(0xFFFF)
        qid.setIntStep(100)
        async_call(self.dc.get_minimum_voltage, None, qid.setIntValue, self.increase_error_count)
        qid.intValueSelected.connect(self.minimum_voltage_selected)
        qid.setLabelText("Choose minimum motor voltage in mV.")
        qid.open()
        
    def stack_input_voltage_update(self, sv):
        sv_str = "%gV"  % round(sv/1000.0, 1)
        self.stack_voltage_label.setText(sv_str)
        
    def external_input_voltage_update(self, ev):
        ev_str = "%gV"  % round(ev/1000.0, 1)
        self.external_voltage_label.setText(ev_str)
        
    def minimum_voltage_update(self, mv):
        mv_str = "%gV"  % round(mv/1000.0, 1)
        self.minimum_voltage_label.setText(mv_str)
        
    def drive_mode_update(self, dm):
        if dm == 0:
            self.radio_mode_brake.setChecked(True)
            self.radio_mode_coast.setChecked(False)
        else:
            self.radio_mode_brake.setChecked(False)
            self.radio_mode_coast.setChecked(True)
            
    def current_consumption_update(self, cc):
        if cc >= 1000:
            cc_str = "%gA"  % round(cc/1000.0, 1)
        else:
            cc_str = "%gmA" % cc
            
        self.current_label.setText(cc_str)

    
    def update_velocity(self, value):
        if value != self.speedometer.value():
            self.speedometer.set_velocity(value)
        
    def get_velocity_async(self, velocity):
        if not self.velocity_slider.isSliderDown():
            if velocity != self.velocity_slider.sliderPosition():
                self.velocity_slider.setSliderPosition(velocity)
                self.velocity_spin.setValue(velocity)
        
    def get_acceleration_async(self, acceleration):
        if not self.acceleration_slider.isSliderDown():
            if acceleration != self.acceleration_slider.sliderPosition():
                self.acceleration_slider.setSliderPosition(acceleration)
                self.acceleration_spin.setValue(acceleration)
        
    def get_pwm_frequency_async(self, frequency):
        if not self.frequency_slider.isSliderDown():
            if frequency != self.frequency_slider.sliderPosition():
                self.frequency_slider.setSliderPosition(frequency)
                self.frequency_spin.setValue(frequency)
        
    def is_enabled_async(self, enabled):
        if enabled:
            self.enable_checkbox.setCheckState(Qt.Checked)
        else:
            self.enable_checkbox.setCheckState(Qt.Unchecked)
            
    def is_encoder_enabled_async(self, enabled):
        if enabled:
            self.enable_encoder_checkbox.setCheckState(Qt.Checked)
        else:
            self.enable_encoder_checkbox.setCheckState(Qt.Unchecked)
            
    def get_encoder_config_async(self, cpr):
        self.cpr_spinbox.setValue(cpr)
    
    def get_encoder_pid_config_async(self, pid_config):
        self.p_spinbox.setValue(pid_config.p)
        self.i_spinbox.setValue(pid_config.i)
        self.d_spinbox.setValue(pid_config.d)
        self.st_spinbox.setValue(pid_config.sample_time)
        
    def update_encoder(self):
        async_call(self.dc.get_encoder_config, None, self.get_encoder_config_async, self.increase_error_count)
        async_call(self.dc.get_encoder_pid_config, None, self.get_encoder_pid_config_async, self.increase_error_count)
        async_call(self.dc.is_encoder_enabled, None, self.is_encoder_enabled_async, self.increase_error_count)
        
        
    def update_start(self):
        async_call(self.dc.get_drive_mode, None, self.drive_mode_update, self.increase_error_count)
        async_call(self.dc.get_velocity, None, self.get_velocity_async, self.increase_error_count)
        async_call(self.dc.get_acceleration, None, self.get_acceleration_async, self.increase_error_count)
        async_call(self.dc.get_pwm_frequency, None, self.get_pwm_frequency_async, self.increase_error_count)
        async_call(self.dc.is_enabled, None, self.is_enabled_async, self.increase_error_count)
#        if self.version >= (2, 0, 1):
#            self.update_encoder()
            

    def update_data(self):
        async_call(self.dc.get_stack_input_voltage, None, self.stack_input_voltage_update, self.increase_error_count)
        async_call(self.dc.get_external_input_voltage, None, self.external_input_voltage_update, self.increase_error_count)
        async_call(self.dc.get_minimum_voltage, None, self.minimum_voltage_update, self.increase_error_count)
        async_call(self.dc.get_current_consumption, None, self.current_consumption_update, self.increase_error_count)
        
    def acceleration_slider_released(self):
        value = self.acceleration_slider.value()
        self.acceleration_spin.setValue(value)
        try:
            self.dc.set_acceleration(value)
        except ip_connection.Error:
            return
        
    def acceleration_spin_finished(self):
        value = self.acceleration_spin.value()
        self.acceleration_slider.setValue(value)
        try:
            self.dc.set_acceleration(value)
        except ip_connection.Error:
            return
        
    def velocity_slider_released(self):
        value = self.velocity_slider.value()
        self.velocity_spin.setValue(value)
        try:
            self.dc.set_velocity(value)
        except ip_connection.Error:
            return
        
    def velocity_spin_finished(self):
        value = self.velocity_spin.value()
        self.velocity_slider.setValue(value)
        try:
            self.dc.set_velocity(value)
        except ip_connection.Error:
            return
        
    def frequency_slider_released(self):
        value = self.frequency_slider.value()
        self.frequency_spin.setValue(value)
        try:
            self.dc.set_pwm_frequency(value)
        except ip_connection.Error:
            return
        
    def frequency_spin_finished(self):
        value = self.frequency_spin.value()
        self.frequency_slider.setValue(value)
        try:
            self.dc.set_pwm_frequency(value)
        except ip_connection.Error:
            return
예제 #58
-1
    def input_device_changed(self, index):
        self.ui.actionStart.setChecked(False)

        success, index = self.audiobackend.select_input_device(index)

        self.settings_dialog.comboBox_inputDevice.setCurrentIndex(index)

        if not success:
            # Note: the error message is a child of the settings dialog, so that
            # that dialog remains on top when the error message is closed
            error_message = QErrorMessage(self.settings_dialog)
            error_message.setWindowTitle("Input device error")
            error_message.showMessage(
                "Impossible to use the selected input device, reverting to the previous one"
            )

        # reset the channels
        first_channel = self.audiobackend.get_current_first_channel()
        self.settings_dialog.comboBox_firstChannel.setCurrentIndex(
            first_channel)
        second_channel = self.audiobackend.get_current_second_channel()
        self.settings_dialog.comboBox_secondChannel.setCurrentIndex(
            second_channel)

        self.ui.actionStart.setChecked(True)