Пример #1
0
    def __init__(self, *args, **kwargs):
        QWidget.__init__(self, *args, **kwargs)
        self.simulationInterval = None
        self.updateInterval = None
        self.runTime = None

        self.modelRoot = None
        self.dataRoot = None
        self.runner = Runner()
        self.resetAndRunAction = None
        self.stopAction = None
        self.continueAction = None
        self.preferences = preferences
        self.currentSimulationRuntime = None
        self.modelType = None
        self.simulationRuntime = None
        self.schedulerToolBar = self.getSchedulerToolBar()
        self.runner.simulationProgressed.connect(
            self.updateCurrentSimulationRuntime)
        self.continueFlag = False
        self.preferences.applyChemicalSettings.connect(self.resetSimulation)
Пример #2
0
    def __init__(self, *args, **kwargs):
        QtGui.QWidget.__init__(self, *args, **kwargs)
        self.simulationInterval = None
        self.updateInterval     = None
        self.runTime            = None

        self.modelRoot                  = None
        self.dataRoot                   = None
        self.runner                     = Runner()
        self.resetAndRunAction          = None
        self.stopAction                 = None
        self.continueAction             = None
        self.preferences                = preferences
        self.currentSimulationRuntime   = None
        self.modelType                  = None
        self.simulationRuntime          = None
        self.schedulerToolBar           = self.getSchedulerToolBar()
        self.runner.simulationProgressed.connect(self.updateCurrentSimulationRuntime)
        self.continueFlag               = False
        self.preferences.applyChemicalSettings.connect(self.resetSimulation)
