Loops and Transitions
By default, FociStm / PatternStm play back the same pattern sequence infinitely.
To make the playback count finite, proceed as follows.
Finite loops
Section titled “Finite loops”The playback count is specified with loop_behavior of FociStmOption and the like.
LoopBehavior::Infinite (default) loops infinitely, while LoopBehavior::Finite(n) plays back n times (up to 65535 times) and then stops.
Note that on stopping, the last pattern continues to be output.
An important point is that a finite loop takes effect only when switching to a bank different from the current one.
// Play the circular motion only 3 times, then stop.// A finite loop (and non-immediate transition) only fires when switching to a// different bank, so write to bank B1 instead of the current B0.let mut builder = client.datagram_builder();builder.push(FociStm::new( 50.0 * Hz, &foci, FociStmOption { loop_behavior: LoopBehavior::Finite(NonZeroU16::new(3).unwrap()), bank: PatternBank::B1, transition_mode: TransitionMode::SyncIdx, ..Default::default() },));for frame in &builder.build()? { client.send_checked(frame).await?;}# Play the circular motion only 3 times, then stop.# A finite loop (and non-immediate transition) only fires when switching to a# different bank, so write to bank B1 instead of the current B0.builder = client.datagram_builder()builder.push( FociStm( 50.0 * Hz, foci, FociStmOption( loop_behavior=LoopBehavior.Finite(3), bank=PatternBank.B1, transition_mode=TransitionMode.SyncIdx, ), ))for frame in builder.build(): await client.send_checked(frame)// Play the circular motion only 3 times, then stop.// A finite loop (and non-immediate transition) only fires when switching to a// different bank, so write to bank B1 instead of the current B0.var builder = client.DatagramBuilder();builder.Push(new FociStm( 50.0f * Hz, foci, new FociStmOption( bank: PatternBank.B1, loopBehavior: LoopBehavior.Finite(3), transitionMode: TransitionMode.SyncIdx )));foreach (var frame in builder.Build()){ await client.SendCheckedAsync(frame);}Transition timing
Section titled “Transition timing”The timing at which the playback target switches to a bank is specified with transition_mode.
The modes that can be used are constrained by the loop setting (loop_behavior) of the destination bank.
Modes available when the destination is an infinite loop.
Immediate(default): switches the bank immediately after the write.Ext: extended mode. Automatically switches to the next bank when playback within the bank finishes.
Modes available when the destination is a finite loop.
SyncIdx: switches at the timing when the playback index of the target bank returns to 0.SysTime(DcSysTime): switches at the specified DC system time.Gpio(GpioIn): switches on the trigger of the specified GPIO input pin.
As with the loop setting, the transition timing takes effect only when a bank is switched.
For fine-grained control such as preloading the next output into another bank in advance and switching at an arbitrary timing, refer to the low-level commands in the API reference.