GVKun编程网logo

在没有 X11 的情况下获取 Linux 中 Keycode 的 Keymap 等效字符

2

如果您想了解在没有X11的情况下获取Linux中Keycode的Keymap等效字符的知识,那么本篇文章将是您的不二之选。同时我们将深入剖析Atom飞行手册翻译:4.2深入键表(keymap)、Chr

如果您想了解在没有 X11 的情况下获取 Linux 中 Keycode 的 Keymap 等效字符的知识,那么本篇文章将是您的不二之选。同时我们将深入剖析Atom飞行手册翻译: 4.2 深入键表(keymap)、Chrome/Chromium 的 Ozone X11 代码全面启用,旧版 X11 代码将删除、Clockify API - 如何在不使用 Web UI 的情况下获取 API 密钥/令牌、fbterm keymap 键盘问题的各个方面,并给出实际的案例分析,希望能帮助到您!

本文目录一览:

在没有 X11 的情况下获取 Linux 中 Keycode 的 Keymap 等效字符

在没有 X11 的情况下获取 Linux 中 Keycode 的 Keymap 等效字符

如何解决在没有 X11 的情况下获取 Linux 中 Keycode 的 Keymap 等效字符

我正在编写一个控制台程序,它在纯文本控制台上运行。我需要同时接收按键和按键释放事件。但我还需要支持非英语语言的键盘布局。我在以下代码中接收键代码以及按下和释放的事件,但我需要根据当前的键盘映射将该键代码转换为其相应的 utf-8 字符。我该怎么办?

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <getopt.h>
#include <signal.h>
#include <fcntl.h>
#include <termios.h>
#include <locale.h>
#include <linux/kd.h>
#include <linux/keyboard.h>
#include <sys/ioctl.h>


int fd;
int oldkbmode;

struct termios old;

#define _(a) (a)

static int
is_a_console(int fd) 
{
    char arg;
    arg = 0;
    return (ioctl(fd,KDGKBTYPE,&arg) == 0
        && ((arg == KB_101) || (arg == KB_84)));
}

static int
open_a_console(const char *fnam) 
{
    int fd;
    /*
     * For ioctl purposes we only need some fd and permissions
     * do not matter. But setfont:activatemap() does a write.
     */
    fd = open(fnam,O_RDWR);
    if (fd < 0 && errno == EACCES)
        fd = open(fnam,O_WRONLY);
    if (fd < 0 && errno == EACCES)
        fd = open(fnam,O_RDONLY);
    if (fd < 0)
        return -1;
    if (!is_a_console(fd)) {
        close(fd);
        return -1;
    }
    return fd;
}

int 
getfd(const char *fnam) 
{
    int fd;
    if (fnam) {
        fd = open_a_console(fnam);
        if (fd >= 0)
            return fd;
        fprintf(stderr,_("Couldnt open %s\\n"),fnam);
        exit(1);
    }
    fd = open_a_console("/dev/tty");
    if (fd >= 0)
        return fd;
    fd = open_a_console("/dev/tty0");
    if (fd >= 0)
        return fd;
    fd = open_a_console("/dev/vc/0");
    if (fd >= 0)
        return fd;
    fd = open_a_console("/dev/console");
    if (fd >= 0)
        return fd;
    for (fd = 0; fd < 3; fd++)
        if (is_a_console(fd))
            return fd;
    fprintf(stderr,_("Couldnt get a file descriptor referring to the console\\n"));
    exit(1);        /* total failure */
}

static void
get_mode(void) 
{
        char *m;
    if (ioctl(fd,KDGKBMODE,&oldkbmode)) {
        perror("KDGKBMODE");
        exit(1);
    }
    switch(oldkbmode) {
      case K_RAW:
        m = "RAW"; break;
      case K_XLATE:
        m = "XLATE"; break;
      case K_MEDIUMRAW:
        m = "MEDIUMRAW"; break;
      case K_UNICODE:
        m = "UNICODE"; break;
      default:
        m = _("?UNKNowN?"); break;
    }
    printf(_("kb mode was %s\\n"),m);
    if (oldkbmode != K_XLATE) {
        printf(_("[ if you are trying this under X,it might not work\\n"
             "since the X server is also reading /dev/console ]\\n"));
    }
    printf("\\n");
}

