From b0a60131bf48ce7dbc9c0c9ff72ed8f96d5197cd Mon Sep 17 00:00:00 2001 From: Alynx Zhou Date: Wed, 30 Aug 2023 15:35:14 +0800 Subject: [PATCH] Updated to toggle click through with a switch. Closes . --- showmethekey-gtk/po/showmethekey.pot | 86 ++++++++++++---------- showmethekey-gtk/po/zh_CN.po | 105 ++++++++++++++++----------- showmethekey-gtk/smtk-app-win.c | 55 ++++++++++++-- showmethekey-gtk/smtk-app-win.h | 1 + showmethekey-gtk/smtk-app-win.ui | 19 +++++ showmethekey-gtk/smtk-app.c | 16 +++- showmethekey-gtk/smtk-keys-win.c | 83 +++++++++++++++------ showmethekey-gtk/smtk-keys-win.h | 1 + 8 files changed, 252 insertions(+), 114 deletions(-) diff --git a/showmethekey-gtk/po/showmethekey.pot b/showmethekey-gtk/po/showmethekey.pot index a87a9e4..fdf843e 100644 --- a/showmethekey-gtk/po/showmethekey.pot +++ b/showmethekey-gtk/po/showmethekey.pot @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: showmethekey\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2023-07-10 21:54+0800\n" +"POT-Creation-Date: 2023-08-30 15:29+0800\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -17,20 +17,20 @@ msgstr "" "Content-Type: text/plain; charset=CHARSET\n" "Content-Transfer-Encoding: 8bit\n" -#: showmethekey-gtk/smtk-app.c:77 showmethekey-gtk/smtk-app-win.c:526 +#: showmethekey-gtk/smtk-app.c:86 showmethekey-gtk/smtk-app-win.c:565 #: showmethekey-gtk/smtk-app-win.ui:9 showmethekey-gtk/smtk-app-win.ui:17 msgid "Show Me The Key" msgstr "" -#: showmethekey-gtk/smtk-app.c:82 +#: showmethekey-gtk/smtk-app.c:91 msgid "Display version then exit." msgstr "" -#: showmethekey-gtk/smtk-app-win.c:448 +#: showmethekey-gtk/smtk-app-win.c:484 msgid "Usage" msgstr "" -#: showmethekey-gtk/smtk-app-win.c:449 +#: showmethekey-gtk/smtk-app-win.c:485 msgid "" "1. Please input admin password after toggling the switch, because it needs " "superuser permission to read input events, and Wayland does not allow " @@ -40,16 +40,15 @@ msgid "" "\n" "2. After you toggle the switch to show the floating window, you need to drag " "it manually to anywhere you want, because Wayland does not allow window to " -"set its position. Though the floating window is mostly transparent for " -"click, the \"Clickable Area\" label on titlebar are clickable and can be " -"dragged as a handle.\n" +"set its position. The \"Clickable\" label on titlebar can be dragged as a " +"handle.\n" "\n" "3. Because Wayland does not allow a window to set \"Always on Top\" and " "\"Always on Visible Workspace\" by itself, you should set it manually if you " "are in a Wayland session and your window manager support it.\n" "For example if you are using GNOME Shell (Wayland), you can right click the " -"\"Clickable Area\" on title bar to show a window manager menu and check " -"\"Always on Top\" and \"Always on Visible Workspace\" in it.\n" +"\"Clickable\" on title bar to show a window manager menu and check \"Always " +"on Top\" and \"Always on Visible Workspace\" in it.\n" "If you are using KDE Plasma (Wayland), you can right click \"Floating Window " "- Show Me The Key\" on task bar, check \"Move to Desktop\" -> \"All " "Desktops\" and \"More Actions\" -> \"Keep Above Others\".\n" @@ -57,27 +56,31 @@ msgid "" "showmethekey#special-notice-for-wayland-session-users\">README to see if " "there are configurations for your compositor.\n" "\n" -"4. If you want to pause it (for example you need to insert password), you " +"4. To allow user move or resize the keys window, it is not click through by " +"default, after moving it to the location you want, turn off \"Clickable\" " +"switch so it won't block your other operations.\n" +"\n" +"5. If you want to pause it (for example you need to insert password), you " "can use the \"Pause\" switch, it will not record your keys when paused.\n" "\n" -"5. Set Timeout to 0 if you want to keep all keys.\n" +"6. Set Timeout to 0 if you want to keep all keys.\n" "\n" "You can open this dialog again via menu icon on title bar -> \"Usage\"." msgstr "" -#: showmethekey-gtk/smtk-app-win.c:487 +#: showmethekey-gtk/smtk-app-win.c:526 msgid "Close" msgstr "" -#: showmethekey-gtk/smtk-app-win.c:524 +#: showmethekey-gtk/smtk-app-win.c:563 msgid "translator-credits" msgstr "" -#: showmethekey-gtk/smtk-app-win.c:525 +#: showmethekey-gtk/smtk-app-win.c:564 msgid "About Show Me The Key" msgstr "" -#: showmethekey-gtk/smtk-app-win.c:527 +#: showmethekey-gtk/smtk-app-win.c:566 msgid "Show keys you typed on screen." msgstr "" @@ -94,80 +97,89 @@ msgid "General" msgstr "" #: showmethekey-gtk/smtk-app-win.ui:60 -msgid "_Pause" +msgid "_Clickable" msgstr "" #: showmethekey-gtk/smtk-app-win.ui:61 -msgid "Temporary hide input like password." +msgid "" +"Turning off will pass input event to other apps under the floating window." +msgstr "" + +#: showmethekey-gtk/smtk-app-win.ui:79 +msgid "_Pause" msgstr "" #: showmethekey-gtk/smtk-app-win.ui:80 +msgid "Temporary hide input like password." +msgstr "" + +#: showmethekey-gtk/smtk-app-win.ui:99 msgid "Show _Shift Separately" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:81 +#: showmethekey-gtk/smtk-app-win.ui:100 msgid "Show Ctrl+Shfit+A or Ctrl+A." msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:99 +#: showmethekey-gtk/smtk-app-win.ui:118 msgid "Show _Mouse Button" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:100 +#: showmethekey-gtk/smtk-app-win.ui:119 msgid "Mouse buttons can be very annoying." msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:117 +#: showmethekey-gtk/smtk-app-win.ui:136 msgid "Display Mode" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:118 +#: showmethekey-gtk/smtk-app-win.ui:137 msgid "Raw is Linux kernel's scancode and maybe not so useful." msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:124 +#: showmethekey-gtk/smtk-app-win.ui:143 msgid "Composed" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:125 +#: showmethekey-gtk/smtk-app-win.ui:144 msgid "Raw" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:139 +#: showmethekey-gtk/smtk-app-win.ui:158 msgid "Timeout (ms)" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:140 +#: showmethekey-gtk/smtk-app-win.ui:159 msgid "" "Clear keys if no new key after how many miliscconds. Set to 0 to keep all " "keys." msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:160 +#: showmethekey-gtk/smtk-app-win.ui:179 msgid "Width (px)" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:161 +#: showmethekey-gtk/smtk-app-win.ui:180 msgid "Width of keys window." msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:176 +#: showmethekey-gtk/smtk-app-win.ui:195 msgid "Height (px)" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:177 +#: showmethekey-gtk/smtk-app-win.ui:196 msgid "Height of keys window." msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:193 -msgid "Keyboard Rules" +#: showmethekey-gtk/smtk-app-win.ui:212 +msgid "Keyboard" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:197 +#: showmethekey-gtk/smtk-app-win.ui:216 msgid "Keymap" msgstr "" -#: showmethekey-gtk/smtk-app-win.ui:198 +#: showmethekey-gtk/smtk-app-win.ui:217 msgid "Choose your keyboard layout and variant." msgstr "" @@ -183,6 +195,6 @@ msgstr "" msgid "_Quit" msgstr "" -#: showmethekey-gtk/smtk-keys-win.c:285 -msgid "Clickable Area" +#: showmethekey-gtk/smtk-keys-win.c:303 +msgid "Clickable" msgstr "" diff --git a/showmethekey-gtk/po/zh_CN.po b/showmethekey-gtk/po/zh_CN.po index 4d83c5e..0b9c32d 100644 --- a/showmethekey-gtk/po/zh_CN.po +++ b/showmethekey-gtk/po/zh_CN.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: showmethekey\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2023-07-10 21:54+0800\n" +"POT-Creation-Date: 2023-08-30 15:29+0800\n" "PO-Revision-Date: 2021-04-21 15:16+0800\n" "Last-Translator: Automatically generated\n" "Language-Team: none\n" @@ -16,20 +16,20 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: showmethekey-gtk/smtk-app.c:77 showmethekey-gtk/smtk-app-win.c:526 +#: showmethekey-gtk/smtk-app.c:86 showmethekey-gtk/smtk-app-win.c:565 #: showmethekey-gtk/smtk-app-win.ui:9 showmethekey-gtk/smtk-app-win.ui:17 msgid "Show Me The Key" msgstr "让我看键" -#: showmethekey-gtk/smtk-app.c:82 +#: showmethekey-gtk/smtk-app.c:91 msgid "Display version then exit." msgstr "显示版本号然后退出。" -#: showmethekey-gtk/smtk-app-win.c:448 +#: showmethekey-gtk/smtk-app-win.c:484 msgid "Usage" msgstr "使用说明(_U)" -#: showmethekey-gtk/smtk-app-win.c:449 +#: showmethekey-gtk/smtk-app-win.c:485 msgid "" "1. Please input admin password after toggling the switch, because it needs " "superuser permission to read input events, and Wayland does not allow " @@ -39,16 +39,15 @@ msgid "" "\n" "2. After you toggle the switch to show the floating window, you need to drag " "it manually to anywhere you want, because Wayland does not allow window to " -"set its position. Though the floating window is mostly transparent for " -"click, the \"Clickable Area\" label on titlebar are clickable and can be " -"dragged as a handle.\n" +"set its position. The \"Clickable\" label on titlebar can be dragged as a " +"handle.\n" "\n" "3. Because Wayland does not allow a window to set \"Always on Top\" and " "\"Always on Visible Workspace\" by itself, you should set it manually if you " "are in a Wayland session and your window manager support it.\n" "For example if you are using GNOME Shell (Wayland), you can right click the " -"\"Clickable Area\" on title bar to show a window manager menu and check " -"\"Always on Top\" and \"Always on Visible Workspace\" in it.\n" +"\"Clickable\" on title bar to show a window manager menu and check \"Always " +"on Top\" and \"Always on Visible Workspace\" in it.\n" "If you are using KDE Plasma (Wayland), you can right click \"Floating Window " "- Show Me The Key\" on task bar, check \"Move to Desktop\" -> \"All " "Desktops\" and \"More Actions\" -> \"Keep Above Others\".\n" @@ -56,10 +55,14 @@ msgid "" "showmethekey#special-notice-for-wayland-session-users\">README to see if " "there are configurations for your compositor.\n" "\n" -"4. If you want to pause it (for example you need to insert password), you " +"4. To allow user move or resize the keys window, it is not click through by " +"default, after moving it to the location you want, turn off \"Clickable\" " +"switch so it won't block your other operations.\n" +"\n" +"5. If you want to pause it (for example you need to insert password), you " "can use the \"Pause\" switch, it will not record your keys when paused.\n" "\n" -"5. Set Timeout to 0 if you want to keep all keys.\n" +"6. Set Timeout to 0 if you want to keep all keys.\n" "\n" "You can open this dialog again via menu icon on title bar -> \"Usage\"." msgstr "" @@ -69,39 +72,42 @@ msgstr "" "过密码验证。\n" "\n" "2. 在打开开关显示悬浮窗口之后,您需要手动拖拽它到您想要的位置,因为 Wayland " -"不允许窗口自行设定位置。尽管悬浮窗口的大部分面积都无法点击,标题栏上的“可点击" -"区域”标签仍然是可以点击的并且可以作为把手来拖拽。\n" +"不允许窗口自行设定位置。标题栏上的“可点击”标签可以作为把手来拖拽。\n" "\n" "3. 因为 Wayland 不允许窗口自行设置“置顶”和“总在可见工作区”,所以如果您在使用 " "Wayland 会话,您需要手动设置这两种功能,如果您的窗口管理器支持的话。\n" "例如如果您在使用 GNOME Shell (Wayland),您可以右键点击标题栏上的“可点击区" "域”来显示窗口管理器菜单并勾选“置顶”和“总在可见工作区”。\n" -"如果您在使用 KDE Plasma (Wayland),您可以右键点击任务栏上的“悬浮窗口 - 让我看" -"键”,勾选“移动到桌面”->“全部桌面”和“更多动作”->“常居顶端”。\n" +"如果您在使用 KDE Plasma (Wayland),您可以右键点击任务栏上的“Floating Window " +"- Show Me The Key”,勾选“移动到桌面”->“全部桌面”和“更多动作”->“常居顶端”。\n" "您可以访问项目的 README 文件来查看是否有针对您的混成器" "的配置方法。\n" "\n" -"4. 如果您想要暂停该程序(比如你需要输入密码),您可以使用“暂停”开关,在暂停状" +"4. 为了允许用户移动窗口或者调整窗口大小,窗口默认是接收输入事件的,当把窗口移" +"动到您需要的位置后,可以关闭“接收输入事件(_C)”开关,这样它就不会影响您的其它" +"操作。\n" +"\n" +"5. 如果您想要暂停该程序(比如你需要输入密码),您可以使用“暂停”开关,在暂停状" "态下它不会记录您的按键。\n" "\n" -"5. 如果想保留所有的按键记录,请将超时设为 0。\n" +"6. 如果想保留所有的按键记录,请将超时设为 0。\n" "\n" "您可以通过标题栏上的菜单按钮 ->“使用说明”来再次访问此对话框。" -#: showmethekey-gtk/smtk-app-win.c:487 +#: showmethekey-gtk/smtk-app-win.c:526 msgid "Close" msgstr "关闭" -#: showmethekey-gtk/smtk-app-win.c:524 +#: showmethekey-gtk/smtk-app-win.c:563 msgid "translator-credits" msgstr "Alynx Zhou" -#: showmethekey-gtk/smtk-app-win.c:525 +#: showmethekey-gtk/smtk-app-win.c:564 msgid "About Show Me The Key" msgstr "关于让我看键" -#: showmethekey-gtk/smtk-app-win.c:527 +#: showmethekey-gtk/smtk-app-win.c:566 msgid "Show keys you typed on screen." msgstr "在屏幕上显示你按的键。" @@ -118,80 +124,91 @@ msgid "General" msgstr "常规" #: showmethekey-gtk/smtk-app-win.ui:60 +msgid "_Clickable" +msgstr "接收输入事件(_C)" + +#: showmethekey-gtk/smtk-app-win.ui:61 +msgid "" +"Turning off will pass input event to other apps under the floating window." +msgstr "" +"关闭该项后,输入事件将会被传递给悬浮窗口下面的其它应用。" + +#: showmethekey-gtk/smtk-app-win.ui:79 msgid "_Pause" msgstr "暂停(_P)" -#: showmethekey-gtk/smtk-app-win.ui:61 +#: showmethekey-gtk/smtk-app-win.ui:80 msgid "Temporary hide input like password." msgstr "临时隐藏输入,比如密码。" -#: showmethekey-gtk/smtk-app-win.ui:80 +#: showmethekey-gtk/smtk-app-win.ui:99 msgid "Show _Shift Separately" msgstr "单独显示 Shift(_S)" -#: showmethekey-gtk/smtk-app-win.ui:81 +#: showmethekey-gtk/smtk-app-win.ui:100 msgid "Show Ctrl+Shfit+A or Ctrl+A." msgstr "显示 Ctrl+Shift+A 还是 Ctrl+A。" -#: showmethekey-gtk/smtk-app-win.ui:99 +#: showmethekey-gtk/smtk-app-win.ui:118 msgid "Show _Mouse Button" msgstr "显示鼠标按钮(_M)" -#: showmethekey-gtk/smtk-app-win.ui:100 +#: showmethekey-gtk/smtk-app-win.ui:119 msgid "Mouse buttons can be very annoying." msgstr "鼠标按钮有时候会太占地方。" -#: showmethekey-gtk/smtk-app-win.ui:117 +#: showmethekey-gtk/smtk-app-win.ui:136 msgid "Display Mode" msgstr "显示模式" -#: showmethekey-gtk/smtk-app-win.ui:118 +#: showmethekey-gtk/smtk-app-win.ui:137 msgid "Raw is Linux kernel's scancode and maybe not so useful." msgstr "按键名是 Linux 内核的扫描码,可能不会特别有用。" -#: showmethekey-gtk/smtk-app-win.ui:124 +#: showmethekey-gtk/smtk-app-win.ui:143 msgid "Composed" msgstr "组合键" -#: showmethekey-gtk/smtk-app-win.ui:125 +#: showmethekey-gtk/smtk-app-win.ui:144 msgid "Raw" msgstr "按键名" -#: showmethekey-gtk/smtk-app-win.ui:139 +#: showmethekey-gtk/smtk-app-win.ui:158 msgid "Timeout (ms)" msgstr "超时(毫秒)" -#: showmethekey-gtk/smtk-app-win.ui:140 +#: showmethekey-gtk/smtk-app-win.ui:159 msgid "" "Clear keys if no new key after how many miliscconds. Set to 0 to keep all " "keys." -msgstr "多少毫秒没有新按键之后清除已有的按键。设置为 0 保留所有按键。" +msgstr "" +"多少毫秒没有新按键之后清除已有的按键。设置为 0 保留所有按键。" -#: showmethekey-gtk/smtk-app-win.ui:160 +#: showmethekey-gtk/smtk-app-win.ui:179 msgid "Width (px)" msgstr "宽度(像素)" -#: showmethekey-gtk/smtk-app-win.ui:161 +#: showmethekey-gtk/smtk-app-win.ui:180 msgid "Width of keys window." msgstr "按键窗口的宽度。" -#: showmethekey-gtk/smtk-app-win.ui:176 +#: showmethekey-gtk/smtk-app-win.ui:195 msgid "Height (px)" msgstr "高度(像素)" -#: showmethekey-gtk/smtk-app-win.ui:177 +#: showmethekey-gtk/smtk-app-win.ui:196 msgid "Height of keys window." msgstr "按键窗口的高度。" -#: showmethekey-gtk/smtk-app-win.ui:193 +#: showmethekey-gtk/smtk-app-win.ui:212 msgid "Keyboard" msgstr "键盘" -#: showmethekey-gtk/smtk-app-win.ui:197 +#: showmethekey-gtk/smtk-app-win.ui:216 msgid "Keymap" msgstr "键位" -#: showmethekey-gtk/smtk-app-win.ui:198 +#: showmethekey-gtk/smtk-app-win.ui:217 msgid "Choose your keyboard layout and variant." msgstr "选择您的键盘布局和变体。" @@ -207,6 +224,6 @@ msgstr "关于让我看键(_A)" msgid "_Quit" msgstr "退出(_Q)" -#: showmethekey-gtk/smtk-keys-win.c:285 -msgid "Clickable Area" -msgstr "可点击区域" +#: showmethekey-gtk/smtk-keys-win.c:303 +msgid "Clickable" +msgstr "可点击" diff --git a/showmethekey-gtk/smtk-app-win.c b/showmethekey-gtk/smtk-app-win.c index 65c18ed..20039de 100644 --- a/showmethekey-gtk/smtk-app-win.c +++ b/showmethekey-gtk/smtk-app-win.c @@ -16,6 +16,7 @@ struct _SmtkAppWin { GSettings *settings; GtkWidget *menu_button; GtkWidget *keys_win_switch; + GtkWidget *clickable_switch; GtkWidget *pause_switch; GtkWidget *shift_switch; GtkWidget *mouse_switch; @@ -30,6 +31,7 @@ G_DEFINE_TYPE(SmtkAppWin, smtk_app_win, ADW_TYPE_APPLICATION_WINDOW) static void smtk_app_win_enable(SmtkAppWin *win) { + gtk_widget_set_sensitive(win->clickable_switch, false); gtk_widget_set_sensitive(win->pause_switch, false); gtk_widget_set_sensitive(win->width_entry, true); gtk_widget_set_sensitive(win->height_entry, true); @@ -37,6 +39,7 @@ static void smtk_app_win_enable(SmtkAppWin *win) static void smtk_app_win_disable(SmtkAppWin *win) { + gtk_widget_set_sensitive(win->clickable_switch, true); gtk_widget_set_sensitive(win->pause_switch, true); gtk_widget_set_sensitive(win->width_entry, false); gtk_widget_set_sensitive(win->height_entry, false); @@ -47,9 +50,12 @@ static void smtk_app_win_keys_win_on_destroy(SmtkAppWin *win, SmtkKeysWin *keys_win) { if (win->keys_win != NULL) { + // Should set this first as we check it in callback. win->keys_win = NULL; gtk_switch_set_active(GTK_SWITCH(win->keys_win_switch), false); + // Clickable by default. + gtk_switch_set_active(GTK_SWITCH(win->clickable_switch), true); gtk_switch_set_active(GTK_SWITCH(win->pause_switch), false); smtk_app_win_enable(win); } @@ -122,6 +128,21 @@ static void smtk_app_win_on_keys_win_switch_active(SmtkAppWin *win, } } +static void smtk_app_win_on_clickable_switch_active(SmtkAppWin *win, + GParamSpec *prop, + GtkSwitch *clickable_switch) +{ + // This only works when keys_win is open. + // Calling `gtk_switch_set_active()` also triggers this, but then we + // don't have a `keys_win` at that time. + if (win->keys_win == NULL) + return; + + smtk_keys_win_set_clickable( + SMTK_KEYS_WIN(win->keys_win), + gtk_switch_get_active(GTK_SWITCH(win->clickable_switch))); +} + static void smtk_app_win_on_pause_switch_active(SmtkAppWin *win, GParamSpec *prop, GtkSwitch *pause_switch) @@ -367,6 +388,8 @@ static void smtk_app_win_class_init(SmtkAppWinClass *win_class) SmtkAppWin, keys_win_switch); gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(win_class), SmtkAppWin, menu_button); + gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(win_class), + SmtkAppWin, clickable_switch); gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(win_class), SmtkAppWin, pause_switch); gtk_widget_class_bind_template_child(GTK_WIDGET_CLASS(win_class), @@ -386,6 +409,9 @@ static void smtk_app_win_class_init(SmtkAppWinClass *win_class) gtk_widget_class_bind_template_callback( GTK_WIDGET_CLASS(win_class), smtk_app_win_on_keys_win_switch_active); + gtk_widget_class_bind_template_callback( + GTK_WIDGET_CLASS(win_class), + smtk_app_win_on_clickable_switch_active); gtk_widget_class_bind_template_callback( GTK_WIDGET_CLASS(win_class), smtk_app_win_on_pause_switch_active); @@ -410,6 +436,16 @@ GtkWidget *smtk_app_win_new(SmtkApp *app) return g_object_new(SMTK_TYPE_APP_WIN, "application", app, NULL); } +void smtk_app_win_toggle_clickable_switch(SmtkAppWin *win) +{ + g_return_if_fail(win != NULL); + + if (gtk_widget_get_sensitive(win->clickable_switch)) + gtk_switch_set_active(GTK_SWITCH(win->clickable_switch), + !gtk_switch_get_active(GTK_SWITCH( + win->clickable_switch))); +} + void smtk_app_win_toggle_pause_switch(SmtkAppWin *win) { g_return_if_fail(win != NULL); @@ -456,17 +492,16 @@ void smtk_app_win_show_usage_dialog(SmtkAppWin *win) "2. After you toggle the switch to show the floating window, " "you need to drag it manually to anywhere you want, " "because Wayland does not allow window to set its position. " - "Though the floating window is mostly transparent for click, " - "the \"Clickable Area\" label on titlebar are clickable and " - "can be dragged as a handle.\n\n" + "The \"Clickable\" label on titlebar can be dragged as a " + "handle.\n\n" "3. Because Wayland does not allow a window to set " "\"Always on Top\" and \"Always on Visible Workspace\" " "by itself, you should set it manually if you are in a " "Wayland session and your window manager support it.\n" "For example if you are using GNOME Shell (Wayland), you can " - "right click the \"Clickable Area\" on title bar to show a " - "window manager menu and check \"Always on Top\" and " - "\"Always on Visible Workspace\" in it.\n" + "right click the \"Clickable\" on title bar to show a window " + "manager menu and check \"Always on Top\" and \"Always on " + "Visible Workspace\" in it.\n" "If you are using KDE Plasma (Wayland), you can right click " "\"Floating Window - Show Me The Key\" on task bar, check " "\"Move to Desktop\" -> \"All Desktops\" and " @@ -475,10 +510,14 @@ void smtk_app_win_show_usage_dialog(SmtkAppWin *win) "href=\"https://github.com/AlynxZhou/showmethekey#special-" "notice-for-wayland-session-users\">README to see if " "there are configurations for your compositor.\n\n" - "4. If you want to pause it (for example you need to insert " + "4. To allow user move or resize the keys window, it is not " + "click through by default, after moving it to the location " + "you want, turn off \"Clickable\" switch so it won't block " + "your other operations.\n\n" + "5. If you want to pause it (for example you need to insert " "password), you can use the \"Pause\" switch, it will not " "record your keys when paused.\n\n" - "5. Set Timeout to 0 if you want to keep all keys.\n\n" + "6. Set Timeout to 0 if you want to keep all keys.\n\n" "You can open this dialog again via menu icon on title bar " "-> \"Usage\".")); adw_message_dialog_set_body_use_markup(ADW_MESSAGE_DIALOG(dialog), diff --git a/showmethekey-gtk/smtk-app-win.h b/showmethekey-gtk/smtk-app-win.h index 8009033..56d86fc 100644 --- a/showmethekey-gtk/smtk-app-win.h +++ b/showmethekey-gtk/smtk-app-win.h @@ -13,6 +13,7 @@ G_DECLARE_FINAL_TYPE(SmtkAppWin, smtk_app_win, SMTK, APP_WIN, AdwApplicationWindow) GtkWidget *smtk_app_win_new(SmtkApp *app); +void smtk_app_win_toggle_clickable_switch(SmtkAppWin *win); void smtk_app_win_toggle_pause_switch(SmtkAppWin *win); void smtk_app_win_toggle_shift_switch(SmtkAppWin *win); void smtk_app_win_toggle_mouse_switch(SmtkAppWin *win); diff --git a/showmethekey-gtk/smtk-app-win.ui b/showmethekey-gtk/smtk-app-win.ui index 67895e3..de5bf06 100644 --- a/showmethekey-gtk/smtk-app-win.ui +++ b/showmethekey-gtk/smtk-app-win.ui @@ -54,6 +54,25 @@ General + + + true + _Clickable + Turning off will pass input event to other apps under the floating window. + clickable_switch + + + center + true + + + + + true diff --git a/showmethekey-gtk/smtk-app.c b/showmethekey-gtk/smtk-app.c index 01e724f..81b2be6 100644 --- a/showmethekey-gtk/smtk-app.c +++ b/showmethekey-gtk/smtk-app.c @@ -12,6 +12,15 @@ struct _SmtkApp { }; G_DEFINE_TYPE(SmtkApp, smtk_app, ADW_TYPE_APPLICATION) +static void clickable_action(GSimpleAction *action, GVariant *parameter, + gpointer user_data) +{ + SmtkApp *app = SMTK_APP(user_data); + + if (app->win != NULL) + smtk_app_win_toggle_clickable_switch(SMTK_APP_WIN(app->win)); +} + static void pause_action(GSimpleAction *action, GVariant *parameter, gpointer user_data) { @@ -104,7 +113,9 @@ static void smtk_app_startup(GApplication *g_app) // Because application is not a construct property of GtkWindow, // we have to setup accels here. - GActionEntry actions[] = { { "pause", pause_action, NULL, NULL, NULL }, + GActionEntry actions[] = { { "clickable", clickable_action, NULL, NULL, + NULL }, + { "pause", pause_action, NULL, NULL, NULL }, { "shift", shift_action, NULL, NULL, NULL }, { "mouse", mouse_action, NULL, NULL, NULL }, { "usage", usage_action, NULL, NULL, NULL }, @@ -112,6 +123,7 @@ static void smtk_app_startup(GApplication *g_app) { "quit", quit_action, NULL, NULL, NULL } }; g_action_map_add_action_entries(G_ACTION_MAP(app), actions, G_N_ELEMENTS(actions), app); + const char *clickable_accels[] = { "C", NULL }; const char *pause_accels[] = { "P", NULL }; const char *shift_accels[] = { "S", NULL }; const char *mouse_accels[] = { "M", NULL }; @@ -121,6 +133,8 @@ static void smtk_app_startup(GApplication *g_app) // See Description of // // about "app." here. + gtk_application_set_accels_for_action( + GTK_APPLICATION(app), "app.clickable", clickable_accels); gtk_application_set_accels_for_action(GTK_APPLICATION(app), "app.pause", pause_accels); gtk_application_set_accels_for_action(GTK_APPLICATION(app), "app.shift", diff --git a/showmethekey-gtk/smtk-keys-win.c b/showmethekey-gtk/smtk-keys-win.c index e2cbd61..bc35e96 100644 --- a/showmethekey-gtk/smtk-keys-win.c +++ b/showmethekey-gtk/smtk-keys-win.c @@ -18,21 +18,23 @@ struct _SmtkKeysWin { GtkWidget *area; SmtkKeysEmitter *emitter; SmtkKeyMode mode; + bool clickable; + bool paused; bool show_shift; bool show_mouse; int timeout; char *layout; char *variant; - bool paused; GError *error; }; G_DEFINE_TYPE(SmtkKeysWin, smtk_keys_win, ADW_TYPE_WINDOW) enum { PROP_0, - PROP_MODE, + PROP_CLICKABLE, PROP_SHOW_SHIFT, PROP_SHOW_MOUSE, + PROP_MODE, PROP_TIMEOUT, PROP_LAYOUT, PROP_VARIANT, @@ -48,8 +50,8 @@ static void smtk_keys_win_set_property(GObject *object, SmtkKeysWin *win = SMTK_KEYS_WIN(object); switch (property_id) { - case PROP_MODE: - smtk_keys_win_set_mode(win, g_value_get_enum(value)); + case PROP_CLICKABLE: + smtk_keys_win_set_clickable(win, g_value_get_boolean(value)); break; case PROP_SHOW_SHIFT: smtk_keys_win_set_show_shift(win, g_value_get_boolean(value)); @@ -57,6 +59,9 @@ static void smtk_keys_win_set_property(GObject *object, case PROP_SHOW_MOUSE: smtk_keys_win_set_show_mouse(win, g_value_get_boolean(value)); break; + case PROP_MODE: + smtk_keys_win_set_mode(win, g_value_get_enum(value)); + break; case PROP_TIMEOUT: smtk_keys_win_set_timeout(win, g_value_get_int(value)); break; @@ -80,8 +85,8 @@ static void smtk_keys_win_get_property(GObject *object, SmtkKeysWin *win = SMTK_KEYS_WIN(object); switch (property_id) { - case PROP_MODE: - g_value_set_enum(value, win->mode); + case PROP_CLICKABLE: + g_value_set_boolean(value, win->clickable); break; case PROP_SHOW_SHIFT: g_value_set_boolean(value, win->show_shift); @@ -89,6 +94,9 @@ static void smtk_keys_win_get_property(GObject *object, case PROP_SHOW_MOUSE: g_value_set_boolean(value, win->show_mouse); break; + case PROP_MODE: + g_value_set_enum(value, win->mode); + break; case PROP_TIMEOUT: g_value_set_int(value, win->timeout); break; @@ -222,6 +230,8 @@ static void smtk_keys_win_on_map(SmtkKeysWin *win, gpointer user_data) #endif } +// NOTE: Not sure why but we can only alter input region in this function, +// calling `gdk_surface_set_input_region()` in setter is invalid. static void smtk_keys_win_size_allocate(GtkWidget *widget, int width, int height, int baseline) { @@ -234,20 +244,22 @@ static void smtk_keys_win_size_allocate(GtkWidget *widget, int width, g_debug("Allocated size: %dx%d.", width, height); - // Widget's allocation is only usable after realize. - GtkAllocation handle_allocation; - gtk_widget_get_allocation(win->handle, &handle_allocation); - g_debug("Clickable area: x: %d, y: %d, w: %d, h: %d.", - handle_allocation.x, handle_allocation.y, - handle_allocation.width, handle_allocation.height); - cairo_region_t *clickable_region = - cairo_region_create_rectangle(&handle_allocation); GtkNative *native = gtk_widget_get_native(widget); if (native != NULL) { GdkSurface *surface = gtk_native_get_surface(native); - gdk_surface_set_input_region(surface, clickable_region); + if (win->clickable) { + // See . + // The initial value for an input region is infinite. + // That means the whole surface will accept input. A + // NULL wl_region causes the input region to be set to + // infinite. + gdk_surface_set_input_region(surface, NULL); + } else { + cairo_region_t *empty_region = cairo_region_create(); + gdk_surface_set_input_region(surface, empty_region); + cairo_region_destroy(empty_region); + } } - cairo_region_destroy(clickable_region); } static void smtk_keys_win_init(SmtkKeysWin *win) @@ -258,6 +270,12 @@ static void smtk_keys_win_init(SmtkKeysWin *win) win->error = NULL; win->paused = false; + win->handle = NULL; + win->emitter = NULL; + win->area = NULL; + win->layout = NULL; + win->variant = NULL; + // AdwApplication will automatically load `style.css` under resource // base path, so we don't need to load it manually, just add a class so // we change style of the keys window only. @@ -282,7 +300,7 @@ static void smtk_keys_win_constructed(GObject *object) ADW_HEADER_BAR(win->header_bar), false); adw_header_bar_set_show_end_title_buttons( ADW_HEADER_BAR(win->header_bar), false); - win->handle = adw_window_title_new(_("Clickable Area"), NULL); + win->handle = adw_window_title_new(_("Clickable"), NULL); adw_header_bar_set_title_widget(ADW_HEADER_BAR(win->header_bar), win->handle); gtk_box_append(GTK_BOX(win->box), win->header_bar); @@ -350,6 +368,9 @@ static void smtk_keys_win_class_init(SmtkKeysWinClass *win_class) // really need it. widget_class->size_allocate = smtk_keys_win_size_allocate; + obj_props[PROP_CLICKABLE] = g_param_spec_boolean( + "clickable", "Clickable", "Clickable or Click Through", true, + G_PARAM_CONSTRUCT | G_PARAM_READWRITE); obj_props[PROP_MODE] = g_param_spec_enum( "mode", "Mode", "Key Mode", SMTK_TYPE_KEY_MODE, SMTK_KEY_MODE_COMPOSED, G_PARAM_CONSTRUCT | G_PARAM_READWRITE); @@ -384,15 +405,13 @@ GtkWidget *smtk_keys_win_new(bool show_shift, bool show_mouse, SmtkKeyMode mode, "Floating Window - Show Me The Key", "icon-name", "one.alynx.showmethekey", "can-focus", false, "focus-on-click", false, "vexpand", false, "vexpand-set", true, "hexpand", false, - "hexpand-set", true, - // We cannot focus on this window, and it has no border, - // so user resize is meaningless for it. - "resizable", false, + "hexpand-set", true, "focusable", false, "resizable", true, // Wayland does not support this, it's ok. // "skip-pager-hint", true, "skip-taskbar-hint", true, - "mode", mode, "show-shift", show_shift, "show-mouse", - show_mouse, "timeout", timeout, "layout", layout, "variant", - variant, NULL); + // Window should not be click through by default. + "clickable", true, "mode", mode, "show-shift", show_shift, + "show-mouse", show_mouse, "timeout", timeout, "layout", layout, + "variant", variant, NULL); if (win->error != NULL) { g_propagate_error(error, win->error); @@ -411,6 +430,22 @@ GtkWidget *smtk_keys_win_new(bool show_shift, bool show_mouse, SmtkKeyMode mode, return GTK_WIDGET(win); } +void smtk_keys_win_set_clickable(SmtkKeysWin *win, bool clickable) +{ + g_return_if_fail(win != NULL); + + // We don't need the handle if click through. But the handle might not + // be there during init. + if (win->handle != NULL) + gtk_widget_set_visible(win->handle, clickable); + + // NOTE: We don't handle input region here, I don't know why we can't. + // We just save property and handle the input region in + // `size_allocate()`. + // Sync self property. + win->clickable = clickable; +} + void smtk_keys_win_pause(SmtkKeysWin *win) { g_return_if_fail(win != NULL); diff --git a/showmethekey-gtk/smtk-keys-win.h b/showmethekey-gtk/smtk-keys-win.h index 549a081..0c4b878 100644 --- a/showmethekey-gtk/smtk-keys-win.h +++ b/showmethekey-gtk/smtk-keys-win.h @@ -16,6 +16,7 @@ GtkWidget *smtk_keys_win_new(bool show_shift, bool show_mouse, SmtkKeyMode mode, int width, int height, int timeout, const char *layout, const char *variant, GError **error); +void smtk_keys_win_set_clickable(SmtkKeysWin *win, bool clickable); void smtk_keys_win_pause(SmtkKeysWin *win); void smtk_keys_win_resume(SmtkKeysWin *win); void smtk_keys_win_set_mode(SmtkKeysWin *win, SmtkKeyMode mode);