| #!/bin/sh |
| # Copyright (c) 2014 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. |
| |
| logger -- "$0" "$@" |
| |
| . /usr/share/misc/shflags |
| . $(dirname "$0")/xinput.sh |
| |
| # Sets mouse sensitivity preference |
| apply_mouse_sensitivity() { |
| device_set_prop "$1" "Pointer Sensitivity" "$2" |
| device_set_prop "$1" "Scroll Sensitivity" "$2" |
| } |
| |
| # Sets touchpad sensitivity preference |
| apply_touchpad_sensitivity() { |
| device_set_prop "$1" "Pointer Sensitivity" "$2" |
| device_set_prop "$1" "Scroll Sensitivity" "$2" |
| } |
| |
| apply_mouse_swap_lr() { |
| local map="1 2 3" |
| if [ "$2" -eq 1 ]; then |
| map="3 2 1" |
| fi |
| log "$XINPUT get-button-map $1 | sed \"s/^[0-9]* [0-9]* [0-9]*/$map/\" | \ |
| xargs $XINPUT set-button-map $1" |
| $XINPUT get-button-map "$1" | sed "s/^[0-9]* [0-9]* [0-9]*/$map/" | \ |
| xargs $XINPUT set-button-map "$1" |
| } |
| |
| apply_tp_custom_point_accel() { |
| the_id="$1" |
| values="$(echo "$2" | sed 's/,/ /g')" |
| $XINPUT set-prop "$the_id" "Pointer Accel Curve" \ |
| $values |
| } |
| |
| apply_tp_custom_scroll_accel() { |
| the_id="$1" |
| values="$(echo "$2" | sed 's/,/ /g')" |
| $XINPUT set-prop "$the_id" "Scroll Accel Curve" \ |
| $values |
| } |
| |
| apply_mouse_custom_point_accel() { |
| the_id="$1" |
| values="$(echo "$2" | sed 's/,/ /g')" |
| $XINPUT set-prop "$the_id" "Mouse Pointer Accel Curve" \ |
| $values |
| } |
| |
| # Generate activity log files for all devices |
| generate_logs() { |
| local devices="$1" |
| local now=$(date '+%Y%m%d-%H%M%S') |
| local raw_file="/var/log/xorg/touchpad_activity_log.txt" |
| local cmt_log_file="/var/log/xorg/cmt_input_events.dat" |
| local evdev_log_file="/var/log/xorg/evdev_input_events.dat" |
| |
| local out_dir="$2" |
| local out_prefix="touchpad_activity_" |
| local cmt_out_prefix="cmt_input_events_" |
| local evdev_out_prefix="evdev_input_events_" |
| |
| # Dump log files for each device |
| for device in $devices ; do |
| local name=$(device_get_canonical_name $device) |
| local out_file="${out_dir}/${out_prefix}${now}.$device.$name" |
| local cmt_out_file="${out_dir}/${cmt_out_prefix}${now}.$device.$name" |
| local evdev_out_file="${out_dir}/${evdev_out_prefix}${now}.$device.$name" |
| |
| if ! device_is_touchscreen $device; then |
| device_set_prop $device "Logging Notify" 1 |
| fi |
| device_set_prop $device "Dump Debug Log" 1 |
| |
| # Wait for writing to the files to complete. We do this by waiting for |
| # two consecutive checks in which the file size of the logs doesn't |
| # change. |
| local raw_size="-1" |
| local events_size="-1" |
| local max_iterations=6 |
| while true; do |
| if device_is_touchscreen $device; then |
| local raw_size_new=0 |
| local events_size_new=$(stat -c %s $evdev_log_file) |
| else |
| local raw_size_new=$(stat -c %s $raw_file) |
| local events_size_new=$(stat -c %s $cmt_log_file) |
| fi |
| |
| if [ $raw_size -eq $raw_size_new -a \ |
| $events_size -eq $events_size_new ]; then |
| break |
| fi |
| max_iterations=$((max_iterations - 1)) |
| if [ $max_iterations -lt 0 ]; then |
| break |
| fi |
| sleep 0.5 |
| raw_size=$raw_size_new |
| events_size=$events_size_new |
| done |
| |
| if [ -d $out_dir ]; then |
| if device_is_touchscreen $device ; then |
| cp "$evdev_log_file" "$evdev_out_file" |
| else |
| gzip -c --stdout "$raw_file" > "$out_file" |
| gzip -c --stdout "$cmt_log_file" > "$cmt_out_file" |
| fi |
| else |
| echo "\"$out_dir\" is not a directory." |
| fi |
| done |
| |
| # Delete old log files |
| if [ -d $out_dir ]; then |
| del="$(ls -t ${out_dir}/${out_prefix}* | grep -v ${now})" |
| del="${del} $(ls -t ${out_dir}/${cmt_out_prefix}* | grep -v ${now})" |
| del="${del} $(ls -t ${out_dir}/${evdev_out_prefix}* | grep -v ${now})" |
| for file in $del ; do |
| rm -f "$file" |
| done |
| fi |
| } |
| |
| # Mouse specific device setup |
| setup_mouse() { |
| local device="$1" |
| device_set_prop $device "Device Accel Profile" -1 |
| device_set_prop $device "Device Accel Constant Deceleration" 1 |
| device_set_prop $device "Device Accel Velocity Scaling" 1 |
| } |
| |
| # Detup device preferences and properties |
| setup_device() { |
| local device=$1 |
| apply_all_preferences $device |
| |
| if device_is_mouse $device; then |
| setup_mouse $device |
| fi |
| } |
| |
| # Helper method to add flags that set user preferences |
| DEFINE_prop_preference() { |
| local name="$2" |
| local prop_name="$5" |
| eval "apply_${name} () { device_set_prop \"\$1\" \"${prop_name}\" \"\$2\"; }" |
| DEFINE_preference "$1" "$2" "$3" "$4" |
| } |
| |
| DEFINE_preference() { |
| local name=$2 |
| |
| DEFINE_string ${name} '' "$3 set ${name} preference" |
| eval "pref_${name}_type=\"$1\"" |
| eval "pref_${name}_validator=\"$3\"" |
| eval "pref_${name}_default=\"$4\"" |
| preferences="$preferences $name" |
| } |
| |
| DEFINE_string 'type' 'all' 'type of devices to operate on' 't' |
| DEFINE_string 'id' '' 'id to operate on' 'i' |
| DEFINE_boolean 'verbose' false \ |
| 'show xinput commands executed by this script' 'v' |
| DEFINE_boolean 'list' false 'list device xinput ids' |
| DEFINE_boolean 'hwprops' false 'print hardware properties of device' |
| DEFINE_boolean 'names' false 'list device ids and their names' |
| DEFINE_boolean 'status' false 'show devices status' |
| DEFINE_string 'add' '' 'to be called by udev when a new device is added' |
| DEFINE_boolean 'refresh' false 're-apply preferences to all selected devices' |
| |
| DEFINE_boolean 'log' false 'generate activityt log files' |
| DEFINE_string 'logdir' '/home/chronos/user/log' \ |
| 'use with --log. Choose target directory' |
| |
| DEFINE_prop_preference touchpad tapdrag "[01]" "0" "Tap Drag Enable" |
| DEFINE_prop_preference touchpad tapclick "[01]" "1" "Tap Enable" |
| DEFINE_prop_preference touchpad t5r2_three_finger_click "[01]" "0" \ |
| "T5R2 Three Finger Click Enable" |
| DEFINE_prop_preference multitouch australian_scrolling "[01]" "1" \ |
| "Australian Scrolling" |
| DEFINE_prop_preference nontouch_mouse mouse_australian_scrolling "[01]" "0" \ |
| "Australian Scrolling" |
| DEFINE_preference touchpad touchpad_sensitivity "[12345]" "3" |
| DEFINE_preference mouse mouse_sensitivity "[12345]" "3" |
| DEFINE_preference mouse mouse_swap_lr "[01]" "0" |
| DEFINE_prop_preference mouse mouse_old_accel "[01]" "0" \ |
| "Old Mouse Accel Curves" |
| |
| default_curve_string() { |
| # Trick to print this string (up to % sign) 20 times |
| printf "inf 0 1 0 %.0s" {1..20} |
| } |
| |
| DEFINE_preference touchpad tp_custom_point_accel "*" \ |
| "$(default_curve_string)" |
| DEFINE_preference multitouch tp_custom_scroll_accel "*" \ |
| "$(default_curve_string)" |
| DEFINE_preference mouse mouse_custom_point_accel "*" \ |
| "$(default_curve_string)" |
| |
| DEFINE_prop_preference touchpad use_tp_custom_point_accel "[01]" "0" \ |
| "Use Custom Touchpad Pointer Accel Curve" |
| DEFINE_prop_preference multitouch use_tp_custom_scroll_accel "[01]" "0" \ |
| "Use Custom Touchpad Scroll Accel Curve" |
| DEFINE_prop_preference mouse use_mouse_custom_point_accel "[01]" "0" \ |
| "Use Custom Mouse Pointer Accel Curve" |
| |
| main() { |
| if ! [ -z ${FLAGS_add} ] ; then |
| local device=$(wait_and_get_added_device ${FLAGS_add}) |
| setup_device $device |
| return |
| fi |
| |
| # Determine list of devices to use for commands |
| local devices="" |
| if ! [ -z "${FLAGS_id}" ] ; then |
| devices=${FLAGS_id} |
| else |
| case ${FLAGS_type} in |
| mouse) devices=$(list_mice);; |
| touchpad) devices=$(list_touchpads);; |
| touchscreen) devices=$(list_touchscreens);; |
| multitouch) devices=$(list_multitouch);; |
| multitouchmouse) devices=$(list_multitouch_mice);; |
| all) devices=$(list_devices);; |
| *) |
| echo "error: unknown device type ${FLAGS_type}" >&2 |
| flags_help |
| ;; |
| esac |
| fi |
| |
| # Process preferences that have been set in arguments |
| for pref in $preferences; do |
| flag="$(eval echo \${FLAGS_$pref})" |
| if ! [ -z "$flag" ]; then |
| if validate_preference "$pref" "$flag"; then |
| apply_preference "$pref" "$devices" "$flag" |
| save_preference "$pref" "$flag" |
| fi |
| fi |
| done |
| |
| # Refresh other properties of touchpads/mice. |
| # We do this here because Chrome doesn't call --refresh. |
| # We abuse chrome's calls to set sensitivity. |
| if ! [ -z ${FLAGS_mouse_sensitivity} ] ; then |
| devs="$(list_mice)" |
| for dev in $devs; do |
| setup_device $dev |
| done |
| fi |
| if ! [ -z ${FLAGS_touchpad_sensitivity} ] ; then |
| devs="$(list_touchpads)" |
| for dev in $devs; do |
| setup_device $dev |
| done |
| fi |
| |
| # Process commands |
| if [ ${FLAGS_list} -eq ${FLAGS_TRUE} ] ; then |
| if ! [ -z $devices ]; then |
| echo $devices |
| fi |
| fi |
| if [ ${FLAGS_hwprops} -eq ${FLAGS_TRUE} ] ; then |
| for device in $devices; do |
| local path=$(device_get_string_prop "$device" "Device Node") |
| log "evemu-describe $path" |
| evemu-describe $path |
| if [ $? -ne 0 ]; then |
| exit 1 |
| fi |
| done |
| fi |
| if [ ${FLAGS_status} -eq ${FLAGS_TRUE} ] ; then |
| for device in $devices; do |
| device_status $device |
| done |
| fi |
| if [ ${FLAGS_names} -eq ${FLAGS_TRUE} ] ; then |
| for device in $devices; do |
| echo "${device}: $(device_get_name $device)" |
| done |
| fi |
| if [ ${FLAGS_log} -eq ${FLAGS_TRUE} ] ; then |
| generate_logs "$devices" "${FLAGS_logdir}" |
| fi |
| if [ ${FLAGS_refresh} -eq ${FLAGS_TRUE} ] ; then |
| for device in $devices; do |
| setup_device $device |
| done |
| fi |
| |
| # Process "Property Name=Value" arguments |
| for arg; do |
| if echo $arg | grep -q =; then |
| local name="${arg%%=*}" |
| local value="${arg#*=}" |
| for device in $devices; do |
| device_set_prop "$device" "$name" "$value" |
| done |
| else |
| flags_help |
| fi |
| done |
| } |
| |
| if [ $# = 0 ] ; then |
| flags_help |
| exit 1 |
| fi |
| |
| # parse the command-line |
| FLAGS "$@" || exit $? |
| eval set -- "${FLAGS_ARGV}" |
| main "$@" |