Читаем Программирование в X Window средствами Free Pascal полностью

Клавиши-модификаторы также имеют логические коды. Клавишам Shift сопоставлены символы XK_Shift_L и XK_Shift_R; Caps Lock соответствует XK_CapsLock; Control - XK_Control_L; Mod1 - XK_Meta_L и XK_Meta_R. Символы остальных модификаторов (Mod2 - Mod5) не определены. X содержит набор специальных процедур, которые позволяют получить и установить соответствие код-символ для модификаторов. Эти функции следующие: XGetModifierMapping, XInsertModifiermapEntry, XDeleteModifiermapEntry, XSetModifierMapping.

X не останавливается на задании соответствия код клавиши - символы, а идет дальше. Система позволяет программе сопоставить любой комбинации модификаторов и клавиш (например, ‹Shift+Ctrl+A›) ASCII строку (например, "EXIT"). Для некоторых клавиш соответствующие строки задаются сервером по умолчанию. Так, символу XK_A соответствует строка "A".

Макрос XRebindKeysym берет символ, список модификаторов и сопоставляет им строку.

Процедура XLookupString, наоборот, берет событие о нажатии (отпускании) клавиши и возвращает соответствующие ему символ и строку. Последний ее параметр - указатель на структуру типа XComposeStatus. Дело в том, что некоторые клавиатуры имеют специальную клавишу Compose, которая позволяет печатать символы, которым нет соответствия среди клавиш. Специальная таблица указывает, какой символ должен быть создан, если обычная клавиша нажимается одновременно с Compose. Ссылка на эту информацию и возвращается в структуре XComposeStatus.

Ниже приводится фрагмент программы, которая распознает функциональные клавиши ‹F1›-‹F5›, и при их нажатии печатает соответствующую строку. Программа также сопоставляет комбинации ‹Shift+Control+A› строку "EXIT". Эта комбинация используется для завершения программы.

var

 prDisplay: PDisplay;

 nScreenNum: integer;

 prGC: TGC;

 rEvent: TXEvent;

 nWnd: TWindow;

 sKeyStr: array [0…19] of char;

 nKeySym: TKeySym;

 naModList: array [0…1] of TKeySym;

 n: integer;

 r: char;


const

 XK_Control_L=$FFE3; (* Left control *)

 XK_Shift_L=$FFE1; (* Left shift *)

 XK_F1=$FFBE;

 XK_F2=$FFBF;

 XK_F3=$FFC0;

 XK_F4=$FFC1;

 XK_F5=$FFC2;

 XK_F6=$FFC3;


 (* Устанавливаем связь с сервером, получаем номер экрана… *)

 (* Задаем соответствие символ-строка *)

 naModList[0]:= XK_Control_L;

 naModList[1]:= XK_Shift_L;

 XRebindKeysym (prDisplay, XK_F6, naModList, 2, 'EXIT', strlen('EXIT'));

 (* Цикл получения и обработки событий *)

 while true do begin

  XNextEvent (prDisplay, @rEvent);

  case (rEvent.eventtype) of

  KeyPress:

  begin

   (* Очищаем строку *)

   for n:=0 to 19 do sKeyStr[n]:=#0;


   (* Получаем строку, соответствующую событию *)

   XLookupString (@rEvent.xkey, sKeyStr, 20, @nKeySym, NIL);

   if (strcomp (sKeyStr, 'EXIT')=0) then

   begin

    XFreeGC (prDisplay, prGC);

    XCloseDisplay (prDisplay);

    halt (0);

   end;


   case nKeySym of

   XK_F1: r:='1';

   XK_F2: r:='2';

   XK_F3: r:='3';

   XK_F4: r:='4';

   XK_F5: r:='5';

   else r:='0';

   end;


   if (n<>0) then begin

    sKeyStr[0]:='F';

    sKeyStr[1]:=r;

    sKeyStr[2]:=#0;

    strcat(sKeyStr, ' pressed.');

    XClearWindow (prDisplay, nWnd);

    XDrawString (prDisplay, nWnd, prGC, 10, 50, sKeyStr, strlen (sKeyStr));

   end;

  end;

 end;

end;

Сервер имеет ряд атрибутов, воздействующих на обработку сигналов клавиатуры. Получить их можно с помощью функции XGetKeyboardControl. Она возвращает указанные параметры в переменной, имеющей тип TXKeyboardState, определенный следующим образом:

TXKeyboardControl = record

 key_click_percent: longint;

 bell_percent: longint;

 bell_pitch: longint;

 bell_duration: longint;

 led: longint;

 led_mode: longint;

 key: longint;

 auto_repeat_mode: longint;

 end;

PXKeyboardControl = ^TXKeyboardControl;

Перейти на страницу:
Нет соединения с сервером, попробуйте зайти чуть позже