|  | Wine now needs to know about your keyboard layout. This requirement comes from | 
|  | a need from many apps to have the correct scancodes available, since they read | 
|  | these directly, instead of just taking the characters returned by the X server. | 
|  | This means that Wine now needs to have a mapping from X keys to the scancodes | 
|  | these applications expect. | 
|  |  | 
|  | On startup, Wine will try to recognize the active X layout by seeing if it | 
|  | matches any of the defined tables. If it does, everything is allright. If not, | 
|  | you need to define it. | 
|  |  | 
|  | To do this, open the file windows/x11drv/keyboard.c and take a look at the | 
|  | existing tables. Make a backup copy of it, especially if you don't use CVS. | 
|  |  | 
|  | What you really would need to do, is to find out which scancode each key needs | 
|  | to generate, find it in the main_key_scan table, which looks like this | 
|  |  | 
|  | static const int main_key_scan[MAIN_LEN] = | 
|  | { | 
|  | /* this is my (102-key) keyboard layout, sorry if it doesn't quite match yours */ | 
|  | 0x29,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0A,0x0B,0x0C,0x0D, | 
|  | 0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B, | 
|  | 0x1E,0x1F,0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x2B, | 
|  | 0x2C,0x2D,0x2E,0x2F,0x30,0x31,0x32,0x33,0x34,0x35, | 
|  | 0x56 /* the 102nd key (actually to the right of l-shift) */ | 
|  | }; | 
|  |  | 
|  | and then assign each scancode the characters imprinted on the keycaps. This | 
|  | was done (sort of) for the US 101-key keyboard, which you can find near the | 
|  | top in keyboard.c. It also shows that if there is no 102nd key, you can skip | 
|  | that. | 
|  |  | 
|  | However, for most international 102-key keyboards, we have done it easy for you. | 
|  | The scancode layout for these already pretty much matches the physical layout | 
|  | in the main_key_scan, so all you need to do is to go through all the keys that | 
|  | generate characters on your main keyboard (except spacebar), and stuff those | 
|  | into an appropriate table. The only exception is that the 102nd key, which is | 
|  | usually to the left of the first key of the last line (usually Z), must be | 
|  | placed on a separate line after the last line. | 
|  |  | 
|  | For example, my Norwegian keyboard looks like this | 
|  |  | 
|  | §  !  "  #  ¤  %  &  /  (  )  =  ?  `  Back- | 
|  | |  1  2@ 3£ 4$ 5  6  7{ 8[ 9] 0} +  \´ space | 
|  |  | 
|  | Tab Q  W  E  R  T  Y  U  I  O  P  Å  ^ | 
|  | ¨~ | 
|  | Enter | 
|  | Caps A  S  D  F  G  H  J  K  L  Ø  Æ  * | 
|  | Lock                                  ' | 
|  |  | 
|  | Sh- > Z  X  C  V  B  N  M  ;  :  _  Shift | 
|  | ift <                      ,  .  - | 
|  |  | 
|  | Ctrl  Alt       Spacebar       AltGr  Ctrl | 
|  |  | 
|  |  | 
|  | Note the 102nd key, which is the "<>" key, to the left of Z. The character | 
|  | to the right of the main character is the character generated by AltGr. | 
|  |  | 
|  | This keyboard is defined as follows: | 
|  |  | 
|  | static const char main_key_NO[MAIN_LEN][4] = | 
|  | { | 
|  | "|§","1!","2\"@","3#£","4¤$","5%","6&","7/{","8([","9)]","0=}","+?","\\´", | 
|  | "qQ","wW","eE","rR","tT","yY","uU","iI","oO","pP","åÅ","¨^~", | 
|  | "aA","sS","dD","fF","gG","hH","jJ","kK","lL","øØ","æÆ","'*", | 
|  | "zZ","xX","cC","vV","bB","nN","mM",",;",".:","-_", | 
|  | "<>" | 
|  | }; | 
|  |  | 
|  | Except that " and \ needs to be quoted with a backslash, and that the 102nd | 
|  | key is on a separate line, it's pretty straightforward. | 
|  |  | 
|  | After you have written such a table, you need to add it to the main_key_tab[] | 
|  | layout index table. This will look like this: | 
|  |  | 
|  | static struct { | 
|  | WORD lang, ansi_codepage, oem_codepage; | 
|  | const char (*key)[MAIN_LEN][4]; | 
|  | } main_key_tab[]={ | 
|  | ... | 
|  | ... | 
|  | {MAKELANGID(LANG_NORWEGIAN,SUBLANG_DEFAULT),  1252, 865, &main_key_NO}, | 
|  | ... | 
|  |  | 
|  | After you have added your table, recompile Wine and test that it works. | 
|  | If it fails to detect your table, try running | 
|  |  | 
|  | wine -debugmsg +key,+keyboard >& key.log | 
|  |  | 
|  | and look in the resulting key.log file to find the error messages it | 
|  | gives for your layout. | 
|  |  | 
|  | Note that the LANG_* and SUBLANG_* definitions are in include/winnls.h, | 
|  | which you might need to know to find out which numbers your language | 
|  | is assigned, and find it in the debugmsg output. The numbers will | 
|  | be SUBLANG * 0x400 + LANG, so, for example the combination | 
|  | LANG_NORWEGIAN (0x14) and SUBLANG_DEFAULT (0x1) will be (in hex) | 
|  | 14 + 1*400 = 414, so since I'm Norwegian, I could look for 0414 in | 
|  | the debugmsg output to find out why my keyboard won't detect. | 
|  |  | 
|  | Once it works, submit it to the Wine project. If you use CVS, you | 
|  | will just have to do | 
|  |  | 
|  | cvs -z3 diff -u windows/x11drv/keyboard.c > layout.diff | 
|  |  | 
|  | from your main Wine directory, then submit layout.diff to | 
|  | wine-patches@winehq.com along with a brief note of what it is. | 
|  |  | 
|  | If you don't use CVS, you need to do | 
|  |  | 
|  | diff -u the_backup_file_you_made windows/x11drv/keyboard.c > layout.diff | 
|  |  | 
|  | and submit it as explained above. | 
|  |  | 
|  | If you did it right, it will be included in the next Wine release, and all | 
|  | the troublesome applications (especially remote-control applications) and | 
|  | games that use scancodes will be happily using your keyboard layout, and you | 
|  | won't get those annoying fixme messages either. | 
|  |  | 
|  | Good luck. | 
|  |  | 
|  | -Ove Kåven <ovek@arcticnet.no> |