Skip to content

Instantly share code, notes, and snippets.

@tuxflo
Forked from mildmojo/rotate_desktop.sh
Last active January 28, 2024 23:07
Show Gist options
  • Save tuxflo/5b400c86a5ebde871d94c6bff94ad6cb to your computer and use it in GitHub Desktop.
Save tuxflo/5b400c86a5ebde871d94c6bff94ad6cb to your computer and use it in GitHub Desktop.
Script to rotate the screen and touch devices on modern Linux desktops. Great for convertible laptops.
#!/bin/bash
#
# rotate_desktop.sh
#
# Rotates modern Linux desktop screen and input devices to match. Handy for
# convertible notebooks. Call this script from panel launchers, keyboard
# shortcuts, or touch gesture bindings (xSwipe, touchegg, etc.).
#
# Using transformation matrix bits taken from:
# https://wiki.ubuntu.com/X/InputCoordinateTransformation
#
# Forked from https://gist.github.com/mildmojo/48e9025070a2ba40795c
# Configured to use with a Lenovo Yoga 260 (names taken from `xinput` output).
# If the rotation position ($1) is ommited, the script toggles through the different states: inverted, left, right, normal
TOUCHPAD='ETPS/2 Elantech Touchpad'
TOUCHSCREEN='Wacom Co.,Ltd. Pen and multitouch sensor Finger touch'
TRANSFORM='Coordinate Transformation Matrix'
NORMAL="Coordinate Transformation Matrix (142): 1.000000, 0.000000, 0.000000, 0.000000, 1.000000, 0.000000, 0.000000, 0.000000, 1.000000"
INVERTED="Coordinate Transformation Matrix (142): -1.000000, 0.000000, 1.000000, 0.000000, -1.000000, 1.000000, 0.000000, 0.000000, 1.000000"
LEFT="Coordinate Transformation Matrix (142): 0.000000, -1.000000, 1.000000, 1.000000, 0.000000, 0.000000, 0.000000, 0.000000, 1.000000"
RIGHT="Coordinate Transformation Matrix (142): 0.000000, 1.000000, 0.000000, -1.000000, 0.000000, 1.000000, 0.000000, 0.000000, 1.000000"
function do_rotate
{
xrandr --output $1 --rotate $2
TRANSFORM='Coordinate Transformation Matrix'
case "$2" in
normal)
[ ! -z "$TOUCHPAD" ] && xinput set-prop "$TOUCHPAD" "$TRANSFORM" 1 0 0 0 1 0 0 0 1
[ ! -z "$TOUCHSCREEN" ] && xinput set-prop "$TOUCHSCREEN" "$TRANSFORM" 1 0 0 0 1 0 0 0 1
;;
inverted)
[ ! -z "$TOUCHPAD" ] && xinput set-prop "$TOUCHPAD" "$TRANSFORM" -1 0 1 0 -1 1 0 0 1
[ ! -z "$TOUCHSCREEN" ] && xinput set-prop "$TOUCHSCREEN" "$TRANSFORM" -1 0 1 0 -1 1 0 0 1
;;
left)
[ ! -z "$TOUCHPAD" ] && xinput set-prop "$TOUCHPAD" "$TRANSFORM" 0 -1 1 1 0 0 0 0 1
[ ! -z "$TOUCHSCREEN" ] && xinput set-prop "$TOUCHSCREEN" "$TRANSFORM" 0 -1 1 1 0 0 0 0 1
;;
right)
[ ! -z "$TOUCHPAD" ] && xinput set-prop "$TOUCHPAD" "$TRANSFORM" 0 1 0 -1 0 1 0 0 1
[ ! -z "$TOUCHSCREEN" ] && xinput set-prop "$TOUCHSCREEN" "$TRANSFORM" 0 1 0 -1 0 1 0 0 1
;;
esac
}
if [ -z "$1" ]; then
echo "No orientation given, toggle mode"
CURRENT_MODE=`xinput --list-props "$TOUCHPAD" | grep "$TRANSFORM"`
XDISPLAY=`xrandr --current | grep primary | sed -e 's/ .*//g'`
echo "$CURRENT_MODE"
if [ "${CURRENT_MODE//[$' \t\n\r']/}" = "${NORMAL//[$' \t\n\r']/}" ]; then
echo "Current mode: normal"
echo "switching to: inverted"
do_rotate $XDISPLAY inverted
elif [ "${CURRENT_MODE//[$' \t\n\r']/}" == "${INVERTED//[$' \t\n\r']/}" ]; then
echo "Current mode: inverted"
echo "switching to: left"
do_rotate $XDISPLAY left
elif [ "${CURRENT_MODE//[$' \t\n\r']/}" == "${LEFT//[$' \t\n\r']/}" ]; then
echo "Current mode: left"
echo "switching to: right"
do_rotate $XDISPLAY right
elif [ "${CURRENT_MODE//[$' \t\n\r']/}" == "${RIGHT//[$' \t\n\r']/}" ]; then
echo "Current mode: right"
echo "switching to: normal"
do_rotate $XDISPLAY normal
fi
fi
XDISPLAY=`xrandr --current | grep primary | sed -e 's/ .*//g'`
XROT=`xrandr --current --verbose | grep primary | egrep -o ' (normal|left|inverted|right) '`
do_rotate $XDISPLAY $1
if [ ! -z "$2" ]; then
sleep $2
do_rotate $XDISPLAY $XROT
exit 0
fi
@magesticmage
Copy link

