示例#1
0
 def onTransition(self, event: QEvent):
     super().onTransition(event)
     # Change active session
     session_id = self.machine().s9.session_id
     logger.debug(f'[{type(self).__name__}] Change active session to {session_id}')
     with session_scope(self.database) as s:
         session = s.query(Session).filter(Session.session_id == session_id).first()
     self.machine().session = session
示例#2
0
文件: state.py 项目: smomni/cranio
 def onEntry(self, event: QEvent):
     super().onEntry(event)
     self.main_window.show()
     # Set focus on Start button so that pressing Enter will trigger it
     logger.debug('Set focus on Start button')
     self.main_window.measurement_widget.stop_button.setDefault(False)
     self.main_window.measurement_widget.start_button.setDefault(True)
     self.main_window.measurement_widget.start_button.setFocus()
示例#3
0
 def onTransition(self, event: QEvent):
     super().onTransition(event)
     with session_scope(self.database) as s:
         for e in self.machine().annotated_events:
             logger.debug(f'Remove {str(e)} from database')
             s.query(AnnotatedEvent).filter(
                 AnnotatedEvent.document_id == e.document_id
             ).filter(AnnotatedEvent.event_type == e.event_type).filter(
                 AnnotatedEvent.event_num == e.event_num
             ).delete()
示例#4
0
 def session_id(self) -> str:
     """ Return session_id of active (selected) session. If no session is selected, None is returned. """
     try:
         session_id = self.table_widget.item(
             self.table_widget.currentRow(), 0
         ).text()
     except AttributeError:
         # AttributeError: 'NoneType' object has no attribute 'text'
         session_id = None
     logger.debug(f'Active session_id = {session_id}')
     return session_id
示例#5
0
文件: window.py 项目: smomni/cranio
 def keyPressEvent(self, event):
     # Increase add count when up arrow is pressed
     if event.key() == Qt.Key_Up:
         n = self.get_add_count() + 1
         logger.debug(f'Increase add count to {n} (Up arrow pressed)')
         self.set_add_count(n)
     # Decrease add count when up arrow is pressed
     elif event.key() == Qt.Key_Down:
         n = self.get_add_count() - 1
         logger.debug(f'Decrease add count to {n} (Down arrow pressed)')
         self.set_add_count(n)
     return super().keyPressEvent(event)
示例#6
0
 def onTransition(self, event: QEvent):
     super().onTransition(event)
     logger.debug('Update document in database')
     with session_scope(self.database) as s:
         document = (
             s.query(Document)
             .filter(Document.document_id == self.document.document_id)
             .first()
         )
         document.notes = self.document.notes
         document.full_turn_count = self.document.full_turn_count
         logger.debug(str(document))
示例#7
0
def create_dummy_sensor() -> Sensor:
    """
    Create a dummy torque (Nm) sensor.

    :return: Sensor object
    """
    logger.debug('Initialize dummy torque sensor')
    sensor = Sensor()
    sensor.value_generator = random_value_generator
    ch = ChannelInfo('torque', 'Nm')
    sensor.register_channel(ch)
    return sensor
示例#8
0
 def keyPressEvent(self, event):
     # Increase active distractor when up arrow is pressed
     if event.key() == QtCore.Qt.Key_Up:
         self.distractor = self.distractor + 1
         logger.debug(
             f'Change active distractor to {self.distractor} (Up arrow pressed)'
         )
     # Decrease active distractor when down arrow is pressed
     elif event.key() == QtCore.Qt.Key_Down:
         self.distractor = self.distractor - 1
         logger.debug(
             f'Change active distractor to {self.distractor} (Down arrow pressed)'
         )
     return super().keyPressEvent(event)
示例#9
0
文件: window.py 项目: smomni/cranio
    def update_focus(self):
        """
        If no regions have been entered, set focus on Add so that pressing Enter triggers it.
        Otherwise, set focus on Ok.

        :return:
        """
        if not self.region_count():
            logger.debug('Set focus on Add button')
            self.region_plot_widget.add_button.setDefault(True)
            self.ok_button.setDefault(False)
        else:
            logger.debug('Set focus on Ok button')
            self.region_plot_widget.add_button.setDefault(False)
            self.ok_button.setDefault(True)
示例#10
0
文件: state.py 项目: smomni/cranio
 def onEntry(self, event: QEvent):
     super().onEntry(event)
     # Set default full turn count
     event_count = len(self.document.get_related_events(self.database))
     with session_scope(self.database) as s:
         sensor_info = (s.query(SensorInfo).filter(
             SensorInfo.sensor_serial_number ==
             self.document.sensor_serial_number).first())
     self.full_turn_count = event_count / float(
         sensor_info.turns_in_full_turn)
     logger.debug(
         f'Calculate default full_turn_count = {self.full_turn_count} = '
         f'{event_count} / {sensor_info.turns_in_full_turn}')
     self.notes = ''
     self.dialog.open()
