Библиотека сайта rus-linux.net
Ввод русских букв в XFree86.
В статье рассказывается о настройке xkb - составной части XFree86 - для работы с русской клавиатурой. Мы не касаемся здесь вопросов, связанных со шрифтами - это предмет отдельной статьи.
Установка системной locale.
Описание клавиатуры в XF86Config.
"Правильные" и "неправильные" приложения.
Мы предполагаем далее, что на вашем компьютере установлена XFree >=3.3.2.
Если вас интересует только результат - читайте лишь разделы HOW.
Внимание очень важно!
Сразу после установки KDE удалите kikbd и поставте kkb (об этом написано ниже)!
Установка системной locale.
HOW
Если у Вас дистрибутив, построенный на glibc (Debian 2.x, Red Hat 5.x, SuSE 6.x, Stampede, Mandrake), то все необходимое для компиляции системной locale вы найдете в /usr/share/i18n/locales и /usr/share/i18n/charmaps. В противном случае, поместите файл с описанием русской locale в /usr/share/i18n/locales, а файл с описанием KOI8-R - в /usr/share/i18n/charmap.
После компиляции
$ localedef -f KOI8-R -i ru_RU ru_RU.KOI8-R
вы найдете каталог ru_RU.koi8r в /usr/share/locale.
Переименуйте его:
$ cd /usr/share/locale
$ mv -f ru_RU.koi8r ru_RU.KOI8-R
и установите значение системной переменной LANG
$ export LANG=ru_RU.KOI8-R
или, если вы работаете в csh:
$ setenv LANG ru_RU.KOI8-R
Установку переменной LANG можно поместить в
- /etc/profile в Debian,
- /etc/profile.local - в SuSE (в нашем пакете русификации консоли это сделано несколько лучше, через rc.config) - export LANG=ru_RU.KOI8-R
- файл /etc/sysconfig/i18n - в RedHat (LANG=ru_RU.KOI8-R).
WHY
Установка русской системной locale является абсолютно необходимой для русификации ввода в X, так как без этого не будет правильно установлена X locale. Название locale - ru_RU.KOI8-R - соответствует стандарту POSIX (язык[_ТЕРРИТОРИЯ[.кодировка]]) и, кроме того, позволяет избежать модификации файла /usr/X11R6/lib/X11/locale/locale.alias, так как X-locale koi8-r соответствует именно ru_RU.KOI8-R. locale, называемая в Red Hat (а теперь и в glibc 2.1) ru_SU на самом деле и есть ru_RU.KOI8-R, так что можно просто переименовать соответствующий каталог.
Утилита localedef из пакета libc по непонятным причинам (bug или feature?) делает всем символам в названии кодировки tolower() и убирает дефис, чем и объясняется странная операция переименования каталога.
Для правильной установки X-locale достаточно определения категории locale LC_CTYPE:
$ export LC_CTYPE=ru_RU.KOI8-R
Остальными категориями вы можете манипулировать по своему усмотрению. Например, если вам не нравится десятичная запятая (почему?) , то можно установить
$ export LC_NUMERIC=POSIX
и десятичным разделителем станет точка. Только не используйте "исправленных" locale тем более, что абсолютно никаких причин для этого нет. Если это совершенно необходимо - измените отдельную категорию. Последний совет: не используйте в shell переменную LC_ALL. Установив ее, вы не сможете изменить другие категории. Эта переменная - для программ.
Подробно о locale читайте на странице Александра Воропая. Мы посвятим этой теме отдельную статью.
Описание клавиатуры в XF86Config.
HOW
Файл /etc/XF86Config (или /etc/X11/XF86Config) создается любым конфигуратором X: Xconfigurator, XF86Setup, SaX, xf86config. (XF86Setup и SaX спросят вас о типе клавиатуры. Выберите русскую.) Добавьте путь к русским KOI8 - шрифтам в секцию Files (здесь мы не рассказываем о том, как это сделать) и посмотрите на содержимое секции Keyboard, точнее - на переменные, начинающиеся с Xkb. Переменной XkbDisable не должно быть в файле или строчка с ней должна начинаться с #. Переменная XkbModel, напротив, должна присутствовать. Значение переменной XkbLayout установите в "ru":
XkbLayout "ru"
В начале строки с переменной XkbOptions пока поставьте # - знак комментария.
Убедитесь, что в Вашем домашнем каталоге нет файла .Xmodmap, а также, что при запуске X не начнут автоматически выполняться программы xruskb и kikbd. Настройка, точнее ее основная часть, закончена. Запустите xterm в X и убедитесь, что нажатие на CapsLock и удержание правой клавиши Alt переключает группы Рус/Lat.
Скорее всего, вас не удовлетворит раскладка клавиатуры - цифры в верхнем ряду набираются при нажатом Shift. Если это действительно так, то поместите в каталог /usr/X11R6/lib/X11/xkb/symbols раскладку ru1 для обычной клавиатуры и rums - для клавиатуры с клавишами MS, а затем исправьте строчку XkbLayout в XF86Config, указав вместо ru - ru1 или ru-ms. Если же и эти раскладки вас не устроили, - поправьте файлы раскладок, с их мнемоникой разобраться совсемнесложно.
Если вы не удовлетворены клавишей CapsLock в качестве переключателя раскладок, то измените строчку XkbLatout, добавив после названия раскладки слово basic в скобках, например:
XkbLayout "ru-ms(basic)"
и определите переменную XkbOptions. Она может, в частности, принимать значения (все они описаны в файле /usr/X11R6/lib/X11/xkb/symbols/rules/xfree86.lst):
grp:toggle - переключение правым Alt,
grp:shift_toggle - двумя клавишами shift,
grp:ctrl_shift_toggle - ctrl+shift,
grp:ctrl_alt_toggle - ctrl+alt.
Например, строка
XkbOptions "grp:shift_toggle"
задает переключение Рус/Lat двумя клавишами shift.
Наконец, если вам очень хочется, чтобы при переключении раскладок загоралась лампочка ScrollLock, то можно сделать и это. Посмотрите в каталог /usr/X11R6/lib/X11/xkb/compat. Если в нем нет файла group_led, - возьмите его здесь (files/xf86_rus/group_led). Затем загрузите в любой редактор файл /usr/X11R6/lib/X11/xkb/rules/xfree86 и найдите в нем первое вхождение слова complete, оно должно быть под словом compat. Замените это вхождение complete на group_led и сохраните измененный файл. При очередном запуске X лампочка ScrollLock будет сигнализировать о переключении алфавитов. Заметим, однако, что нажате на клавишу ScrollLock также зажжет лампочку, но изменения группы клавиатуры не вызовет.
Можно использовать и экранный индикатор групп клавиатуры. Один из них - fookb Алексея Выскубова, он особенно красив в WindowMaker. Другой - kkb 0.1.5 Петра Новодворского, он сделан для KDE. (Версии kkb после 0.2. выполняют значительно более интересные функции, о них мы расскажем ниже.)
WHY
Существует три способа описания клавиатуры в секции Keyboard файла XF86Config. Первый - при помощи первичных переменных Xkb: XkbKeycodes, XkbCompst, XkbTypes, XkbSymbols и XkbGeometry. XkbGeometry указывает на описание геометрии клавиатуры, которое может понадобиться графическим программам настройки. Значение по умолчанию - "pc" (файл geometry/pc). XkbKeycodes указывает на файл с мнемоническими обозначениями клавиш и соответствующими им scan-кодами, по умолчанию "xfree86" (keycodes/xfree86). XkbTypes и XkbCompat указывают на файлы с макроопределениями в соответствующих каталогах (по умолчанию - "default"). Наконец, XkbSymbols - файл с раскладкой клавиатуры, точнее, - последовательность файлов, объединяемых знаками +. Например, конфигурации с русской ms-клавиатурой и переключателем ctrl+shift соответствует
XkbSymbols "en_US(pc102)+rums(basic)+group(ctrl_shift_toggle)"
А для лампочки индикатора достаточно добавить
XkbCompat "group_led"
Этих двух строк вполне достаточно. Мы однако, не советуем применять этот способ, так как в этом случае не будет работать утилита setxkbmap и программа kkb (с версии 0.2).
Второй способ позволяет задать только значение макропеременной XkbKeymap. Каждое из ее значений имеет вид "файл(запись)". Файл ищется в каталоге keymap, а запись содержит значения пяти базовых переменных. Для русской клавиатуры определена одна запись ru в файле xfree86, что соответствует
XkbKeymap "xfree86(ru)"
Третий способ используется всеми программами настройки XFree86 и именно о нем мы рассказывали выше. В каталоге rules содержатся базы данных со значениями первичных переменных Xkb. По умолчанию используется база xfree86. Необходимые значения переменных определяются заданием ключей XkbModel (модель клавиатуры), XkbLayout, XkbOptions, XkbVariant. Ключ XkbVariant указывает на наличие или отсутствие "мертвых клавиш".
Наибольший интерес представляют файлы в каталоге symbols, определяющие раскладку клавиатуры. Рассмотрим содержимое одного из них - /usr/X11R6/lib/X11/xkb/symbols/ru. Первая содержащаяся в нем раскладка (она же - умалчиваемая) выглядит так:
xkb_symbols "toggle" { include "ru(basic)" key <CAPS> { [ ISO_Next_Group, Caps_Lock ] }; };Называется она ru(toggle) , включает раскладку ru(basic) и определяет в качестве клавиши переключения групп <CAPS>, то есть Caps Lock. Соответствие скан-кодов клавиш и их имен приведено, напомним, в keycodes/xfree86 (или другом файле из каталога keycodes).
Базовая раскладка - ru(basic): xkb_symbols "basic" { name[Group1]="US/ASCII"; name[Group2]="Russian"; key <TLDE>{[grave, asciitilde],[Cyrillic_io,Cyrillic_IO]};Здесь указаны имена групп (их может быть до четырех) , а каждой клавише соответствует описание символов, - без shift и с ним в каждой из групп. В отличие от старого метода, часто называемого xmodmap (что неточно, правильнее - core protocol ), в раскладках xkb присутствуют не однобайтовые коды символов, а двухбайтовые коды букв различных алфавитов. Их численные значения можно посмотреть в /usr/X11R6/lib/X11/include/X11/keysymdef.h. Для кириллицы там выделены коды со старшим байтом 6. Очень важно, что символы XK_Cyrillic_* не привязаны ни к одной из кодировок - KOI8-R, ISO8859-5 или другим! Таким образом, X Window System всегда знает, какая буква какого алфавита введена, а кодировку узнает из своей(!) X locale. Вот почему при установке системной locale ru_RU, которая соответствует в таблице locale.alias ISO8859-5, на экран будет выводится текст в кодировке ISO8859-5.
Заметим также, что выбор кодировки зашит в исходные тексты XFree, а там известно только два кода для кириллицы - ISO8859-5 и KOI8-R. Поэтому ответ на вопрос о полноценном использовании в X cp1251, cp866, KOI8-U - отрицательный! Интересующихся адресуем к текстам - обратите особое внимание на XKBCvt.c и imConv.c в xc/lib/X11. Именно здесь надо править (точнее, дополнять) с целью подключения новых кодировок.
Отметим еще одну особенность обработки вводимых кириллических букв. Каждая из них проверяется на принадлежность к активной таблице символов. Это приводит к тому, что, например, украинская буква XK_Ukrainian_i, хоть и имеет старший байт 6, будет отброшена при активной X locale koi8-r. Она, однако, будет принята при установленной ISO8859-5, так как входит в соответствующую таблицу символов.
"Правильные" и "неправильные" приложения.
HOW
Настроив русскую клавиатуру, мы обнаружим, что решена проблема ввода русских букв в glibc-версиях Netscape 4.* (при установке View->Charscter Set-> KO8-R), правильно воспринимает кириллицу Gimp, а также xterm и xedit . Заметим, что приемы с подменой шрифтов и wrapper'ами для Netscape больше не нужны, более того - противопоказаны (если Ваш Netscape не принимает русского, - уберите wrapper, вызовите его напрямую). Однако, возникли проблемы с LyX, StarOffice и Applix. Эти программы принимают только буквы Latin-1 (ISO8859-1). придется пойти им навстречу, заменив в описании клавиатуры буквы кириллицы на буквы второй половины кодовой таблицы Latin-1 , всякие diaeresis и ugrave. Такое описание для русской клавиатуры с клавишами MS можно взять здесь (ссылка не работает). Можно пойти еще дальше и сделать раскладки для cp1251 и KOI8_U. Все их надо положить в /usr/X11R6/lib/X11/xkb/symbols. Использовать эти раскладки без прямой необходимости не рекомендуется, более того, с "правильными" Netscape и Gimp он работать не будут, но для "неправильных" приложений - подойдут.
Итак, принципиально вопрос ввода русских букв решен, но как же переключать раскладки ? До сих пор мы задавали одну из них в XF86Config на все время работы в X. Есть несколько способов.
Первый - утилита setxkbmap. Ей достаточно указать файл раскладки:
$ setxkbmap -layout "ruhackms"
Второй способ - использование якобы "неправильной" утилиты xmodmap. Для нее надо приготовить файлы. Делается это так: - загружаем раскладку
$ xmodmap -pke > ruxx.xmm
Сделав таким образом файлы .xmm для "правильных" и "неправильных" раскладок, мы можем потом загружать их:
$ xmodmap ruxx.xmm
Утилита xmodmap реабилитирована - она отлично работает с Xkb!
Теперь можно написать скрипты для переключения раскладок, вынести иконки на desktop, и так далее. Можно даже использовать файл .Xmodmap, хотя неясно - зачем.
Третий способ - самый легкий - воспользоваться программой kkb >=0.2. Она содержит описания нескольких русских, украинской, немецкой, американской и других клавиатур. kkb написана для KDE, но для ее работы достаточно библиотек Qt и kdelibs, - вы можете запустить ее из любого window manager'а. Используя kkb вы можете переключать и группы, и раскладки.
Остались ли программы, не принимающие русских букв. Нет! Остались программы, которые не хотят выводить русские шрифты. Автор этих строк знает одну такую программу - текстовый редактор Maxwell. Его, правда, тоже можно обмануть, но он того не стоит...
Заметим, что описанный метод не модифицирует XFree, он является строго внешним по отношению к системе, а следовательно, позволяет свободно ее обновлять. Метод также не привязан ни к одному из дистрибутивов Linux.
WHY
Заметим, что использование 1251 в Linux - это очень плохо. Не потому, что эта кодировка плохая (она во многом лучше KOI8-R) и не потому, что пришла от MS. Просто в системе должна быть одна кодировка для языка, так как переключать раскладки - это полбеды, а вот переключать locale в online - ужасно. Работать же в кодировке, которая не соответствует locale - не лучше. Реально 1251 нужна только для офисных систем, но каждая из них имеет свой язычок типа basic'а, в котором можно написать перекодировщик буфера. Будем надеяться, что кто-нибудь этим займется, так как ждать милости от Star Division или Applix не приходится.
По поводу xmodmap. Как видно из вышесказанного, дело не в том, какой из утилит (и функций Xlib) загружается раскладка, а в том, как осуществляется переключение Рус/Lat, - при помощи xkb или core protocol. В программе kikbd, например, вы можете в описании русской клавиатуры успешно заменить однобайтовый код буквы Г на Cyrillic_Ghe, но все равно, при переключении на русский не будут работать Ctrl - клавиши, а если screensaver требует пароля, то ввести его вы не сможете.
В режиме xkb для ввода русских букв в xemacs надо определить Cyrillic_*. Пример файла .emacs можно найти в наших пакетах русификации, а можно - на сайте автора идеи Алексей Выскубова.
И последнее. Для обучения free software работе с xkb нужно, зачастую, совсем немного : добавить ближе к началу текста вызов XtSetLanguageProc(NULL,NULL,NULL); Автор этого замечания - Андрей Чернов, на сайте которого вы найдете лаконичное, но полное по сути изложение основ правильной русификации X и обоснование того, почему это нужно.