You are not logged in.

#1 2008-04-04 20:58:12

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Detecting current Xorg keyboard layout

Hello all,

I'm trying to figure out how to programmatically detect what is the current X keyboard layout. I use us, latam, and br and it's a pain to never be sure what the active layout is without hitting a key. What I want to do is to be able to make a keyboard layout plugin for ruby-wmii that will show me the current layout and possibly let me change it. Though the target language is eventually Ruby, using C will work too, since I could just make a Ruby extension if necessary. I'm currently looking at some code to see if I can figure out how to read the current layout and then possibly change it, but it'd be great if someone could point out the correct way.

Thanks and regards,
j

Offline

#2 2008-04-05 07:43:15

lman
Member
From: CZ
Registered: 2007-12-18
Posts: 252

Re: Detecting current Xorg keyboard layout

I was wondering about the same thing. I use 4 keyboard layouts, never sure which one I'm using at the moment... big_smile

Offline

#3 2008-04-05 20:46:43

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

Well, I think I've got it figured out. I studied up on some other programs and created a program that will now let me retrieve the current layout. There are three things that are missing:

1. A way to get the layout abbreviation. My program will return the full name of the group. In my case I get "USA", "Latin American" or "Brazil" when something like "us", "latam" or "br" would be better for a status bar indicator. I am working on this right now.
2. A way to set the layout. This way I can use a ruby-wmii bar applet to also change the group by clicking with the mouse or rolling the wheel. It would be nice to have it integrated into my code, but I may just end up scripting something with setxkbmap.
3. Error handling - the program is more proof of concept right now. I will clean it up to do at least some error handling.

What window manager do you use? If you use ruby-wmii I'd be glad to give you the bar applet once its done. If you're using something else I could give you some code that would dump the current layout name to stdout.

Regards,
j

Offline

#4 2008-04-06 06:56:04

gradgrind
Member
From: Germany
Registered: 2005-10-06
Posts: 921

Re: Detecting current Xorg keyboard layout

Would the output of 'setxkbmap -print' be any use?

Maybe something like:

setxkbmap -print | grep xkb_symbols | sed 's|.*+\([^"]\+\).*|\1|'

That gives me:

de(nodeadkeys)

You can send this sort of thing back to setxkbmap using the -layout option to set the map, e.g.:

setxkbmap -layout 'de(nodeadkeys)'

Offline

#5 2008-04-06 07:17:38

peart
Member
From: Kanuckistan
Registered: 2003-07-28
Posts: 510

Re: Detecting current Xorg keyboard layout

Xfce's xkb plugin knows all about short country codes and switching layouts.  It might be worth a browse.
http://svn.xfce.org/index.cgi/xfce-good … ugin/xkb.c
http://svn.xfce.org/index.cgi/xfce-good … b-plugin.c

The first file seems more interesting.  The 2nd one is mostly GTK2 GUI stuff.

Offline

#6 2008-04-06 08:41:42

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

gradgrind wrote:

Would the output of 'setxkbmap -print' be any use?

Maybe something like:

setxkbmap -print | grep xkb_symbols | sed 's|.*+\([^"]\+\).*|\1|'

That gives me:

de(nodeadkeys)

I looked at setxkbmap, but it didn't pan out. Here's the xkb_symbols line from the output of setxkbmap -print for me:

xkb_symbols   { include "pc+us+latam:2+br:3+group(shifts_toggle)"    };

When I ran your command, I got "group(shifts_toggle)." Note the xkb_symbols line contains all three of the layouts I am using. This presents two problems. First, I did some experiments and there is no way to know which is the active layout. Second, I can get the layout abbreviations (maybe) but it's not clear that I could reliably associate the abbreviations with a layout, given the other noise in the line. Thanks for the suggestion, though.

peart wrote:

Xfce's xkb plugin knows all about short country codes and switching layouts.  It might be worth a browse.
http://svn.xfce.org/index.cgi/xfce-good … ugin/xkb.c

Thanks for the suggestion, I was looking at some of KDE's stuff and that's how I've gotten as far as I have, but I couldn't find where it set the layout (I believe it is managing the layouts via Qt rather than directly through libX11.) Perhaps the XFCE stuff will be a bit simpler.

Regards,
j

Offline

#7 2008-04-06 11:00:23

gradgrind
Member
From: Germany
Registered: 2005-10-06
Posts: 921

Re: Detecting current Xorg keyboard layout