Пример #3
0
class SchedulingWidget(QtGui.QWidget):
    """Widget for scheduling.

    Important member fields:

    runner - object to run/pause/continue simulation. Whenever
    `updateInterval` time has been simulated this object sends an
    `update()` signal. This can be connected to other objects to
    update their data.

    SIGNALS:
    resetAndRun(tickDt, tickTargets, simtime, updateInterval)

        tickDt: dict mapping tick nos to dt
        tickTargets: dict mapping ticks to target paths
        simtime: total simulation runtime
        updateInterval: interval between update signals are to be emitted.

    simtimeExtended(simtime)
        emitted when simulation time is increased by user.

    """

    resetAndRun = QtCore.pyqtSignal(dict, dict, float, float, name='resetAndRun')
    simtimeExtended = QtCore.pyqtSignal(float, name='simtimeExtended')
    continueRun = QtCore.pyqtSignal(float, float, name='continueRun')

    def __init__(self, *args, **kwargs):
        QtGui.QWidget.__init__(self, *args, **kwargs)
        self.simulationInterval = None
        self.updateInterval     = None
        self.runTime            = None

        self.modelRoot                  = None
        self.dataRoot                   = None
        self.runner                     = Runner()
        self.resetAndRunAction          = None
        self.stopAction                 = None
        self.continueAction             = None
        self.preferences                = preferences
        self.currentSimulationRuntime   = None
        self.modelType                  = None
        self.simulationRuntime          = None
        self.schedulerToolBar           = self.getSchedulerToolBar()
        self.runner.simulationProgressed.connect(self.updateCurrentSimulationRuntime)
        self.continueFlag               = False
        self.preferences.applyChemicalSettings.connect(self.resetSimulation)

    def updateCurrentSimulationRuntime(self, time):
        self.currentSimulationRuntime.setText(str(time))

    def getToolBars(self):
        return [self.schedulerToolBar]

    def getSchedulerToolBar(self):

        bar = QToolBar("Run", self)

        self.resetAction = bar.addAction( 
                QIcon( os.path.join( config.MOOSE_ICON_DIR, 'reset.png' ) )
                , 'Reset'
                , self.resetSimulation
                )
        self.resetAction.setToolTip('Reset simulation.')

        self.runAction = bar.addAction( 
                QIcon( os.path.join( config.MOOSE_ICON_DIR, 'run.png') )
                , 'Run'
                , self.runSimulation
                )
        self.runAction.setToolTip('Run simulation.')


        self.stopAction = bar.addAction( 
                QIcon( os.path.join( config.MOOSE_ICON_DIR,  'stop.png') )
                , 'Stop'
                , self.runner.togglePauseSimulation
                )
        self.stopAction.setToolTip('Stop simulation.')

        bar.addSeparator()

        runtimeLabel = QLabel('Run for')
        self.simulationRuntime = QLineEdit()
        self.simulationRuntime.setValidator(QDoubleValidator())
        self.simulationRuntime.setFixedWidth(75)
        bar.addWidget(runtimeLabel)
        bar.addWidget(self.simulationRuntime)
        bar.addWidget(QLabel(' (s)'))
        bar.addSeparator()

        #: current time
        self.currentSimulationRuntime = QLineEdit() # 6 digits
        self.currentSimulationRuntime.setToolTip('Current simulation runtime.')
        self.currentSimulationRuntime.setFixedWidth(75)
        self.currentSimulationRuntime.setValidator(QDoubleValidator())
        self.currentSimulationRuntime.setText("0.0")
        self.currentSimulationRuntime.setReadOnly(True)

        # self.runner.currentTime.connect(self.currentTimeWidget.display)
        bar.addWidget(QLabel("Current Time : "))
        bar.addWidget(self.currentSimulationRuntime)
        bar.addWidget(QLabel(" (s)"))

        bar.addSeparator()

        self.preferencesButton = QToolButton()
        self.preferencesButton.setText("Preferences")
        self.preferencesButton.clicked.connect(self.preferencesToggler)

        bar.addWidget(self.preferencesButton)
        return bar


    def continueSimulation(self):
        self.runner.continueSimulation( self.runTime
                                      , self.updateInterval
                                      , self.simulationInterval
                                      )
        self.simulationRuntime.setText(str(float(self.simulationRuntime.text()) + self.runTime))

    def resetSimulation(self):
        self.setParameters()
        try:
            self.runtime = float(runtime)
        except:
            self.runtime = 100.0
        # print(self.runTime)
        # print(self.updateInterval)
        # print(self.simulationInterval)
        self.currentSimulationRuntime.setText("0.0")
        self.checkConsistency()
        # self.preferences.setChemicalClocks()
        self.simulationRuntime.setText(str(self.runTime))
        self.runner.resetSimulation( self.runTime
                                   , self.updateInterval
                                   , self.simulationInterval
                                   )
        self.continueFlag               = False

    def runSimulation(self):
        if self.modelType == CHEMICAL_MODEL:
            compt = moose.wildcardFind(self.modelRoot+'/##[ISA=ChemCompt]')
            if not moose.exists(compt[0].path+'/stoich'):
                chemPref = self.preferences.getChemicalPreferences()
                solver = chemPref["simulation"]["solver"]
                addSolver(self.modelRoot,solver)
            status = self.solverStatus()
            #print "status ",status
                   # if status != 0 or status == -1:
            #     return
            if status == None or int(status) == -1 or int(status) == 0:
                #allow the model to Run
                pass
            else:
                # if something is dangling or solver is not set then return
                return
        runtime = str(self.simulationRuntime.text())
        try:
            self.runtime = float(runtime)
        except:
            self.runtime = 100.0
            self.simulationRuntime.setText("100.0")
        self.checkConsistency()
        self.continueSimulation = True
        self.runner.runSimulation(self.runtime)

    def setParameters(self):
        if self.modelType == ELECTRICAL_MODEL:
            self.setElectricalParameters()
        elif self.modelType == CHEMICAL_MODEL:
            self.setChemicalParameters()

    def setChemicalParameters(self):
        chemicalPreferences   = self.preferences.getChemicalPreferences()
        self.preferences.initializeChemicalClocks()
        self.updateInterval     = chemicalPreferences["simulation"]["gui-update-interval"]
        self.simulationInterval = chemicalPreferences["simulation"]["simulation-dt"]
        if str(self.simulationRuntime.text()) == "":
            self.simulationRuntime.setText(str(chemicalPreferences["simulation"]["default-runtime"]))
        self.runTime            = float(self.simulationRuntime.text())
        self.solver             = chemicalPreferences["simulation"]["solver"]

    def setElectricalParameters(self):
        electricalPreferences   = self.preferences.getElectricalPreferences()
        self.preferences.initializeElectricalClocks()
        self.updateInterval     = electricalPreferences["simulation"]["gui-update-interval"]
        self.simulationInterval = electricalPreferences["simulation"]["simulation-dt"]
        if str(self.simulationRuntime.text()) == "":
            self.simulationRuntime.setText(str(electricalPreferences["simulation"]["default-runtime"]))
        self.runTime            = float(self.simulationRuntime.text())
        self.solver             = electricalPreferences["simulation"]["solver"]

    def checkConsistency(self):
        if self.updateInterval < self.simulationInterval :
            self.updateInterval = self.simulationInterval
        if self.runTime < self.updateInterval :
            self.runTime = self.updateInterval
        return True

    def solverStatus(self):
        compt = moose.wildcardFind(self.modelRoot+'/##[ISA=ChemCompt]')
        if not moose.exists(compt[0].path+'/stoich'):
            return None
        else:
            stoich = moose.Stoich(compt[0].path+'/stoich')
            status = int(stoich.status)
            # print("Status =>", status)
            if status == -1:
                QtGui.QMessageBox.warning(None,"Could not Run the model","Warning: Reaction path not yet assigned.\n ")
                return -1
            if status == 1:
                QtGui.QMessageBox.warning(None,"Could not Run the model","Warning: Missing a reactant in a Reac or Enz.\n ")
                return 1
            elif status == 2:
                QtGui.QMessageBox.warning(None,"Could not Run the model","Warning: Missing a substrate in an MMenz.\n ")
                return 2
            elif status == 3:
                QtGui.QMessageBox.warning(None,"Could not Run the model","Warning: Missing substrates as well as reactants.\n ")
                return 3
            elif status == 4:
                QtGui.QMessageBox.warning(None,"Could not Run the model"," Warning: Compartment not defined.\n ")
                return 4
            elif status == 8:
                QtGui.QMessageBox.warning(None,"Could not Run the model","Warning: Neither Ksolve nor Dsolve defined.\n ")
                return 8
            elif status == 16:
                QtGui.QMessageBox.warning(None,"Could not Run the model","Warning: No objects found on path.\n ")
                return 16
            elif status == 0:
                print("Successfully built stoichiometry matrix.\n ")
                # moose.reinit()
                return 0

    def __getAdvanceOptionsButton(self):
        icon = QtGui.QIcon(os.path.join(config.settings[config.KEY_ICON_DIR],'arrow.png'))
        # self.advancedOptionsButton.setIcon(QtGui.QIcon(icon))
        # self.advancedOptionsButton.setToolButtonStyle( Qt.ToolButtonTextBesideIcon );
        return self.advancedOptionsButton

    def preferencesToggler(self):
        visibility = not self.preferences.getView().isVisible()
        self.preferences.getView().setVisible(visibility)

    def continueSlot(self):
        pass

    def updateCurrentTime(self):
        sys.stdout.flush()
        self.currentTimeWidget.dispay(str(moose.Clock('/clock').currentTime))

    def updateTextFromTick(self, tickNo):
        tick = moose.vector('/clock/tick')[tickNo]
        widget = self.tickListWidget.layout().itemAtPosition(tickNo + 1, 1).widget()
        if widget is not None and isinstance(widget, QtGui.QLineEdit):
            widget.setText(str(tick.dt))

    def updateFromMoose(self):
        """Update the tick dt from the tick objects"""
        ticks = moose.vector('/clock/tick')
        # Items at position 0 are the column headers, hence ii+1
        for ii in range(ticks[0].localNumField):
            self.updateTextFromTick(ii)
        self.updateCurrentTime()

    def getSimTime(self):
        try:
            time = float(str(self.simtimeEdit.text()))
            return time
        except ValueError as e:
            QtGui.QMessageBox.warning(self, 'Invalid value', 'Specified runtime was meaningless.')
        return 0


    def setDataRoot(self, root='/data'):
        self.dataRoot = moose.element(root).path

    def setModelRoot(self, root='/model'):
        self.modelRoot = moose.element(root).path
        self.setModelType()

    def setModelType(self):
        if moose.exists(self.modelRoot + "/model/cells"):
            self.modelType = ELECTRICAL_MODEL
        else:
            self.modelType = CHEMICAL_MODEL
        self.resetSimulation()