示例#11
0
    def add_button_clicked(self):
        """
        Add a number of regions to the plot matching the number in the add spin box.
        The region edges are initialized so that the region widths are constant and the regions do not overlap.

        :return:
        """
        count = self.get_add_count()
        logger.debug(f'{type(self).__name__} add button clicked (add count={count})')
        if len(self.x_arr) == 0:
            logger.error('Unable to add region to empty plot')
            return 0
        if count > 0:
            x_min = min(self.x_arr)
            interval = (max(self.x_arr) - x_min) / count
            for i in range(count):
                # insert at uniform intervals
                low = x_min + i * interval
                high = x_min + (i + 1) * interval
                self.add_region([low, high])
示例#12
0
文件: state.py 项目: smomni/cranio
 def onEntry(self, event: QEvent):
     super().onEntry(event)
     # MeasurementStateTransition ensures that only one sensor is connected
     sensor = self.machine().sensor
     # Create new document
     self.document = self.create_document()
     self.main_window.measurement_widget.update_timer.start(
         self.main_window.measurement_widget.update_interval * 1000)
     # Clear plot
     logger.debug('Clear plot')
     self.main_window.measurement_widget.clear()
     # Insert sensor info and document to database
     sensor.enter_info_to_database(self.database)
     logger.debug(f'Enter document: {str(self.document)}')
     self.database.insert(self.document)
     # Kill old producer process
     if self.main_window.producer_process is not None:
         self.main_window.producer_process.join()
     # Create producer process and register connected sensor
     self.main_window.producer_process = ProducerProcess(
         'Torque producer process', document=self.document)
     self.main_window.register_sensor_with_producer()
     # Start producing!
     self.main_window.measurement_widget.producer_process.start()
     # Set focus on Start button so that pressing Enter will trigger it
     logger.debug('Set focus on Stop button')
     self.main_window.measurement_widget.start_button.setDefault(False)
     self.main_window.measurement_widget.stop_button.setDefault(True)
     self.main_window.measurement_widget.stop_button.setFocus()
示例#13
0
 def onTransition(self, event: QEvent):
     super().onTransition(event)
     # Assign annotated events and link to document
     logger.debug('Assign annotated events and link to document')
     self.annotated_events = self.sourceState().get_annotated_events()
     for e in self.annotated_events:
         e.document_id = self.document.document_id
     logger.debug('Enter annotated events to database')
     for e in self.annotated_events:
         self.database.insert(e)
         logger.debug(str(e))
示例#14
0
 def add_new(cls, patient_id: str, database: Database):
     patient = cls(patient_id=patient_id)
     logger.debug(f'Add patient {patient.patient_id} to database')
     database.insert(patient)
示例#15
0
文件: state.py 项目: smomni/cranio
 def onEntry(self, event: QEvent):
     logger.debug(f'Enter {self.name}')
示例#16
0
文件: state.py 项目: smomni/cranio
 def onExit(self, event: QEvent):
     logger.debug(f'Exit {self.name}')
示例#17
0
文件: window.py 项目: smomni/cranio
 def ok_button_clicked(self):
     logger.debug('Ok button clicked')
示例#18
0
文件: window.py 项目: smomni/cranio
 def clear_regions(self):
     logger.debug('Clear regions')
     ret = self.region_plot_widget.remove_all()
     self.update_focus()
     return ret
示例#19
0
文件: window.py 项目: smomni/cranio
 def producer_process(self, value: ProducerProcess):
     self._producer_process = value
     logger.debug(
         f'Set measurement widget producer process to {self._producer_process}'
     )
     self.measurement_widget.producer_process = self._producer_process
示例#20
0
文件: window.py 项目: smomni/cranio
 def closeEvent(self, event):
     """ User has clicked X on the dialog or QWidget.close() has been called programmatically. """
     super().closeEvent(event)
     logger.debug('X (close) button clicked')
     self.signal_close.emit()
示例#21
0
 def enter_info_to_database(cls, database: Database) -> SensorInfo:
     """ Enter copy of self.sensor_info to a database. """
     logger.debug(f'Enter sensor info: {str(cls.sensor_info)}')
     database.insert(cls.sensor_info, insert_if_exists=False)
     return cls.sensor_info