can you help me with this error after adding my input and touch device?

TOUCHPAD='LIZHI Flash IC USB Keyboard Mouse'
TOUCHSCREEN='Goodix Capacitive TouchScreen'

error is: warning: output --rotate not found; ignoring

MX Linux Wildflower/Nuvision tablet

@tuxflo
Copy link
Author

tuxflo commented Jun 19, 2023

The error looks like your Display is not found. Can you post the output of the following command?

xrandr --current | grep primary

(this is what is used to generate the variable XDISPLAY)

@magesticmage
Copy link

there is no output, nothing post's and just returns to the shell prompt after running the command " xrandr --current | grep primary "

@tuxflo
Copy link
Author

tuxflo commented Jun 20, 2023

Are you sure that you are on a X11 session? The script won't work with Wayland since it uses xinput and xrandr.
Is there some output if you just run xrandr without parameters and additional grepping?

@magesticmage
Copy link

magesticmage commented Jun 21, 2023

I believe so, using MX Linux 21.3 XFCE

here is the output of xrandr output

@tuxflo
Copy link
Author

tuxflo commented Jun 21, 2023

For some reason your xrandr output does not include the word "primary" as it does in my setup:

 tuxflo@flo-x390 ~ % xrandr --current | grep primary
eDP-1 connected primary 1920x1080+0+0 (normal left inverted right x axis y axis) 294mm x 165mm

maybe you could try it by replacing "primary" with "connected" (in Line 53) in the script, since this is present, based on you xrandr output.

@magesticmage
Copy link

magesticmage commented Jun 22, 2023

instead of changing it to connected, i tried changing it to DSI-1 since when it greps it would include "disconnected" as well, if you understand

but still not working.

here us what i get:

mage@mx:/Desktop
$ ./rotate_desktop.sh right
xrandr: --rotate requires an argument
Try 'xrandr --help' for more information.
mage@mx:/Desktop
$ ./rotate_desktop.sh
No orientation given, toggle mode
Coordinate Transformation Matrix (182): 1.000000, 0.000000, 0.000000, 0.000000, 1.000000, 0.000000, 0.000000, 0.000000, 1.000000
warning: output --rotate not found; ignoring
mage@mx:~/Desktop
$

@magesticmage
Copy link

going to try another distro like ubuntu or mint

@dtaytson
Copy link

#!/usr/bin/bash

monitor-sensor | while read line; do
if echo $line | grep -E 'orientation changed:|Has accelerometer'; then
orientation=$(echo $line | sed -e 's/^.: //' -e 's/ .//' -e 's/[()]//g')
case $orientation in
normal)
xrandr --output eDP-1 --rotate normal
xinput set-prop "ELAN0732:00 04F3:0358" --type=float --format=32 "TransformationMatrix" 1 0 0 0 1 0 0 0 1
xinput set-prop "ELAN0732:00 04F3:0358" "Coordinate Transformation Matrix" 1 0 0 0 1 0 0 0 1
;;
bottom-up)
xrandr --output eDP-1 --rotate inverted
xinput set-prop "ELAN0732:00 04F3:0358" --type=float --format=32 "TransformationMatrix" -1 0 1 0 -1 1 0 0 1
xinput set-prop "ELAN0732:00 04F3:0358" "Coordinate Transformation Matrix" -1 0 1 0 -1 1 0 0 1
;;
right-up)
xrandr --output eDP-1 --rotate right
xinput set-prop "ELAN0732:00 04F3:0358" --type=float --format=32 "TransformationMatrix" 0 1 0 -1 0 1 0 0 1
xinput set-prop "ELAN0732:00 04F3:0358" "Coordinate Transformation Matrix" 0 1 0 -1 0 1 0 0 1
;;
left-up)
xrandr --output eDP-1 --rotate left
xinput set-prop "ELAN0732:00 04F3:0358" --type=float --format=32 "TransformationMatrix" 0 -1 1 1 0 0 0 0 1
xinput set-prop "ELAN0732:00 04F3:0358" "Coordinate Transformation Matrix" 0 -1 1 1 0 0 0 0 1
;;
esac
fi
done

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment