I am almost there!
I want to initiate a single button contact to move a servo tilt head from a down (home position) to an up position with ~ 7 second delay and then back to down (home position) and then stop until the button is pushed again. When I initiate a Frame_0, Frame_1 and Frame_2 play sequence using the Maestro Control Center GUI this is exactly what happens each time I select play.
I used Copy Sequence to Script and added a loop for the switch to initiate the sequence. When I select Run Script and push the momentary push button switch the sequence begins but when the tilt head returns to the home position the sequence starts all over again in a loop until I select Stop Script.
I want the sequence to stop with the tilt head at the home position and not begin again until I initiate a switch to start the sequence. See the script below for whatever script needs to be modified or added to accomplish this.
# Sequence 0
begin
0 get_position 200 greater_than while #wait in while loop until button connected to channel 0 is pushed
repeat
begin
500 7616 0 0 0 0 0
0 0 0 0 0 frame_1..11 # Frame 0
8000 3968 frame_1 # Frame 1
500 7616 frame_1 # Frame 2
repeat
sub frame_1..11
11 servo
10 servo
9 servo
8 servo
7 servo
6 servo
5 servo
4 servo
3 servo
2 servo
1 servo
delay
return
sub frame_1
1 servo
delay
return
Hello.
Thank you for posting your script. You are very close to getting the behavior you’re describing! Essentially, right now you have 2 separate BEGIN/REPEAT
loops, so once your script exits the button’s WHILE
loop, it never returns to it. All you need to do to fix this is move the second BEGIN
command before the WHILE
loop. So it would look like this:
begin #this is where begin was moved to
begin
0 get_position 200 greater_than while #wait in while loop until button connected to channel 0 is pushed
repeat
#this is where begin used to be
500 7616 0 0 0 0 0
0 0 0 0 0 frame_1..11 # Frame 0
8000 3968 frame_1 # Frame 1
500 7616 frame_1 # Frame 2
repeat
Brandon
Thanks Brandon.
Also modifying the button script exercise in the Pololu Maestro User Guide along with YouTube help from… https://www.youtube.com/watch?v=7nFg1cm-UFs …
I was able to get the functionality I was looking for.
Thanks again!
Brandon,
Thanks for all your help.
The following script below does everything we want except we need to delay the servo from activating ~ 1/2 second from the button press. When I add a 500 with space prefix to delay below…
sub frame_1..11
wait_for_button_press
1 servo
delay
return
I get a 1/2 second delay but the speed of the servo changes to maximum for all subsequent button presses rather than the speed (16) applied under channel settings. Please advise an edit to allow a button press delay without effecting the servo speed.
goto main_loop # Run the main loop when the script starts (see below).
# This subroutine returns 1 if the button is pressed, 0 otherwise.
# To convert the input value (0-1023) to a digital value (0 or 1) representing
# the state of the button, we make a comparison to an arbitrary threshold (500).
# This subroutine puts a logical value of 1 or a 0 on the stack, depending
# on whether the button is pressed or not.
sub button
0 get_position 500 less_than
return
# This subroutine uses the BUTTON subroutine above to wait for a button press,
# including a small delay to eliminate noise or bounces on the input.
sub wait_for_button_press
wait_for_button_open_10ms
wait_for_button_closed_10ms
return
# Wait for the button to be NOT pressed for at least 10 ms.
sub wait_for_button_open_10ms
get_ms # put the current time on the stack
begin
# reset the time on the stack if it is pressed
button
if
drop get_ms
else
get_ms over minus 10 greater_than
if drop return endif
endif
repeat
# Wait for the button to be pressed for at least 10 ms.
sub wait_for_button_closed_10ms
get_ms
begin
# reset the time on the stack if it is not pressed
button
if
get_ms over minus 10 greater_than
if drop return endif
else
drop get_ms
endif
repeat
# An example of how to use wait_for_button_press is shown below:
# Uses WAIT_FOR_BUTTON_PRESS to allow a user to step through
# a sequence of positions on servo 1.
main_loop:
begin
# Sequence 0
sub Sequence_0
500 7616 0 0 0 0 0
0 0 0 0 0 frame_1..11 # Frame 0
8000 3968 frame_1 # Frame 1
500 7616 frame_1 # Frame 2
repeat
sub frame_1..11
wait_for_button_press
1 servo
delay
return
sub frame_1
1 servo
delay
return
Hello.
I noticed you started a separate thread asking this exact same question. I have deleted the separate thread since you already have one dedicated to the issue.
There is a larger problem with your code; it looks like you might have edited the frame_1..11
subroutine so it will not work as intended. Right now, it is putting 12 values on the stack, then only using 2 of them. This will end up slowly leaving more values on the stack until it overflows and causes an error. Additionally, because 0 is the last value put on the stack, that’s the value being used for servo 1, which disables the output. When a servo output is disabled, speed and acceleration limits will not work because the Maestro needs to know the current position to calculate the next.
To fix these problems, you should be able to just remove the 0 values after 500 7616
Additionally, it looks like you are not actually using your Sequence_0
subroutine as a subroutine, so you can just remove the sub Sequence_0
so it functions as your main loop instead of a subroutine.
With those changes, your main loop would look like this:
begin
500 7616 frame_1..11
8000 3968 frame_1 # Frame 1
500 7616 frame_1 # Frame 2
repeat
If you try that and it does not function as intended, can you describe what it is doing and post a copy of your settings file? You can save your settings file by selecting the “Save settings file…” option within the “File” drop-down menu of the Maestro Control Center with the Maestro connected.
Brandon
Thanks Brandon.
Sorry for the double entry.
Do you think adding 500 before the delay line of the script below will add ~ ½ second delay before the start of the sequence?
sub frame_1..11
wait_for_button_press
1 servo
delay
**return**
That delay is being specified by the values being placed on the stack before you call the subroutine. Without any other changes, adding a 500 there will eventually cause errors, and before then likely a lot of intended behavior.
In my previous post, you can see that two values are put on the stack before calling frame_1..11
:
begin
500 7616 frame_1..11
. . .
Since 500 is being placed on the stack first, 7616 ends up on top of it. So, when we call frame_1..11
, and the 1 servo
command in it is consuming the top value (7616). This leaves 500 on the stack. Then, frame_1..11
reaches the delay
command, and uses the next value on the stack (500). So, you can change the value in that main code to specify how long you want the delay. For example, if you change it to 2000 7616 frame_1..11
, it will delay for 2 seconds after commanding the servo to move.
Brandon