New analogue of Punto Switcher for linux: xswitcher

The end of support for xneur has caused me some pain in the last six months. (since the advent of OpenSUSE 15.1 on my desktops: with xneur enabled, windows lose focus and funny flicker in time with keyboard input).

“Ah, damn it, again I started typing in the wrong layout” - in my work it occurs obscenely often. And does not add positive.

New analogue of Punto Switcher for linux: xswitcher
At the same time, I (as a design engineer) can articulate what I want quite clearly. And I wanted (first from Punto Switcher, and then, thanks to Windows Vista, finally switching to Linux, from xneur) exactly one. Realizing that the rubbish screen is in the wrong layout (this usually happens at the end of typing a new word), stomp on "Pause / Break". And get what you typed.

At the moment, the product has an optimal (from my point of view) ratio of functionality / complexity. It's time to share.

TL.DR

All sorts of technical details will follow, so first - link "to touch" for the impatient.

The following behavior is currently hardcoded:

  • "Pause/Break": pads (Backspace) the last word, switches the layout in the active window (between 0 and 1) and types again.
  • "Left Ctrl with nothing": switches the layout in the active window (between 0 and 1).
  • "Left Shift without Nothing": turns on layout #0 in the active window.
  • “Right Shift without Nothing”: turns on layout #1 in the active window.

From now on, I plan to customize the behavior. Without feedback, it’s not interesting (it suits me anyway). I believe that on Habré there is a sufficient percentage of the audience with similar problems.

Note Because in the current version, the keylogger is attached to "/dev/input/", xswitcher must be run as root:

chown root:root xswitcher
chmod +xs xswitcher

Note: the owner of the file with suid must be root, because who is the owner - in that suid and will turn at startup.

Paranoids (I am no exception) can clone from GIT and collect on site. Like that:

go get "github.com/micmonay/keybd_event"
go get "github.com/gvalkov/golang-evdev"

### X11 headers for OpenSUSE/deb-based
zypper install libX11-devel libXmu-devel
apt-get install libx11-dev libxmu-dev

cd "x switcher/src/"
go build -o xswitcher -ldflags "-s -w" --tags static_all src/*.go

Add autorun to taste (depending on DE).

Works, "does not ask for porridge" (≈30 CPU seconds per day, ≈12 MB in RSS).

Details

Now - the details.

The entire repository was originally dedicated to my pet project, and I’m too lazy to start another one. So, everything is piled up (just in folders) and covered with AGPL (“patent in reverse”).

The xswitcher code is written in golang, with minimal C inclusions. This approach is supposed to give the least effort (so far). Retaining the ability to connect the missing through cgo.

Comments are laid out in the text, from where they borrowed something and why. Because xneur code "did not inspire" me, took it as a starting point loloswitcher.

Using "/dev/input/" has both its advantages (everything is visible, including the pressed key with auto-repeat) and disadvantages. The cons are:

  • Auto-repeat (events with code "2") does not correlate with retry with xx.
  • Can't see input through X11 interfaces (this is how VNC works for example).
  • Need root.

On the other hand, you can subscribe to X events via "XSelectExtensionEvent()". You can peep at xinput code. For go, I didn’t find anything like that, and the draft implementation gave a hundred lines of C-code on the go. For now, put it aside.

The conclusion "back" is made by screwing the virtual keyboard. Thanks to the author of keybd_event, but there is too high-level abstraction and will have to be redone further. For example, the right Win-key selects the 3rd row for me. And only the left Win is translated back.

Known Bugs

  • We don't know anything about "composite" input (example: ½). It's not needed right now.
  • Incorrectly reproduce the right Win. In my case, it breaks the placement of accents.
  • There is no intelligible input parsing. Instead, there are several functions: Compare(), CtrlSequence(), RepeatSequence(), SpaceSequence(). Thank you nsmcan for attentiveness: corrected in the code and here. With a certain probability, you can grab bugs when replacing.
    In this place, I do not know "how to" and I will be glad to any suggestions.
  • (Oh God) concurrent use of channels (keyboardEvents, miceEvents).

Conclusion

The code is the simplest procedural. And stupid like me. So, I console myself with the hope that almost any techie will be able to finish what he wants. And because of this, this product will not perish without support, like most just-for-fun.

Good luck!

Source: habr.com

Add a comment