示例#22
0
def test_event_detection_state_flow(machine, qtbot):
    pytest.helpers.transition_machine_to_s1(machine)
    # Assign document
    machine.document = machine.s2.create_document()
    # Enter sensor info and document
    machine.sensor.enter_info_to_database(machine.database)
    machine.database.insert(machine.document)
    # Generate and enter data
    n = 10
    time_s = list(range(n))
    torque_Nm = list(range(n))
    machine.document.insert_time_series(machine.database, time_s, torque_Nm)
    # Trigger hidden transition from s1 to s3 (EventDetectionState)
    machine._s1_to_s3_signal.emit()
    app.processEvents()
    # Note that regions (sensor_info.turns_in_full_turn) are created on state entry
    region_count = machine.s3.region_count()
    # Remove regions
    machine.s3.dialog.clear_regions()
    machine.s3.dialog.set_add_count(0)
    assert machine.s3.region_count() == 0
    region_count = 2
    # Increase region count by up arrow press
    for i in range(region_count):
        with qtbot.waitSignal(machine.s3.signal_value_changed):
            qtbot.keyPress(machine.s3.dialog, Qt.Key_Up)
        assert machine.s3.dialog.get_add_count() == i + 1
    # Decrease region count by down arrow press
    for i in reversed(range(region_count)):
        with qtbot.waitSignal(machine.s3.signal_value_changed):
            qtbot.keyPress(machine.s3.dialog, Qt.Key_Down)
        assert machine.s3.dialog.get_add_count() == i
    # Set correct add count
    machine.s3.dialog.set_add_count(region_count)
    # No existing regions -> press enter clicks Add
    with qtbot.waitSignal(machine.s3.signal_add):
        qtbot.keyPress(machine.s3.dialog, Qt.Key_Enter)
    assert machine.s3.region_count() == region_count
    logger.debug('Regions added and asserted')
    # Regions exist -> press enter clicks Ok
    with qtbot.waitSignal(machine.s3.signal_ok):
        qtbot.keyPress(machine.s3.dialog, Qt.Key_Enter)
    assert machine.in_state(machine.s6)
    # Verify that annotated events were entered
    with session_scope(machine.database) as s:
        events = (
            s.query(AnnotatedEvent)
            .filter(AnnotatedEvent.document_id == machine.document.document_id)
            .all()
        )
        assert len(events) == region_count
        region_edits = [
            machine.s3.dialog.get_region_edit(i) for i in range(region_count)
        ]
        # Verify region edges
        for region_edit, event in zip(region_edits, events):
            assert region_edit.left_edge() == event.event_begin
            assert region_edit.right_edge() == event.event_end
    # Trigger transition back to s3 and verify that annotated events were removed
    machine.s6.signal_close.emit()
    assert machine.in_state(machine.s3)
    # Trigger transition back to s6
    with qtbot.waitSignal(machine.s3.signal_ok):
        qtbot.keyPress(machine.s3.dialog, Qt.Key_Enter)
    assert machine.in_state(machine.s6)
    # Trigger transition from s6 to s7 (i.e., click Ok on NotesWindow)
    machine.s6.signal_ok.emit()
    app.processEvents()
    # Trigger transition back to s6 (i.e., click No on "are you sure?" prompt)
    machine.s7.signal_no.emit()
    app.processEvents()
    # Enter data in NotesWindow
    notes = 'foo'
    full_turn_count = 1.2
    machine.s6.dialog.notes = notes
    machine.s6.dialog.full_turn_count = full_turn_count
    # Trigger transition from s6 to s7 (i.e., click Ok on NotesWindow)
    machine.s6.signal_ok.emit()
    app.processEvents()
    # Trigger transition from s7 to s1 (i.e., click Yes on "are you sure?" prompt)
    machine.s7.signal_yes.emit()
    app.processEvents()
    # Verify that document updates were entered to database
    with session_scope(machine.database) as s:
        document = (
            s.query(Document)
            .filter(Document.document_id == machine.document.document_id)
            .first()
        )
        assert document.notes == notes
        assert float(document.full_turn_count) == full_turn_count
示例#23
0
 def onTransition(self, event: QEvent):
     super().onTransition(event)
     patient_id = self.machine().s0_1.dialog.textValue()
     logger.debug(f'Add patient "{patient_id}" to database')
     Patient.add_new(patient_id=patient_id, database=self.database)
示例#24
0
文件: window.py 项目: smomni/cranio
 def connect_dummy_sensor(self):
     self.sensor = create_dummy_sensor()
     logger.debug('Connected dummy sensor')
示例#25
0
文件: window.py 项目: smomni/cranio
 def connect_imada_sensor(self):
     self.sensor = Imada()
     logger.debug(
         f'Connected Imada sensor with serial number "{self.sensor.sensor_info.sensor_serial_number}"'
     )