static void
clean_up(void) 
{
    if (ioctl(fd,KDSKBMODE,oldkbmode)) {
        perror("KDSKBMODE");
        exit(1);
    }
    if (tcsetattr(fd,&old) == -1)
        perror("tcsetattr");
    close(fd);
}

static void
die(int x) 
{
    printf(_("caught signal %d,cleaning up...\\n"),x);
    clean_up();
    exit(1);
}

static void
watch_dog(int x) 
{
    clean_up();
    exit(0);
}


int
main (int argc,char *argv[]) 
{
    const char *short_opts = "haskV";
    const struct option long_opts[] = {
        { "scancodes",no_argument,NULL,''s'' },{ "keycodes",''k'' },{ NULL,0 }
    };

    int c;
    int show_keycodes = 1;
    struct termios new;
    unsigned char buf[16];
    int i,n;

    setlocale(LC_ALL,"");

    while ((c = getopt_long(argc,argv,short_opts,long_opts,NULL)) != -1) {
        switch (c) {
            case ''s'':
                show_keycodes = 0;
                break;
            case ''k'':
                show_keycodes = 1;
                break;

            case ''h'':
            case ''?'':
                usage();
        }
    }
    if (optind < argc)
        usage();

    fd = getfd(NULL);
    signal(SIgalRM,watch_dog);

    signal(SIGHUP,die);
    signal(SIGINT,die);
    signal(SIGQUIT,die);
    signal(SIGILL,die);
    signal(SIGTRAP,die);
    signal(SIGABRT,die);
    signal(SIGIOT,die);
    signal(SIGFPE,die);
    signal(SIGKILL,die);
    signal(SIGUSR1,die);
    signal(SIGSEGV,die);
    signal(SIGUSR2,die);
    signal(SIGPIPE,die);
    signal(SIGTERM,die);
#ifdef SIGSTKFLT
    signal(SIGSTKFLT,die);
#endif
    signal(SIGCHLD,die);
    signal(SIGCONT,die);
    signal(SIGSTOP,die);
    signal(SIGTSTP,die);
    signal(SIGTTIN,die);
    signal(SIGTTOU,die);

    get_mode();
    if (tcgetattr(fd,&old) == -1)
        perror("tcgetattr");
    if (tcgetattr(fd,&new) == -1)
        perror("tcgetattr");
    new.c_lflag &= ~ (ICANON | ECHO | ISIG);
    new.c_iflag = 0;
    new.c_cc[VMIN] = sizeof(buf);
    new.c_cc[VTIME] = 1;    /* 0.1 sec intercharacter timeout */
    if (tcsetattr(fd,TCSAFLUSH,&new) == -1)
        perror("tcsetattr");
    if (ioctl(fd,show_keycodes ? K_MEDIUMRAW : K_RAW)) {
        perror("KDSKBMODE");
        exit(1);
    }
    printf(_("press any key (program terminates 10s after last keypress)...\\n"));
    while (1) {
        alarm(10);
        n = read(fd,buf,sizeof(buf));
        for (i = 0; i < n; i++) {
            if (!show_keycodes)
                printf("0x%02x ",buf[i]);
            else
                printf(_("keycode %3d %s\\n"),buf[i] & 0x7f,buf[i] & 0x80 ? _("release")
                                      : _("press"));
        }
        if (!show_keycodes)
            printf("\\n");
    }
    clean_up();
    exit(0);
} 

另外,这需要root访问权限,有没有没有X11的更好的方法来做到这一点?我想在所有键上都获得按下和释放事件,包括修饰符。谢谢。

Atom飞行手册翻译: 4.2 深入键表(keymap)

Atom飞行手册翻译: 4.2 深入键表(keymap)

深入键表(keymap)

键表文件是以JSON或者CSON编码的文件,其中含有嵌套的哈希表。它们的工作方式像是样式表,但是它们指定匹配选择器的元素的快捷键的作用,而不是应用样式属性。下面是一些快捷键的例子,它们在atom-text-editor元素上按下时生效:

''atom-text-editor'':
  ''cmd-delete'': ''editor:delete-to-beginning-of-line''
  ''alt-backspace'': ''editor:delete-to-beginning-of-word''
  ''ctrl-A'': ''editor:select-to-first-character-of-line''
  ''ctrl-shift-e'': ''editor:select-to-end-of-line''
  ''cmd-left'': ''editor:move-to-first-character-of-line''

''atom-text-editor:not([mini])'':
  ''cmd-alt-['': ''editor:fold-current-row''
  ''cmd-alt-]'': ''editor:unfold-current-row''