Пример #4
0
class SchedulingWidget(QWidget):
    """Widget for scheduling.

    Important member fields:

    runner - object to run/pause/continue simulation. Whenever
    `updateInterval` time has been simulated this object sends an
    `update()` signal. This can be connected to other objects to
    update their data.

    SIGNALS:
    resetAndRun(tickDt, tickTargets, simtime, updateInterval)

        tickDt: dict mapping tick nos to dt
        tickTargets: dict mapping ticks to target paths
        simtime: total simulation runtime
        updateInterval: interval between update signals are to be emitted.

    simtimeExtended(simtime)
        emitted when simulation time is increased by user.

    """

    resetAndRun = QtCore.pyqtSignal(dict,
                                    dict,
                                    float,
                                    float,
                                    name='resetAndRun')
    simtimeExtended = QtCore.pyqtSignal(float, name='simtimeExtended')
    continueRun = QtCore.pyqtSignal(float, float, name='continueRun')

    def __init__(self, *args, **kwargs):
        QWidget.__init__(self, *args, **kwargs)
        self.simulationInterval = None
        self.updateInterval = None
        self.runTime = None

        self.modelRoot = None
        self.dataRoot = None
        self.runner = Runner()
        self.resetAndRunAction = None
        self.stopAction = None
        self.continueAction = None
        self.preferences = preferences
        self.currentSimulationRuntime = None
        self.modelType = None
        self.simulationRuntime = None
        self.schedulerToolBar = self.getSchedulerToolBar()
        self.runner.simulationProgressed.connect(
            self.updateCurrentSimulationRuntime)
        self.continueFlag = False
        self.preferences.applyChemicalSettings.connect(self.resetSimulation)

    def updateCurrentSimulationRuntime(self, time):
        self.currentSimulationRuntime.setText(str(time))

    def getToolBars(self):
        return [self.schedulerToolBar]

    def getSchedulerToolBar(self):

        bar = QToolBar("Run", self)

        self.resetAction = bar.addAction(
            QtGui.QIcon(os.path.join(config.MOOSE_ICON_DIR, 'reset.png')),
            'Reset', self.resetSimulation)
        self.resetAction.setToolTip('Reset simulation.')

        self.runAction = bar.addAction(
            QtGui.QIcon(os.path.join(config.MOOSE_ICON_DIR, 'run.png')), 'Run',
            self.runSimulation)
        self.runAction.setToolTip('Run simulation.')

        self.stopAction = bar.addAction(
            QtGui.QIcon(os.path.join(config.MOOSE_ICON_DIR, 'stop.png')),
            'Stop', self.runner.togglePauseSimulation)
        self.stopAction.setToolTip('Stop simulation.')

        bar.addSeparator()

        runtimeLabel = QLabel('Run for')
        self.simulationRuntime = QLineEdit()
        self.simulationRuntime.setValidator(QtGui.QDoubleValidator())
        self.simulationRuntime.setFixedWidth(75)
        bar.addWidget(runtimeLabel)
        bar.addWidget(self.simulationRuntime)
        bar.addWidget(QLabel(' (s)'))
        bar.addSeparator()

        #: current time
        self.currentSimulationRuntime = QLineEdit()  # 6 digits
        self.currentSimulationRuntime.setToolTip('Current simulation runtime.')
        self.currentSimulationRuntime.setFixedWidth(75)
        self.currentSimulationRuntime.setValidator(QtGui.QDoubleValidator())
        self.currentSimulationRuntime.setText("0.0")
        self.currentSimulationRuntime.setReadOnly(True)

        # self.runner.currentTime.connect(self.currentTimeWidget.display)
        bar.addWidget(QLabel("Current Time : "))
        bar.addWidget(self.currentSimulationRuntime)
        bar.addWidget(QLabel(" (s)"))

        bar.addSeparator()

        self.preferencesButton = QToolButton()
        self.preferencesButton.setText("Preferences")
        self.preferencesButton.clicked.connect(self.preferencesToggler)

        bar.addWidget(self.preferencesButton)
        return bar

    def continueSimulation(self):
        self.runner.continueSimulation(self.runTime, self.updateInterval,
                                       self.simulationInterval)
        self.simulationRuntime.setText(
            str(float(self.simulationRuntime.text()) + self.runTime))

    def resetSimulation(self):
        self.setParameters()
        try:
            self.runtime = float(runtime)
        except:
            self.runtime = 100.0
        # print(self.runTime)
        # print(self.updateInterval)
        # print(self.simulationInterval)
        self.currentSimulationRuntime.setText("0.0")
        self.checkConsistency()
        # self.preferences.setChemicalClocks()
        self.simulationRuntime.setText(str(self.runTime))
        self.runner.resetSimulation(self.runTime, self.updateInterval,
                                    self.simulationInterval)
        self.continueFlag = False

    def runSimulation(self):
        if self.modelType == CHEMICAL_MODEL:
            compt = moose.wildcardFind(self.modelRoot + '/##[ISA=ChemCompt]')
            if not moose.exists(compt[0].path + '/stoich'):
                chemPref = self.preferences.getChemicalPreferences()
                solver = chemPref["simulation"]["solver"]
                mooseAddChemSolver(self.modelRoot, solver)
            status = self.solverStatus()
            #print "status ",status
            # if status != 0 or status == -1:
            #     return
            if status == None or int(status) == -1 or int(status) == 0:
                #allow the model to Run
                pass
            else:
                # if something is dangling or solver is not set then return
                return
        runtime = str(self.simulationRuntime.text())
        try:
            self.runtime = float(runtime)
        except:
            self.runtime = 100.0
            self.simulationRuntime.setText("100.0")
        self.checkConsistency()
        self.continueSimulation = True
        self.runner.runSimulation(self.runtime)

    def setParameters(self):
        if self.modelType == ELECTRICAL_MODEL:
            self.setElectricalParameters()
        elif self.modelType == CHEMICAL_MODEL:
            self.setChemicalParameters()

    def setChemicalParameters(self):
        chemicalPreferences = self.preferences.getChemicalPreferences()
        self.preferences.initializeChemicalClocks()
        self.updateInterval = chemicalPreferences["simulation"][
            "gui-update-interval"]
        self.simulationInterval = chemicalPreferences["simulation"][
            "simulation-dt"]
        if str(self.simulationRuntime.text()) == "":
            self.simulationRuntime.setText(
                str(chemicalPreferences["simulation"]["default-runtime"]))
        self.runTime = float(self.simulationRuntime.text())
        self.solver = chemicalPreferences["simulation"]["solver"]

    def setElectricalParameters(self):
        electricalPreferences = self.preferences.getElectricalPreferences()
        self.preferences.initializeElectricalClocks()
        self.updateInterval = electricalPreferences["simulation"][
            "gui-update-interval"]
        self.simulationInterval = electricalPreferences["simulation"][
            "simulation-dt"]
        if str(self.simulationRuntime.text()) == "":
            self.simulationRuntime.setText(
                str(electricalPreferences["simulation"]["default-runtime"]))
        self.runTime = float(self.simulationRuntime.text())
        self.solver = electricalPreferences["simulation"]["solver"]

    def checkConsistency(self):
        if self.updateInterval < self.simulationInterval:
            self.updateInterval = self.simulationInterval
        if self.runTime < self.updateInterval:
            self.runTime = self.updateInterval
        return True

    def solverStatus(self):
        compt = moose.wildcardFind(self.modelRoot + '/##[ISA=ChemCompt]')
        if not moose.exists(compt[0].path + '/stoich'):
            return None
        else:
            stoich = moose.Stoich(compt[0].path + '/stoich')
            status = int(stoich.status)
            # Flag to track status of Stoich object.
            # -1: No path yet assigned.
            # 0: Success
            # 1: Warning: Missing reactant in Reac or Enz
            # 2: Warning: Missing substrate in MMenz
            # 4: Warning: Compartment not defined
            # 8: Warning: Neither Ksolve nor Dsolve defined
            # 16: Warning: No objects found on path

            # print("Status =>", status)

            if status == 1 or status == 2:
                nameRE = "\n\nclassName --> parentName/groupName --> name  "
                for res in moose.wildcardFind(self.modelRoot +
                                              '/##[ISA=ReacBase],' +
                                              self.modelRoot +
                                              '/##[ISA=EnzBase]'):
                    if not len(res.neighbors["sub"]) or not len(
                            res.neighbors["prd"]):
                        nameRE = nameRE + "\n " + res.className + " --> " + res.parent.name + " --> " + res.name

            if status == -1:
                QMessageBox.warning(
                    None, "Could not Run the model",
                    "Warning: Reaction path not yet assigned.\n ")
                return -1
            if status == 1:
                #QMessageBox.warning(None,"Could not Run the model","Warning: Missing a reactant in a Reac or Enz.\n ")
                QMessageBox.warning(
                    None, "Could not Run the model",
                    "Warning: Missing a reactant in %s " % (nameRE))
                return 1
            elif status == 2:
                QMessageBox.warning(
                    None, "Could not Run the model",
                    "Warning: Missing a substrate in an MMenz %s " % (nameRE))
                #QMessageBox.warning(None,"Could not Run the model","Warning: Missing a substrate in an MMenz.\n ")
                return 2
            elif status == 4:
                QMessageBox.warning(None, "Could not Run the model",
                                    " Warning: Compartment not defined.\n ")
                return 4
            elif status == 8:
                QMessageBox.warning(
                    None, "Could not Run the model",
                    "Warning: Neither Ksolve nor Dsolve defined.\n ")
                return 8
            elif status == 16:
                QMessageBox.warning(None, "Could not Run the model",
                                    "Warning: No objects found on path.\n ")
                return 16
            elif status == 0:
                print("Successfully built stoichiometry matrix.\n ")
                # moose.reinit()
                return 0

    def preferencesToggler(self):
        visibility = not self.preferences.getView().isVisible()
        self.preferences.getView().setVisible(visibility)

    def continueSlot(self):
        pass

    def updateCurrentTime(self):
        sys.stdout.flush()
        self.currentTimeWidget.dispay(str(moose.Clock('/clock').currentTime))

    def updateTextFromTick(self, tickNo):
        tick = moose.vector('/clock/tick')[tickNo]
        widget = self.tickListWidget.layout().itemAtPosition(tickNo + 1,
                                                             1).widget()
        if widget is not None and isinstance(widget, QLineEdit):
            widget.setText(str(tick.dt))

    def updateFromMoose(self):
        """Update the tick dt from the tick objects"""
        ticks = moose.vector('/clock/tick')
        # Items at position 0 are the column headers, hence ii+1
        for ii in range(ticks[0].localNumField):
            self.updateTextFromTick(ii)
        self.updateCurrentTime()

    def getSimTime(self):
        try:
            time = float(str(self.simtimeEdit.text()))
            return time
        except ValueError:
            QMessageBox.warning(self, 'Invalid value',
                                'Specified runtime was meaningless.')
        return 0.0

    def setDataRoot(self, root='/data'):
        self.dataRoot = moose.element(root).path

    def setModelRoot(self, root='/model'):
        self.modelRoot = moose.element(root).path
        self.setModelType()

    def setModelType(self):
        if moose.exists(self.modelRoot + "/model/cells"):
            self.modelType = ELECTRICAL_MODEL
        else:
            self.modelType = CHEMICAL_MODEL
        self.resetSimulation()