def test_split_with_final_row_zero_repeat(self):
        seq_rows = SequencerRows()
        seq_rows.add_seq_entry(4, Trigger.POSB_LT, 400, 1000, 0, 1, 50)
        seq_rows.add_seq_entry(3, Trigger.BITA_0, 300, 2000, 1, 0, 100)
        seq_rows.add_seq_entry(0, Trigger.IMMEDIATE, 300, 2000, 0, 1, 100)

        expected = SequencerRows()  # End of scan - no switch delay
        expected.add_seq_entry(4, Trigger.POSB_LT, 400, 1000, 0, 1, 50)
        expected.add_seq_entry(3, Trigger.BITA_0, 300, 2000, 1, 0, 100)
        expected.add_seq_entry(0, Trigger.IMMEDIATE, 300, 2000, 0, 1, 100)

        remainder = seq_rows.split(3)

        assert seq_rows.as_tuples() == expected.as_tuples()
        assert remainder.as_tuples() == SequencerRows().as_tuples()
    def test_split_below_max_table_size(self):
        seq_rows = SequencerRows()
        seq_rows.add_seq_entry(4, Trigger.POSB_LT, 400, 1000, 0, 1, 50)
        seq_rows.add_seq_entry(3, Trigger.BITA_0, 300, 2000, 1, 0, 100)

        expected = SequencerRows()
        expected.add_seq_entry(4, Trigger.POSB_LT, 400, 1000, 0, 1, 50)
        expected.add_seq_entry(2, Trigger.BITA_0, 300, 2000, 1, 0, 100)
        expected.add_seq_entry(1, Trigger.BITA_0, 300, 2000, 1, 0,
                               100 + SEQ_TABLE_SWITCH_DELAY)

        remainder = seq_rows.split(100)

        assert seq_rows.as_tuples() == expected.as_tuples()
        assert remainder.as_tuples() == SequencerRows().as_tuples()
    def test_configure_stepped(self):
        xs = LineGenerator("x", "mm", 0.0, 0.3, 4)
        ys = LineGenerator("y", "mm", 0.0, 0.2, 3)
        generator = CompoundGenerator([ys, xs], [], [], 1.0, continuous=False)
        generator.prepare()
        self.set_motor_attributes()
        self.set_attributes(self.child, rowTrigger="Motion Controller")
        self.set_attributes(self.child_seq1, bita="TTLIN1.VAL")
        self.set_attributes(self.child_seq2, bita="TTLIN1.VAL")
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move)
        # Triggers
        B0 = Trigger.BITA_0
        B1 = Trigger.BITA_1
        IT = Trigger.IMMEDIATE
        # Half a frame
        hf = 62500000
        expected = SequencerRows()
        for i in range(11):
            expected.add_seq_entry(1, B1, 0, hf, 1, 0)
            expected.add_seq_entry(1, B0, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(1, B1, 0, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_configure_motion_controller_trigger(self):
        xs = LineGenerator("x", "mm", 0.0, 0.3, 4, alternate=True)
        ys = LineGenerator("y", "mm", 0.0, 0.1, 2)
        generator = CompoundGenerator([ys, xs], [], [], 1.0)
        self.set_motor_attributes()
        self.set_attributes(self.child, rowTrigger="Motion Controller")
        self.set_attributes(self.child_seq1, bita="TTLIN1.VAL")
        self.set_attributes(self.child_seq2, bita="TTLIN1.VAL")
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move)
        # Triggers
        B0 = Trigger.BITA_0
        B1 = Trigger.BITA_1
        IT = Trigger.IMMEDIATE
        # Half a frame
        hf = 62500000
        expected = SequencerRows()
        expected.add_seq_entry(count=1,
                               trigger=B1,
                               position=0,
                               half_duration=hf,
                               live=1,
                               dead=0)
        expected.add_seq_entry(3, IT, 0, hf, 1, 0)
        expected.add_seq_entry(1, B0, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(1, B1, 0, hf, 1, 0)
        expected.add_seq_entry(3, IT, 0, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_configure_continuous(self):
        xs = LineGenerator("x", "mm", 0.0, 0.3, 4, alternate=True)
        ys = LineGenerator("y", "mm", 0.0, 0.1, 2)
        generator = CompoundGenerator([ys, xs], [], [], 1.0)
        self.set_motor_attributes()
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move)
        # Triggers
        GT = Trigger.POSA_GT
        IT = Trigger.IMMEDIATE
        LT = Trigger.POSA_LT
        # Half a frame
        hf = 62500000
        # Half how long to be blind for
        hb = 22500000
        expected = SequencerRows()
        expected.add_seq_entry(count=1,
                               trigger=LT,
                               position=50,
                               half_duration=hf,
                               live=1,
                               dead=0)
        expected.add_seq_entry(3, IT, 0, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hb, 0, 1)
        expected.add_seq_entry(1, GT, -350, hf, 1, 0)
        expected.add_seq_entry(3, IT, 0, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_split_with_final_row_one_repeat(self):
        seq_rows = SequencerRows()
        seq_rows.add_seq_entry(4, Trigger.POSB_LT, 400, 1000, 0, 1, 50)
        seq_rows.add_seq_entry(3, Trigger.BITA_0, 300, 2000, 1, 0, 100)
        seq_rows.add_seq_entry(1, Trigger.POSB_LT, 300, 2000, 0, 1, 100)

        expected = SequencerRows()
        expected.add_seq_entry(4, Trigger.POSB_LT, 400, 1000, 0, 1, 50)
        expected.add_seq_entry(3, Trigger.BITA_0, 300, 2000, 1, 0, 100)
        expected.add_seq_entry(1, Trigger.POSB_LT, 300, 2000, 0, 1,
                               100 + SEQ_TABLE_SWITCH_DELAY)

        remainder = seq_rows.split(3)

        assert seq_rows.as_tuples() == expected.as_tuples()
        assert remainder.as_tuples() == SequencerRows().as_tuples()
    def test_configure_with_zero_points(self):
        xs = LineGenerator("x", "mm", 0.0, 0.3, 4, alternate=True)
        ys = LineGenerator("y", "mm", 0.0, 0.1, 2)
        generator = CompoundGenerator([ys, xs], [], [], 1.0)
        self.set_motor_attributes()
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move, steps=0)
        # Triggers
        IT = Trigger.IMMEDIATE
        expected = SequencerRows()
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_configure_with_delay_after(self):
        # a test to show that delay_after inserts a "loop_back" turnaround
        delay = 1.0
        x_steps, y_steps = 3, 2
        xs = LineGenerator("x", "mm", 0.0, 0.5, x_steps, alternate=True)
        ys = LineGenerator("y", "mm", 0.0, 0.1, y_steps)
        generator = CompoundGenerator([ys, xs], [], [], 1.0, delay_after=delay)
        self.set_motor_attributes()
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move)
        # Triggers
        GT = Trigger.POSA_GT
        IT = Trigger.IMMEDIATE
        LT = Trigger.POSA_LT
        # Half a frame
        hf = 62500000
        # Half how long to be blind for a single point
        hfb = 55625000
        # Half how long to be blind for end of row
        hrb = 56500000
        expected = SequencerRows()
        expected.add_seq_entry(count=1,
                               trigger=LT,
                               position=125,
                               half_duration=hf,
                               live=1,
                               dead=0)
        expected.add_seq_entry(1, IT, 0, hfb, 0, 1)
        expected.add_seq_entry(1, LT, -125, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hfb, 0, 1)
        expected.add_seq_entry(1, LT, -375, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hrb, 0, 1)
        expected.add_seq_entry(1, GT, -625, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hfb, 0, 1)
        expected.add_seq_entry(1, GT, -375, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hfb, 0, 1)
        expected.add_seq_entry(1, GT, -125, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_acquire_scan(self):
        generator = CompoundGenerator([StaticPointGenerator(size=5)], [], [],
                                      1.0)
        generator.prepare()

        seq_rows = self.get_sequencer_rows(generator, [])
        # Triggers
        IT = Trigger.IMMEDIATE
        # Half a frame
        hf = 62500000
        expected = SequencerRows()
        expected.add_seq_entry(count=5,
                               trigger=IT,
                               position=0,
                               half_duration=hf,
                               live=1,
                               dead=0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_configure_with_one_point(self):
        xs = LineGenerator("x", "mm", 0.0, 0.3, 4, alternate=True)
        ys = LineGenerator("y", "mm", 0.0, 0.1, 2)
        generator = CompoundGenerator([ys, xs], [], [], 1.0)
        self.set_motor_attributes()
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move, steps=1)
        # Triggers
        IT = Trigger.IMMEDIATE
        LT = Trigger.POSA_LT
        # Half a frame
        hf = 62500000
        expected = SequencerRows()
        expected.add_seq_entry(count=1,
                               trigger=LT,
                               position=50,
                               half_duration=hf,
                               live=1,
                               dead=0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()
    def test_configure_pcomp_row_trigger_with_single_point_rows(self):
        x_steps, y_steps = 1, 5
        xs = LineGenerator("x", "mm", 0.0, 0.5, x_steps, alternate=True)
        ys = LineGenerator("y", "mm", 0.0, 4, y_steps)
        generator = CompoundGenerator([ys, xs], [], [], 1.0)
        self.set_motor_attributes()
        axes_to_move = ["x", "y"]

        seq_rows = self.get_sequencer_rows(generator, axes_to_move)
        # Triggers
        GT = Trigger.POSA_GT
        LT = Trigger.POSA_LT
        IT = Trigger.IMMEDIATE
        # Half a frame
        hf = 62500000
        # Half blind
        hb = 75000000
        expected = SequencerRows()
        expected.add_seq_entry(count=1,
                               trigger=LT,
                               position=0,
                               half_duration=hf,
                               live=1,
                               dead=0)
        expected.add_seq_entry(1, IT, 0, hb, 0, 1)
        expected.add_seq_entry(1, GT, -500, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hb, 0, 1)
        expected.add_seq_entry(1, LT, 0, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hb, 0, 1)
        expected.add_seq_entry(1, GT, -500, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, hb, 0, 1)
        expected.add_seq_entry(1, LT, 0, hf, 1, 0)
        expected.add_seq_entry(1, IT, 0, MIN_PULSE, 0, 1)
        expected.add_seq_entry(0, IT, 0, MIN_PULSE, 0, 0)

        assert seq_rows.as_tuples() == expected.as_tuples()