在第一个选择器底下绑定了一些快捷键,将特定的键位通配符映射到命令上面。当一个atom-text-editor元素获得焦点,并且cmd-delete被按下,一个叫做editor:delete-to-beginning-of-line的自定义DOM事件会在atom-text-editor元素上面触发。

第二个选择器分组也指向了编辑器,但是只是没有mini属性的编辑器。在这个例子中,代码折叠的命令在迷你编辑器中毫无意义,所以选择器将它们限制于普通的编辑器中。

键位通配符(keystroke pattern)

键位通配符表示一个或者多个键位,带有可选的辅助键(modifier key)。例如ctrl-w vcmd-shift-up。键位由下面的符号组成,以-分隔。一个多种键位的通配符可以表示为以空格分割的键位通配符。

类型 例子
字符的字面值 a 4 $
辅助键 cmd ctrl alt shift
特殊键 enter escape backspace delete tab home end pageup pagedown left right up down

命令

命令是自定义的DOM事件,当一个键位匹配到绑定的快捷键时触发。这可以让UI代码来监听具名的命令,而不需要指定触发它的特定的快捷键。例如,下面的代码创建了一个命令来向编辑器插入当前日期:

atom.commands.add ''atom-text-editor'',
  ''user:insert-date'': (event) ->
    editor = @getModel()
    editor.insertText(new Date().toLocaleString())

atom.commands指向全局{CommandRegistry}的实例,所有命令在它里面设置,并且可以通过命令面板来获取。

当你想要绑定新的快捷键时,使用命令面板(ctrl-shift-p)来看一看在一个具有焦点的上下文中,什么命令正在被监听,是十分有用的。遵循一个简单的算法使得命令会很“人性化”,所以editor:fold-current-row命令会显示为“Editor: Fold Current Row”。

“组合”命令

一个很常见的问题是,“我如何使用一个快捷键来执行两个或者更多命令?”Atom并不直接支持这一需求,但是我们可以通过创建一个自定义命令,它执行你想要的多个操作,并且为这个命令创建一个快捷键来解决。例如,假设我想创建一个“组合”命令,选取并剪切一行。你可以在init.coffee中添加一下代码:

atom.commands.add ''atom-text-editor'', ''custom:cut-line'', ->
  editor = atom.workspace.getActiveTextEditor()
  editor.selectLinesContainingCursors()
  editor.cutSelectedText()

然后我们想要把这个命令关联到alt-ctrl-z上去,你应该添加以下内容到键表中:

''atom-text-editor'':
  ''alt-ctrl-z'': ''custom:cut-line''

特异性(优先级)和层级顺序

就像这个应用了CSS样式的例子,当很多快捷键的绑定匹配到一个元素的时候,冲突通过选择最特别的选择器来解决。如果两个匹配到的选择器具有相同的特异性,在层级中出现顺序靠后的选择器的快捷键会优先执行。

当前,没有任何方法在一个单独的键表中指定快捷键的顺序,因为JSON的对象是无序的。我们最终打算为键表引入一个自定义类似CSS的文件格式来允许在单个文件中排序。到目前为止,我们可以选择性解决一些情况,其中选择器的顺序由把键表分开放到两个文件中来严格规定。就像snippets-1.csonsnippets-2.cson

移除快捷键

当键表系统遇到了以unset!作为快捷键的命令,它就会像没有绑定匹配到当前键位序列一样,继续从它的父节点中寻找。如果你想移除一个你不再用到的快捷键,例如Atom核心中的或者包中的快捷键,应该直接使用unset!

例如,下面的代码移除了树视图上a的快捷键,它一般会触发tree-view:add-file命令:

''.tree-view'':
  ''a'': ''unset!''

强制Chrome处理本地快捷键

如果你想要在一个提供的快捷键上强制执行本地浏览器的行为,直接使用native!作为绑定的命令。这会在启动本地输入元素的正确行为时比较有用。例如,如果你在一个元素上面应用了.native-key-bindings class,所有由浏览器处理的快捷键都会绑定为native!

重载快捷键

一些情况下需要把多个动作依次放到同一个快捷键下面。一个例子就是代码段的包,代码段由输入一个类似for的前缀之后按下tab来插入。每次tab按下的时候,如果光标前面的文字存在对应的代码段,我们想要执行代码来展开代码段。如果代码段并不存在,我们希望tab插入空白字符。

