blob: 66743938773608aa62bd0e532a4418bc81c24b39 [file] [log] [blame]
# Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
""" This is a tapping script for Touchbot II
When you run this script, the robot will perform a customizable tap action
on the touchpad. This essentially consists of tapping repeatedly with a series
of fingers in a certain location on the pad.
The gesture takes in a position to move the hand to, a list of which fingers
to do the tap or drumroll with, and the number of taps to perform.
x, y coordinates in the range from 0.0->1.0
angle in degrees
finger distance in mm that specifies how far apart the hand should open
Which fingers the robot should be used as a list of 4 booleans
Top right, Top Left, Bottom Left, Bottom Right
'tap' or 'drumroll'
The robot will move to that position, then tap the fingers as specified. For
a drumroll it alternates tapping each one in turn, for a regular 'tap' all of
the fingers descend at once.
Example:
To do a standard 2 finger drumroll in the center of the pad 20mm apart
Python drumroll.py lumpy.p 0.5 0.5 45 20 0 1 0 1 50 drumroll
To tap 3 fingers 20 times in the top left corner of the pad 30mm apart
Python drumroll.py lumpy.p 0.1 0.3 0 30 0 1 1 1 20 tap
"""
import math
import sys
import time
from touchbotII import Touchbot, Device, PositionArg
try:
# Parse the command line arguments
device = Device(sys.argv[1])
pos = PositionArg(*[float(v) for v in sys.argv[2:6]])
fingers = [int(arg) for arg in sys.argv[6:10]]
num_taps = int(sys.argv[10])
is_drumroll = (sys.argv[11] == 'drumroll')
delay = 0.0
if len(sys.argv) > 12:
delay = float(sys.argv[12])
except:
print ('Usage: python %s device.p position fingers num_taps [tap|drumroll]'
% __file__)
print ' * position is formatted as x y angle finger_distance'
print ' * finger_states: a list of 4 values (1s and 0s)'
print ' * the number of individual taps to make'
print
print 'For a standard 2 finger drumroll in the center you might do:'
print 'python %s link.p 0.5 0.5 45 20 0 1 0 1 50 drumroll' % __file__
sys.exit(1)
print 'Executing the tap gesture defined by:'
print '\tPosition: %s' % str(pos)
print '\tFingers: %s' % str(fingers)
print '\tNum taps: %d' % num_taps
print '\tDrumroll?: %s' % str(is_drumroll)
num_fingers = sum(fingers)
if num_fingers < 1:
print 'You must specify at least 1 finger to use'
sys.exit(1)
# Connect to the robot and configure the profile to move slowly
bot = Touchbot()
bot.SetSpeed(Touchbot.SPEED_SLOW)
# Convert the point specifications into something the robot understands
abs_pos = device.RelativePosToAbsolutePos((pos.x, pos.y), angle=pos.angle)
# For one finger taps, compensate to center the finger
abs_pos = bot.CenterIfSingleFinger(fingers, abs_pos, pos.finger_distance)
# Go to the starting point and prepare for the drumroll
bot.SetFingerStates([0, 0, 0, 0])
bot.SetCartesian(abs_pos, pos.finger_distance, blocking=True)
# Commence the tapping
fingers_tapping = [i for i, v in enumerate(fingers) if v]
next_finger = 0
last_state = [0, 0, 0, 0]
for tap_num in range(num_taps):
if num_fingers > 1 and is_drumroll:
finger_number = fingers_tapping[next_finger % len(fingers_tapping)]
next_states = [1 if i == finger_number else 0
for i in range(len(Touchbot.ALL_FINGERS))]
middle_states = [1 if (l or n) else 0
for l, n in zip(last_state, next_states)]
# Start the new finger moving down before lifting up the last one
bot.SetFingerStates(middle_states)
time.sleep(Touchbot.MINIMUM_FINGER_EXTENSION_TIME / 2)
# Now start to lift the finger that was on the pad before
bot.SetFingerStates(next_states)
time.sleep(Touchbot.MINIMUM_FINGER_EXTENSION_TIME / 2)
last_state = next_states
next_finger += 1
else:
bot.SetFingerStates(fingers)
# The pressure is split across all the fingers, so they are slower to
# extend if there are multiples being used at once
time.sleep(Touchbot.MINIMUM_FINGER_EXTENSION_TIME * num_fingers
+ delay)
bot.SetFingerStates([0, 0, 0, 0])
time.sleep(Touchbot.MINIMUM_FINGER_EXTENSION_TIME)
# Make sure all the fingers are lifted up when it's done
bot.SetFingerStates([0, 0, 0, 0])