jbromley wrote:

I looked at setxkbmap, but it didn't pan out. Here's the xkb_symbols line from the output of setxkbmap -print for me:

xkb_symbols   { include "pc+us+latam:2+br:3+group(shifts_toggle)"    };

... Note the xkb_symbols line contains all three of the layouts I am using.

Oh, wow, I see your problem. Out of interest, could you post the xorg.conf line(s) - or whatever else it was - that led to this?

Another idea that might get round this: if you are using some sort of gui for reading/setting keymap, you wouldn't really need all your layouts included in xorg.conf - you could just put them in the setter utility. But there might be some layouts that intrinsically wouldn't work with this method, I only tested a couple.

Anyway, if you find an acceptable solution, please let us know, it could be quite useful.

Offline

#8 2008-04-06 20:57:01

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

Here is the keyboard InputDevice section of my xorg.conf:

Section "InputDevice"
    Identifier  "Keyboard0"
    Driver      "keyboard"
    Option        "CoreKeyboard"
    Option        "XkbRules" "xorg"
    Option        "XkbModel" "pc101"
    Option        "XkbLayout" "us,latam,br"
    Option        "XkbOptions" "grp:shifts_toggle"
EndSection

The setxkbmap output looked kind of odd to me. I don't get the "pc+us+latam" part. Anyway, as you can see it is pretty much textbook setting up multiple language layouts. I don't use any GUI tools to manage the layout because I've never really needed it. In the past, when I used KDE, I used kkbswitch to show the current layout, but I still had the layouts in xorg.conf. I use xmodmap to map my multimedia keys, add a Mod3 key and a number of other custom keys and I've found that most GUI tools completely nuke my xmodmap setup because they are not aware of anything except the basic maps themselves.

Anyway, I've browsed the code for the XFCE xkb panel app (suggested by peart, thank you) and it looks promising. I just need to integrate switching layouts into the code I've already got and I think I'll be good. When I finish I'll be glad to post any code and Ruby scripts if anyone is interested.

Regards,
j

Offline

#9 2008-04-10 21:37:22

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

lman wrote:

I was wondering about the same thing. I use 4 keyboard layouts, never sure which one I'm using at the moment... big_smile

I've got a solution. I've got a C++ class that I wrapped with SWiG to make a ruby extension. This is useful for me since I use ruby-wmii. This allows me to get the group names and symbols and change the current group. I'd like to be able to respond to layout change events, but this is a bit more complicated and what I've got right now is useful.

If anyone else wants this or some variation (CLI program, etc.) let me know and I can probably put something together.

Regards,
j

Offline

#10 2008-04-12 08:13:44

gradgrind
Member
From: Germany
Registered: 2005-10-06
Posts: 921

Re: Detecting current Xorg keyboard layout

jbromley wrote:

I've got a solution. I've got a C++ class that I wrapped with SWiG to make a ruby extension. This is useful for me since I use ruby-wmii. This allows me to get the group names and symbols and change the current group. I'd like to be able to respond to layout change events, but this is a bit more complicated and what I've got right now is useful.

If anyone else wants this or some variation (CLI program, etc.) let me know and I can probably put something together.

Regards,
j

A CLI version would be great, but please post at least the C++ class.

Offline

#11 2008-04-18 04:53:53

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

gradgrind wrote:

A CLI version would be great, but please post at least the C++ class.

OK, then. You can get the tarball here. There is a README file in the tarball that will explain everything. The tarball contains the C++ class, the files necessary to build a Ruby extension, and a Ruby CLI script that can query and change XKB state.

Enjoy,
j

Offline

#12 2008-12-03 20:57:22

skualito
Member
Registered: 2008-11-19
Posts: 184

Re: Detecting current Xorg keyboard layout

Hi

OK, then. You can get the tarball here.

I don't succeed in building the ruby extension, I get the following errors after using swig and extconf, when running make:

g++ -I. -I/usr/lib/ruby/1.8/i686-linux -I/usr/lib/ruby/1.8/i686-linux -I. -D_FILE_OFFSET_BITS=64  -fPIC -march=i686 -mtune=generic -O2 -pipe  -fPIC    -c XKeyboard_wrap.cxx
XKeyboard_wrap.cxx: In function 'int _wrap_XKeyboard_group_names(void*, Tcl_Interp*, int, Tcl_Obj* const*)':
XKeyboard_wrap.cxx:1926: erreur: lvalue required as left operand of assignment
XKeyboard_wrap.cxx:1929: erreur: invalid conversion from 'Tcl_Obj*' to 'VALUE'
XKeyboard_wrap.cxx:1929: erreur:   initializing argument 1 of 'void rb_ary_store(VALUE, long int, VALUE)'
XKeyboard_wrap.cxx: In function 'int _wrap_XKeyboard_group_symbols(void*, Tcl_Interp*, int, Tcl_Obj* const*)':
XKeyboard_wrap.cxx:1953: erreur: lvalue required as left operand of assignment
XKeyboard_wrap.cxx:1956: erreur: invalid conversion from 'Tcl_Obj*' to 'VALUE'
XKeyboard_wrap.cxx:1956: erreur:   initializing argument 1 of 'void rb_ary_store(VALUE, long int, VALUE)'
make: *** [XKeyboard_wrap.o] Erreur 1

I use ruby-wmii and am trying to write a much simpler keyboard plugin for it. But I don't know anything about programming. I use only two layouts, us and dk.

It would be something like that in the big lines
--  info = %x{setxkbmap -print}.grep(/xkb_symbols/).first.split[3].sub(/\"pc\+/,'').sub(/\"/,'')  -->This gives in my case either "us" or "dk"
-- bar.data = #{info}
-- bar.on_click(....) do
   if info == "us"  'setxkbmap dk'    bar.data = "dk"
  else 'setxkbmap us'    bar.data = "us"

The problem is I don't know programming and I don't figure out how to update the #{info} when bar is clicked, and I don't succeed in actually changing the layout.
If anyone would give me some tips

Thanks

Skualito

Last edited by skualito (2008-12-04 19:40:23)

Offline

#13 2009-04-20 06:16:25

jazz1303
Member
Registered: 2009-04-20
Posts: 7

Re: Detecting current Xorg keyboard layout

You can also use the following script to change the keyboard layout:

if [ `setxkbmap -print | grep xkb_symbols | awk '{print $4}' | awk -F"+" '{print $2}'` = us ] ;then echo "EN"; echo "changing to RU..."; setxkbmap ru ; else echo "RU"; echo "Changing to US..."; setxkbmap us ; fi

Offline

#14 2009-04-20 09:53:09

skualito
Member
Registered: 2008-11-19
Posts: 184

Re: Detecting current Xorg keyboard layout

Thanks jazz1303. That's what I needed smile

Offline

#15 2009-06-06 00:21:34

damjan
Member
Registered: 2006-05-30
Posts: 310

Re: Detecting current Xorg keyboard layout

btw, have you seen libxklavier?
it's a somewhat more high-level library for doing keyboard layout stuff.

http://library.gnome.org/devel/libxklavier/3.2/

Offline

#16 2009-06-06 06:42:37

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

skualito wrote:

I don't succeed in building the ruby extension, I get the following errors after using swig and extconf, when running make:

g++ -I. -I/usr/lib/ruby/1.8/i686-linux -I/usr/lib/ruby/1.8/i686-linux -I. -D_FILE_OFFSET_BITS=64  -fPIC -march=i686 -mtune=generic -O2 -pipe  -fPIC    -c XKeyboard_wrap.cxx
XKeyboard_wrap.cxx: In function 'int _wrap_XKeyboard_group_names(void*, Tcl_Interp*, int, Tcl_Obj* const*)':
XKeyboard_wrap.cxx:1926: erreur: lvalue required as left operand of assignment
XKeyboard_wrap.cxx:1929: erreur: invalid conversion from 'Tcl_Obj*' to 'VALUE'
XKeyboard_wrap.cxx:1929: erreur:   initializing argument 1 of 'void rb_ary_store(VALUE, long int, VALUE)'
XKeyboard_wrap.cxx: In function 'int _wrap_XKeyboard_group_symbols(void*, Tcl_Interp*, int, Tcl_Obj* const*)':
XKeyboard_wrap.cxx:1953: erreur: lvalue required as left operand of assignment
XKeyboard_wrap.cxx:1956: erreur: invalid conversion from 'Tcl_Obj*' to 'VALUE'
XKeyboard_wrap.cxx:1956: erreur:   initializing argument 1 of 'void rb_ary_store(VALUE, long int, VALUE)'
make: *** [XKeyboard_wrap.o] Erreur 1

Hello there. I realize this is some months late, but just for posterity, I've looked at the problem and it turns out that for some reason the std::vector<std::string> to ruby array mapping in XKeyboard.i wasn't working any more. I fixed the problem and uploaded a new tarball. You can get it here.

Regards.

Offline

#17 2009-06-06 06:43:39

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

bergundy wrote:

thanks jbromley,

your code really helped me.
...

I'm glad to hear someone has made use of it. I've just patched up the ruby wrappers, so the ruby extension should be working again.

Enjoy.

Offline

#18 2009-08-10 08:49:08

veox
Member
Registered: 2008-10-28
Posts: 45

Re: Detecting current Xorg keyboard layout

jbromley, bergundy - thanks for the code, weird there was no such utility already.

Offline

#19 2009-08-10 10:57:09

veox
Member
Registered: 2008-10-28
Posts: 45

Re: Detecting current Xorg keyboard layout

I thought a bit and made it into a package: http://aur.archlinux.org/packages.php?ID=29137

There're some issues so far, though: no LICENSE defined, a few improvements needed to be made to the Makefiles (so far done during package build).

Offline

#20 2009-08-10 17:20:14

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

veox wrote:

I thought a bit and made it into a package: http://aur.archlinux.org/packages.php?ID=29137

There're some issues so far, though: no LICENSE defined, a few improvements needed to be made to the Makefiles (so far done during package build).

You can make the license whatever you'd like. If this code helps anyone then let's just get it out there.

Offline

#21 2009-08-13 10:28:57

veox
Member
Registered: 2008-10-28
Posts: 45

Re: Detecting current Xorg keyboard layout

I'd make it GPLv3 (or v2), but as a packager I have no authorito to put a license in. It must be distributed with the code; or, I guess, the authors must at least explicitly specify it on the site.

Alternatively, just say it's in the public domain.

Last edited by veox (2009-08-13 10:45:28)

Offline

#22 2009-08-13 20:28:21

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

veox wrote:

I'd make it GPLv3 (or v2), but as a packager I have no authorito to put a license in. It must be distributed with the code; or, I guess, the authors must at least explicitly specify it on the site.

Alternatively, just say it's in the public domain.

This weekend I'll try to add some license information so you can package it up.

Offline

#23 2009-08-13 23:08:06

anrxc
Member
From: Croatia
Registered: 2008-03-22
Posts: 833
Website

Re: Detecting current Xorg keyboard layout

veox wrote:

thanks for the code, weird there was no such utility already.

http://www.archlinux.org/packages/search/?q=xxkb


You need to install an RTFM interface.

Offline

#24 2009-08-14 04:49:11

jbromley
Member
From: Pasadena, CA
Registered: 2007-02-04
Posts: 268

Re: Detecting current Xorg keyboard layout

anrxc wrote:
veox wrote:

thanks for the code, weird there was no such utility already.

http://www.archlinux.org/packages/search/?q=xxkb

I looked at it and it was not satisfying. Here is why I wrote the code under discussion.

1. I use xmodmap to modify my keyboard layout. Switching with xxkb (or any other layout switcher, I've tried those from GNOME, KDE, and XFCE)  nuked my custom key configuration. I could find no way to make these tools pay attention to my custom layout. This was a huge problem for me.

2. Most switchers are tray apps. At the time I was wrote this I was using wmii, which had (has?) no system tray. These tools also generally require that you use the mouse, something that I avoid.

3. I was writing a bunch of modules for wmii-ruby and I thought, why not?

So certainly similar software existed, but still there was none that did exactly what I wanted.

Regards.

Offline

#25 2009-09-14 10:58:09

yhager
Member
Registered: 2009-08-21
Posts: 6

Re: Detecting current Xorg keyboard layout

jbromley, thanks for the code, it works perfectly.

Just to complete it, I have created a very simple bar applet for ruby-wmii that displays the current layout, and allows me to change it on a click of a mouse:

  bar_applet("xkb", 900) do |wmii, bar|
    require 'ruby-wmii/xkb'
    xkb = Xkb::XKeyboard.new
    Thread.new do
      loop do
        bar.data = xkb.current_group_symbol
        sleep 1
      end
    end
    bar.on_click do |name, button|
      curr_group = xkb.current_group_num
      curr_group += 1
      xkb.set_group_by_num curr_group
      bar.data = xkb.current_group_symbol
    end
  end

Offline

Board footer

Powered by FluxBB