要实现成这样,代码段的包利用了代表snippets:expand命令的事件对象的.abortKeyBinding()方法。

# pseudo-code
editor.command ''snippets:expand'', (e) =>
  if @cursorFollowsValidPrefix()
    @expandSnippet()
  else
    e.abortKeyBinding()

当事件处理器观察到光标前面并没有一个有效的前缀时,会调用`e.abortKeyBinding()来告诉键表系统继续寻找另一个匹配到的绑定。

详细步骤:按键事件如何映射到命令

  • 按键事件出现在获得焦点的元素上面。
  • 由获取焦点的元素开始,键表会向上搜索,直到文档的根元素,寻找最具特异性的CSS选择器,它匹配当前DOM元素并且含有匹配按键事件的快捷键通配符。
  • 找到匹配的快捷键通配符之后,搜索就结束了,并且与通配符绑定的命令会在当前元素上触发。
  • 如果在触发的事件对象上调用了.abortKeyBinding(),会恢复搜索,在相同元素上触发下一个最具特异性的CSS选择器上绑定的事件,或者继续向上搜索。
  • 如果找不到任何快捷键,事件通常就会由Chrome来处理。

Chrome/Chromium 的 Ozone X11 代码全面启用,旧版 X11 代码将删除

Chrome/Chromium 的 Ozone X11 代码全面启用,旧版 X11 代码将删除

Igalia 开发者 Maksim Sisov 于日前在社交平台上对外宣布称, Chrome/Chromium 网络浏览器现在已经完全启用了对 Ozone/X11 平台的支持,包括有 Beta 版和 Stable 版渠道。并表示,在现在这种大好的支持形势下,他们还将致力于废除非 Ozone/X11 的路径,同时在不久的将来删除传统的 X11 路径。

我们很高兴地宣布,Ozone/X11 已经在 STABLE 和 BETA 通道上 100% 启用。我们已经在努力废除非 Ozone/X11,并将开始删除旧的传统 X11 路径。

正如 Phoronix 所述,相当长的一段时间以来,开发人员都在通过 Chrome 的 Ozone 平台抽象代码,努力地从同一个构建中提供良好的 Wayland 和 X11 支持。此前,在 X11/X.Org 上使用 Ozone 还是一个实验性的选择;今年夏天,则终于成功地通过了一个极早期试验(origin trial)。

接下来,随着这个 Ozone/X11 使用的里程碑的完成和默认情况的推进,Igalia 和其他相关的开发者还将致力于运送 Ozone/Wayland 后端。在那之后,相同的Chrome/Chromium 浏览器构建在 X11 和 Wayland 上应该都可以运行良好。

实际上,长路漫漫,有关 Chrome Ozone 工作的讨论已经持续了有近十年之久。感兴趣的用户可以通过 googlesource.com 了解更多关于 Ozone platform layer 的细节。

Clockify API - 如何在不使用 Web UI 的情况下获取 API 密钥/令牌

Clockify API - 如何在不使用 Web UI 的情况下获取 API 密钥/令牌

如何解决Clockify API - 如何在不使用 Web UI 的情况下获取 API 密钥/令牌

如何使用用户名和密码获取 API 密钥/令牌。我想在不使用网络的情况下获取 API 令牌/密钥并想知道,是否有任何 API 来获取令牌/密钥

fbterm keymap 键盘问题

fbterm keymap 键盘问题

4. 常見問題

FAQ1). 第一次運行,出現下面的錯誤信息提示並且輸入法不能啟動(或者只有 root 用戶正常)[input] can''t change kernel keymap table, all shortcuts will NOT work, see SECURITY NOTES section of man page for solution.

解法 1) setuid (適用一般狀況)

chmod u+s /usr/bin/fbterm

解法 2) setcap (適用於 Kernel>= 2.6.27 )

sudo setcap ''cap_sys_tty_config+ep'' /usr/bin/fbterm

关于在没有 X11 的情况下获取 Linux 中 Keycode 的 Keymap 等效字符的问题我们已经讲解完毕,感谢您的阅读,如果还想了解更多关于Atom飞行手册翻译: 4.2 深入键表(keymap)、Chrome/Chromium 的 Ozone X11 代码全面启用,旧版 X11 代码将删除、Clockify API - 如何在不使用 Web UI 的情况下获取 API 密钥/令牌、fbterm keymap 键盘问题等相关内容,可以在本站寻找。

本文标签: