Alternativ vindusbehandling i Linux

Jeg er en av dem som stiller inn Caps Lock til å bytte layout fordi jeg er for lat til å trykke på 2 taster når jeg kan trykke på en. Jeg vil til og med ha to unødvendige nøkler: Jeg vil bruke en til å slå på den engelske layouten, og den andre for russisk. Men den andre unødvendige nøkkelen er å hente frem kontekstmenyen, som er så unødvendig at den kuttes ut av mange bærbare produsenter. Så du må være fornøyd med det du har.

Og jeg vil heller ikke se etter ikonene deres på oppgavelinjen når jeg bytter vinduer, eller fange navnene når jeg blar gjennom Alt + Tab, bla gjennom skrivebord osv. Jeg vil trykke på en tastekombinasjon (ideelt sett bare én, men det er ingen ledige unødvendige taster lenger) og umiddelbart komme til vinduet jeg trenger. For eksempel slik:

  • Alt+F: Firefox
  • Alt+D: Firefox (privat surfing)
  • Alt+T: Terminal
  • Alt+M: Kalkulator
  • Alt+E: IntelliJ-idé
  • etc.

Dessuten ved å trykke for eksempel på Alt+M Jeg vil se kalkulatoren uansett om dette programmet kjører for øyeblikket. Hvis det kjører, må vinduet gis fokus, og hvis ikke, kjør ønsket program og overfør fokus når det laster.

For tilfeller som ikke dekkes av det forrige skriptet, ønsker jeg å ha universelle tastekombinasjoner som enkelt kan tilordnes til alle de åpne vinduene. For eksempel har jeg 10 kombinasjoner tilordnet fra Alt + 1 til Alt + 0, som ikke er knyttet til noen programmer. Jeg kan bare klikke Alt + 1 og vinduet som for øyeblikket er i fokus vil få fokus når det klikkes Alt + 1.

Under kuttet er det en beskrivelse av et par funksjoner til og et svar på hvordan dette kan gjøres. Men jeg vil umiddelbart advare deg om at slik tilpasning "for deg selv" kan forårsake alvorlig avhengighet og til og med tilbaketrekning hvis du trenger å bruke Windows, Mac OS eller til og med noen andres datamaskin med Linux.

Faktisk, hvis du tenker deg om, bruker vi ikke så mange programmer på daglig basis. En nettleser, en terminal, en IDE, en slags messenger, en filbehandler, en kalkulator og kanskje det er nesten alt. Det er ikke mange tastekombinasjoner som trengs for å dekke 95 % av daglige gjøremål.

For programmer som har flere åpne vinduer, kan ett av dem angis som hovedvinduet. For eksempel har du flere IntelliJ Idea-vinduer åpne og tilordnet til Alt + E. Under normale forhold, når du trykker Alt + E et vindu i dette programmet vil åpne, mest sannsynlig det som ble åpnet først. Men hvis du klikker på Alt + E når et av vinduene i dette programmet allerede er i fokus, vil dette bestemte vinduet bli tildelt som hovedvinduet, og det vil være det som vil bli gitt fokus når påfølgende kombinasjoner trykkes.

Hovedvinduet kan tilordnes på nytt. For å gjøre dette må du først tilbakestille kombinasjonen, og deretter tilordne et annet vindu til det som hovedvindu. For å tilbakestille en kombinasjon, må du trykke på selve kombinasjonen, og deretter en spesiell tilbakestillingskombinasjon, jeg har den tildelt Alt+Tilbake. Dette vil kalle opp et skript som vil fjerne tilordningen av hovedvinduet for den forrige kombinasjonen. Og så kan du tilordne et nytt hovedvindu som beskrevet i forrige avsnitt. Tilbakestilling av et koblet vindu til universelle kombinasjoner skjer på samme måte.

Innledningen ble lang, men jeg ville først fortelle hva vi skal gjøre, og så forklare hvordan vi gjør det.

For de som er lei av å lese

Kort fortalt er lenken til skriptene på slutten av artikkelen.

Men du vil fortsatt ikke kunne installere og bruke den med en gang. Du må først finne ut hvordan skriptet finner det ønskede vinduet. Uten dette vil det ikke være mulig å fortelle manuset hvor nøyaktig fokus må overføres. Og du må forstå hva du skal gjøre hvis du plutselig ikke finner et passende vindu.

Og jeg vil ikke fokusere på hvordan du konfigurerer utførelsen av skript ved å trykke på tastekombinasjoner. For eksempel, i KDE er det i Systeminnstillinger → Snarveier → Egendefinerte snarveier. Dette bør også være tilfelle i andre vindusbehandlere.

Vi introduserer wmctrl

Wmctrl — konsollverktøy for samhandling med X Window Manager. Dette er nøkkelprogrammet for manuset. La oss ta en rask titt på hvordan du kan bruke den.

Først, la oss vise en liste over åpne vinduer:

$ wmctrl -lx
0x01e0000e -1 plasmashell.plasmashell             N/A Desktop — Plasma
0x01e0001e -1 plasmashell.plasmashell             N/A Plasma
0x03a00001  0 skype.Skype                         N/A Skype
0x04400003  0 Navigator.Firefox                   N/A Google Переводчик - Mozilla Firefox
0x04400218  0 Navigator.Firefox                   N/A Лучшие публикации за сутки / Хабр - Mozilla Firefox (Private Browsing)
...

alternativ -l viser en liste over alle åpne vinduer, og -NS legger til klassenavnet til utdata (skype.Skype, Navigator.Firefox etc). Her trenger vi vindus-ID (kolonne 1), klassenavn (kolonne 3) og vindusnavn (siste kolonne).

Du kan prøve å aktivere et vindu ved å bruke alternativet -a:

$ wmctrl -a skype.Skype -x

Hvis alt gikk etter planen, skal Skype-vinduet vises på skjermen. Hvis i stedet for alternativet -x bruk alternativet -i, så i stedet for klassenavnet kan du spesifisere vindus-ID. Problemet med id er at vindus-ID-en endres hver gang programmet startes, og vi kan ikke vite det på forhånd. På den annen side identifiserer dette attributtet unikt et vindu, noe som kan være viktig når et program åpner mer enn ett vindu. Mer om dette litt lenger.

På dette stadiet må vi huske at vi vil søke etter ønsket vindu ved å bruke regex etter utdata wmctrl -lx. Men det betyr ikke at vi må bruke noe komplisert. Vanligvis er klassenavnet eller vindusnavnet tilstrekkelig.

I utgangspunktet bør hovedideen allerede være klar. I de globale hurtigtaster/snarveisinnstillingene for vindusbehandleren din, konfigurer den nødvendige kombinasjonen for å kjøre skriptet.

Hvordan bruke skript

Først må du installere konsollverktøy wmctrl и xdotool:

$ sudo apt-get install wmctrl xdotool

Deretter må du laste ned skriptene og legge dem til $ PATH. Jeg pleier å legge dem inn ~/bin:

$ cd ~/bin
$ git clone https://github.com/masyamandev/Showwin-script.git
$ ln -s ./Showwin-script/showwin showwin
$ ln -s ./Showwin-script/showwinDetach showwinDetach

Hvis katalogen ~/bin ikke var der, så må du opprette den og starte på nytt (eller logge på på nytt), ellers ~/bin vil ikke treffe $ PATH. Hvis alt er gjort riktig, bør skriptene være tilgjengelige fra konsollen og tabulatorfullføring skal fungere.

Hovedmanus showwin tar 2 parametere: den første er et regulært uttrykk, der vi vil søke etter det nødvendige vinduet, og den andre parameteren er en kommando som må utføres hvis det nødvendige vinduet ikke blir funnet.

Du kan prøve å kjøre et skript, for eksempel:

$ showwin "Mozilla Firefox$" firefox

Hvis Firefox er installert, bør vinduet ha fokus. Selv om Firefox ikke kjørte, burde den ha startet.

Hvis det fungerer, kan du prøve å konfigurere utførelsen av kommandoer på kombinasjoner. I de globale hurtigtaster/snarveisinnstillingene legg til:

  • Alt+F: visvinn «Mozilla Firefox$» firefox
  • Alt+D: showwin "Mozilla Firefox (Privat surfing)$" "firefox -privat-vindu"
  • Alt+C: showwin "chromium-browser.Chromium-browser N*" chromium-nettleser
  • Alt+X: showwin "chromium-browser.Chromium-browser I*" "chromium-browser -incognito"
  • Alt+S: showwin "skype.Skype" skypeforlinux
  • Alt+E: showwin "jetbrains-idea" idea.sh

Osv. Alle kan konfigurere tastekombinasjoner og programvare etter eget ønske.
Hvis alt fungerte riktig, vil vi ved å bruke kombinasjonene ovenfor kunne bytte mellom vinduer ved å trykke på tastene.

Jeg vil skuffe kromelskere: det kan inkognito skille et vanlig vindu ved utgangen wmctrl Du kan ikke, de har de samme klassenavnene og vindustitlene. I det foreslåtte regex er tegnene N* og I* kun nødvendig for at disse regulære uttrykkene skal skille seg fra hverandre og de kan tilordnes som hovedvinduer.

For å tilbakestille hovedvinduet til forrige kombinasjon (faktisk for regex, som showwin ringte forrige gang) må du ringe skriptet showwinTa løs. Jeg har dette skriptet tildelt en tastekombinasjon Alt+Tilbake.

Ved manuset showwin det er en funksjon til. Når den kalles med én parameter (i dette tilfellet er parameteren bare en identifikator), sjekker den ikke regex i det hele tatt, men anser alle vinduer for å være passende. I seg selv virker dette ubrukelig, men på denne måten kan vi utpeke et hvilket som helst vindu som hovedvinduet og raskt bytte til det aktuelle vinduet.

Jeg har konfigurert følgende kombinasjoner:

  • Alt+1: showwin "CustomKey1"
  • Alt+2: showwin "CustomKey2"
  • ...
  • Alt+0: showwin "CustomKey0"
  • Alt+Tilbake: showwinDetach

På denne måten kan jeg binde alle vinduer til kombinasjoner Alt + 1...Alt + 0. Bare ved å klikke Alt + 1 Jeg binder det gjeldende vinduet til denne kombinasjonen. Jeg kan avbryte bindingen ved å klikke Alt + 1, og så Alt+Tilbake. Eller lukk vinduet, det fungerer også.

Deretter vil jeg fortelle deg noen tekniske detaljer. Du trenger ikke å lese dem, men bare prøv å sette dem opp og se. Men jeg vil likevel anbefale å forstå andres skript før du kjører dem på datamaskinen din :).

Hvordan skille mellom forskjellige vinduer i samme applikasjon

I prinsippet fungerte det aller første eksemplet "wmctrl -a skype.Skype -x" og kan brukes. Men la oss se igjen på eksemplet med Firefox, der 2 vinduer er åpne:

0x04400003  0 Navigator.Firefox                   N/A Google Переводчик - Mozilla Firefox
0x04400218  0 Navigator.Firefox                   N/A Лучшие публикации за сутки / Хабр - Mozilla Firefox (Private Browsing)

Det første vinduet er i normal modus, og det andre er Privat surfing. Jeg vil gjerne vurdere disse vinduene som forskjellige applikasjoner og bytte til dem ved hjelp av forskjellige tastekombinasjoner.

Det er nødvendig å komplisere skriptet som bytter vinduer. Jeg brukte denne løsningen: vis en liste over alle vinduer, gjør grep ved regulært uttrykk, ta den første linjen med hode, få den første kolonnen (dette vil være vindus-ID) ved å bruke kutte opp, bytt til vindu etter id.

Det skal være en vits om regulære uttrykk og to problemer, men jeg bruker faktisk ikke noe komplisert. Jeg trenger regulære uttrykk slik at jeg kan indikere slutten av linjen («$»-symbolet) og skille «Mozilla Firefox$» fra «Mozilla Firefox (Privat surfing)$».

Kommandoen ser omtrent slik ut:

$ wmctrl -i -a `wmctrl -lx | grep -i "Mozilla Firefox$" | head -1 | cut -d" " -f1`

Her kan du allerede gjette om den andre funksjonen i skriptet: hvis grep ikke returnerer noe, er den ønskede applikasjonen ikke åpen, og du må starte den ved å utføre kommandoen fra den andre parameteren. Og kontroller deretter med jevne mellomrom om det nødvendige vinduet har åpnet seg for å overføre fokus til det. Jeg vil ikke fokusere på dette; alle som trenger det vil se på kildene.

Når programvinduer ikke kan skilles

Så vi har lært hvordan du overfører fokus til vinduet til ønsket applikasjon. Men hva om et program har mer enn ett vindu åpent? Hvilken bør jeg fokusere på? Skriptet ovenfor vil mest sannsynlig overføres til det første åpne vinduet. Vi ønsker imidlertid mer fleksibilitet. Jeg vil gjerne huske hvilket vindu vi trenger og bytte til akkurat det vinduet.

Tanken var denne: Hvis vi vil huske et spesifikt vindu for en tastekombinasjon, må vi trykke på denne kombinasjonen når ønsket vindu er i fokus. I fremtiden, når du trykker på denne kombinasjonen, vil fokuset bli gitt til dette vinduet. Inntil vinduet lukkes eller vi gjør en tilbakestilling for denne skriptkombinasjonen showwinTa løs.

Skriptalgoritme showwin noe sånt som dette:

  • Sjekk om vi tidligere har husket ID-en til vinduet som fokus skal overføres til.
    Hvis du husker og et slikt vindu fortsatt eksisterer, overfører vi fokus til det og avslutter.
  • Vi ser på hvilket vindu som er i fokus for øyeblikket, og hvis det samsvarer med forespørselen vår, husk ID-en for å gå til det i fremtiden og avslutte.
  • Vi går til i det minste et passende vindu hvis det finnes eller åpner ønsket applikasjon.

Du kan finne ut hvilket vindu som er i fokus for øyeblikket ved å bruke xdotool-konsollverktøyet ved å konvertere utdataene til heksadesimalt format:

$ printf "0x%08x" `xdotool getwindowfocus`

Den enkleste måten å huske noe i bash er å lage filer i et virtuelt filsystem som ligger i minnet. I Ubuntu er dette aktivert som standard i /dev/shm/. Jeg kan ikke si noe om andre distribusjoner, jeg håper det er noe lignende også. Du kan se med kommandoen:

$ mount -l | grep tmpfs

Skriptet vil lage tomme kataloger i denne mappen, slik: /dev/shm/$USER/showwin/$SEARCH_REGEX/$WINDOW_ID. I tillegg vil hver gang den kalles, opprette en symbolkobling /dev/shm/$USER/showwin/showwin_last/dev/shm/$USER/showwin/$SEARCH_REGEX. Dette vil være nødvendig for om nødvendig å fjerne vindus-ID-en for en bestemt kombinasjon ved hjelp av et skript showwinTa løs.

Hva kan forbedres

For det første må skriptene konfigureres manuelt. Sikkert, på grunn av behovet for å dykke ned i og gjøre mye med hendene, vil mange av dere ikke engang prøve å konfigurere systemet. Hvis det var mulig å ganske enkelt installere pakken og konfigurere alt lettere, ville den kanskje blitt populær. Og se, applikasjonen vil bli utgitt i standarddistribusjoner.

Og kanskje kan det gjøres enklere. Hvis du ved hjelp av ID-en til et vindu kan finne ut ID-en til prosessen som opprettet det, og ved ID-en til prosessen kan du finne ut hvilken kommando som opprettet det, så ville det være mulig å automatisere oppsettet. Faktisk forsto jeg ikke om det jeg skrev i denne paragrafen var mulig. Faktum er at jeg personlig er fornøyd med måten det fungerer på nå. Men hvis noen andre enn meg finner hele tilnærmingen praktisk og noen forbedrer den, så vil jeg gjerne bruke en bedre løsning.

Et annet problem, som jeg allerede skrev, er at vinduene i noen tilfeller ikke kan skilles fra hverandre. Så langt har jeg kun observert dette med inkognito i krom/krom, men kanskje det er noe lignende et annet sted. Som en siste utvei er det alltid mulighet for universelle kombinasjoner Alt + 1...Alt + 0. Igjen, jeg bruker Firefox og for meg personlig er ikke dette problemet betydelig.

Men det betydelige problemet for meg er at jeg bruker Mac OS til jobb, og jeg kunne ikke konfigurere noe sånt der. nytte wmctrl Jeg tror jeg var i stand til å installere det, men det fungerer egentlig ikke på Mac OS. Noe kan gjøres med applikasjonen Automator, men den er så treg at den ikke er praktisk å bruke selv når den fungerer. Jeg kunne heller ikke sette opp tastekombinasjoner slik at de fungerte i alle programmer. Hvis noen plutselig kommer med en løsning, bruker jeg den gjerne.

I stedet for en konklusjon

Det viste seg å være et uventet stort antall ord for en så tilsynelatende enkel funksjonalitet. Jeg ønsket å formidle ideen og ikke overbelaste teksten, men jeg har ennå ikke funnet ut hvordan jeg skal fortelle den enklere. Kanskje det ville vært bedre i videoformat, men folk liker det ikke på den måten her.

Jeg snakket litt om hva som er under panseret på manuset og hvordan man konfigurerer det. Jeg gikk ikke inn på detaljer om selve manuset, men det er bare 50 linjer, så det er ikke vanskelig å forstå.

Jeg håper at noen andre vil prøve denne ideen og kanskje til og med sette pris på den. Jeg kan si om meg selv at manuset ble skrevet for ca 3 år siden, og det er VELDIG praktisk for meg. Så praktisk at det forårsaker alvorlig ubehag når du arbeider med andres datamaskiner. Og med en fungerende MacBook.

Link til skript

Kilde: www.habr.com

Legg til en kommentar