|
Packit Service |
1d8f1c |
/* vim:set et sts=4 sw=4:
|
|
Packit Service |
1d8f1c |
*
|
|
Packit Service |
1d8f1c |
* ibus - The Input Bus
|
|
Packit Service |
1d8f1c |
*
|
|
Packit Service |
1d8f1c |
* Copyright(c) 2011-2016 Peng Huang <shawn.p.huang@gmail.com>
|
|
Packit Service |
1d8f1c |
* Copyright(c) 2015-2017 Takao Fujiwara <takao.fujiwara1@gmail.com>
|
|
Packit Service |
1d8f1c |
*
|
|
Packit Service |
1d8f1c |
* This library is free software; you can redistribute it and/or
|
|
Packit Service |
1d8f1c |
* modify it under the terms of the GNU Lesser General Public
|
|
Packit Service |
1d8f1c |
* License as published by the Free Software Foundation; either
|
|
Packit Service |
1d8f1c |
* version 2.1 of the License, or (at your option) any later version.
|
|
Packit Service |
1d8f1c |
*
|
|
Packit Service |
1d8f1c |
* This library is distributed in the hope that it will be useful,
|
|
Packit Service |
1d8f1c |
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
Packit Service |
1d8f1c |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
Packit Service |
1d8f1c |
* Lesser General Public License for more details.
|
|
Packit Service |
1d8f1c |
*
|
|
Packit Service |
1d8f1c |
* You should have received a copy of the GNU Lesser General Public
|
|
Packit Service |
1d8f1c |
* License along with this library; if not, write to the Free Software
|
|
Packit Service |
1d8f1c |
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
|
|
Packit Service |
1d8f1c |
* USA
|
|
Packit Service |
1d8f1c |
*/
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
class Switcher : Gtk.Window {
|
|
Packit Service |
1d8f1c |
private class IBusEngineButton : Gtk.Button {
|
|
Packit Service |
1d8f1c |
public IBusEngineButton(IBus.EngineDesc engine, Switcher switcher) {
|
|
Packit Service |
1d8f1c |
GLib.Object();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
var longname = engine.get_longname();
|
|
Packit Service |
1d8f1c |
var textdomain = engine.get_textdomain();
|
|
Packit Service |
1d8f1c |
this.transname = GLib.dgettext(textdomain, longname);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
var name = engine.get_name();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (name.length < 4 || name[0:4] != "xkb:") {
|
|
Packit Service |
1d8f1c |
IconWidget icon = new IconWidget(engine.get_icon(),
|
|
Packit Service |
1d8f1c |
Gtk.IconSize.DIALOG);
|
|
Packit Service |
1d8f1c |
icon.set_halign(Gtk.Align.CENTER);
|
|
Packit Service |
1d8f1c |
icon.set_valign(Gtk.Align.CENTER);
|
|
Packit Service |
1d8f1c |
add(icon);
|
|
Packit Service |
1d8f1c |
} else {
|
|
Packit Service |
1d8f1c |
var language = switcher.get_xkb_language(engine);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
Gtk.Label label = new Gtk.Label(language);
|
|
Packit Service |
1d8f1c |
label.set_halign(Gtk.Align.CENTER);
|
|
Packit Service |
1d8f1c |
label.set_valign(Gtk.Align.CENTER);
|
|
Packit Service |
1d8f1c |
string language_font = "Monospace Bold 16";
|
|
Packit Service |
1d8f1c |
string markup = "%s".
|
|
Packit Service |
1d8f1c |
printf(language_font, language);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
label.set_markup(markup);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
int fixed_width, fixed_height;
|
|
Packit Service |
1d8f1c |
Gtk.icon_size_lookup(Gtk.IconSize.DIALOG,
|
|
Packit Service |
1d8f1c |
out fixed_width,
|
|
Packit Service |
1d8f1c |
out fixed_height);
|
|
Packit Service |
1d8f1c |
label.set_size_request(fixed_width, fixed_height);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
add(label);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public string transname { get; set; }
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public override bool draw(Cairo.Context cr) {
|
|
Packit Service |
1d8f1c |
base.draw(cr);
|
|
Packit Service |
1d8f1c |
if (is_focus) {
|
|
Packit Service |
1d8f1c |
cr.save();
|
|
Packit Service |
1d8f1c |
cr.rectangle(
|
|
Packit Service |
1d8f1c |
0, 0, get_allocated_width(), get_allocated_height());
|
|
Packit Service |
1d8f1c |
cr.set_source_rgba(0.0, 0.0, 1.0, 0.1);
|
|
Packit Service |
1d8f1c |
cr.fill();
|
|
Packit Service |
1d8f1c |
cr.restore();
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
return true;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
private Gtk.Box m_box;
|
|
Packit Service |
1d8f1c |
private Gtk.Label m_label;
|
|
Packit Service |
1d8f1c |
private IBusEngineButton[] m_buttons = {};
|
|
Packit Service |
1d8f1c |
private IBus.EngineDesc[] m_engines;
|
|
Packit Service |
1d8f1c |
private uint m_selected_engine;
|
|
Packit Service |
1d8f1c |
private uint m_keyval;
|
|
Packit Service |
1d8f1c |
private uint m_modifiers;
|
|
Packit Service |
1d8f1c |
private Gdk.ModifierType m_primary_modifier;
|
|
Packit Service |
1d8f1c |
private bool m_is_running = false;
|
|
Packit Service |
1d8f1c |
private string m_input_context_path = "";
|
|
Packit Service |
1d8f1c |
private GLib.MainLoop m_loop;
|
|
Packit Service |
1d8f1c |
private int m_result = -1;
|
|
Packit Service |
1d8f1c |
private IBus.EngineDesc? m_result_engine = null;
|
|
Packit Service |
1d8f1c |
private uint m_popup_delay_time = 0;
|
|
Packit Service |
1d8f1c |
private uint m_popup_delay_time_id = 0;
|
|
Packit Service |
1d8f1c |
private int m_root_x;
|
|
Packit Service |
1d8f1c |
private int m_root_y;
|
|
Packit Service |
1d8f1c |
private double m_mouse_init_x;
|
|
Packit Service |
1d8f1c |
private double m_mouse_init_y;
|
|
Packit Service |
1d8f1c |
private bool m_mouse_moved;
|
|
Packit Service |
1d8f1c |
private GLib.HashTable<string, string> m_xkb_languages =
|
|
Packit Service |
1d8f1c |
new GLib.HashTable<string, string>(GLib.str_hash,
|
|
Packit Service |
1d8f1c |
GLib.str_equal);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public Switcher() {
|
|
Packit Service |
1d8f1c |
GLib.Object(
|
|
Packit Service |
1d8f1c |
type : Gtk.WindowType.POPUP,
|
|
Packit Service |
1d8f1c |
events : Gdk.EventMask.KEY_PRESS_MASK | Gdk.EventMask.KEY_RELEASE_MASK,
|
|
Packit Service |
1d8f1c |
window_position : Gtk.WindowPosition.CENTER,
|
|
Packit Service |
1d8f1c |
accept_focus : true,
|
|
Packit Service |
1d8f1c |
decorated : false,
|
|
Packit Service |
1d8f1c |
modal : true,
|
|
Packit Service |
1d8f1c |
focus_visible : true
|
|
Packit Service |
1d8f1c |
);
|
|
Packit Service |
1d8f1c |
Gtk.Box vbox = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
|
|
Packit Service |
1d8f1c |
add(vbox);
|
|
Packit Service |
1d8f1c |
m_box = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 0);
|
|
Packit Service |
1d8f1c |
m_box.set_halign(Gtk.Align.CENTER);
|
|
Packit Service |
1d8f1c |
m_box.set_valign(Gtk.Align.CENTER);
|
|
Packit Service |
1d8f1c |
vbox.pack_start(m_box, true, true, 0);
|
|
Packit Service |
1d8f1c |
m_label = new Gtk.Label("");
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* Set the accessible role of the label to a status bar so it
|
|
Packit Service |
1d8f1c |
* will emit name changed events that can be used by screen
|
|
Packit Service |
1d8f1c |
* readers.
|
|
Packit Service |
1d8f1c |
*/
|
|
Packit Service |
1d8f1c |
Atk.Object obj = m_label.get_accessible();
|
|
Packit Service |
1d8f1c |
obj.set_role (Atk.Role.STATUSBAR);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* Use Gtk.Widget.set_margin_start() and
|
|
Packit Service |
1d8f1c |
* Gtk.Widget.set_margin_top() since gtk 3.12 */
|
|
Packit Service |
1d8f1c |
m_label.set_padding(3, 3);
|
|
Packit Service |
1d8f1c |
vbox.pack_end(m_label, false, false, 0);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
grab_focus();
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public int run(uint keyval,
|
|
Packit Service |
1d8f1c |
uint state,
|
|
Packit Service |
1d8f1c |
Gdk.Event event,
|
|
Packit Service |
1d8f1c |
IBus.EngineDesc[] engines,
|
|
Packit Service |
1d8f1c |
int index,
|
|
Packit Service |
1d8f1c |
string input_context_path) {
|
|
Packit Service |
1d8f1c |
assert (m_loop == null);
|
|
Packit Service |
1d8f1c |
assert (index < engines.length);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_is_running = true;
|
|
Packit Service |
1d8f1c |
m_keyval = keyval;
|
|
Packit Service |
1d8f1c |
m_modifiers = state;
|
|
Packit Service |
1d8f1c |
m_primary_modifier =
|
|
Packit Service |
1d8f1c |
KeybindingManager.get_primary_modifier(
|
|
Packit Service |
1d8f1c |
state & KeybindingManager.MODIFIER_FILTER);
|
|
Packit Service |
1d8f1c |
m_selected_engine = m_result = index;
|
|
Packit Service |
1d8f1c |
m_input_context_path = input_context_path;
|
|
Packit Service |
1d8f1c |
m_result_engine = null;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
update_engines(engines);
|
|
Packit Service |
1d8f1c |
/* Let gtk recalculate the window size. */
|
|
Packit Service |
1d8f1c |
resize(1, 1);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_label.set_text(m_buttons[index].transname);
|
|
Packit Service |
1d8f1c |
m_buttons[index].grab_focus();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
// Avoid regressions.
|
|
Packit Service |
1d8f1c |
if (m_popup_delay_time > 0) {
|
|
Packit Service |
1d8f1c |
get_position(out m_root_x, out m_root_y);
|
|
Packit Service |
1d8f1c |
// Pull the window from the screen so that the window gets
|
|
Packit Service |
1d8f1c |
// the key press and release events but mouse does not select
|
|
Packit Service |
1d8f1c |
// an IME unexpectedly.
|
|
Packit Service |
1d8f1c |
move(-1000, -1000);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
show_all();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (m_popup_delay_time > 0) {
|
|
Packit Service |
1d8f1c |
// Restore the window position after m_popup_delay_time
|
|
Packit Service |
1d8f1c |
m_popup_delay_time_id = GLib.Timeout.add(m_popup_delay_time,
|
|
Packit Service |
1d8f1c |
() => {
|
|
Packit Service |
1d8f1c |
restore_window_position("timeout");
|
|
Packit Service |
1d8f1c |
return false;
|
|
Packit Service |
1d8f1c |
});
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
Gdk.Device pointer;
|
|
Packit Service |
1d8f1c |
#if VALA_0_34
|
|
Packit Service |
1d8f1c |
Gdk.Seat seat = event.get_seat();
|
|
Packit Service |
1d8f1c |
if (seat == null) {
|
|
Packit Service |
1d8f1c |
var display = get_display();
|
|
Packit Service |
1d8f1c |
seat = display.get_default_seat();
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
//keyboard = seat.get_keyboard();
|
|
Packit Service |
1d8f1c |
pointer = seat.get_pointer();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
Gdk.GrabStatus status;
|
|
Packit Service |
1d8f1c |
// Grab all keyboard events
|
|
Packit Service |
1d8f1c |
status = seat.grab(get_window(),
|
|
Packit Service |
1d8f1c |
Gdk.SeatCapabilities.KEYBOARD,
|
|
Packit Service |
1d8f1c |
true,
|
|
Packit Service |
1d8f1c |
null,
|
|
Packit Service |
1d8f1c |
event,
|
|
Packit Service |
1d8f1c |
null);
|
|
Packit Service |
1d8f1c |
if (status != Gdk.GrabStatus.SUCCESS)
|
|
Packit Service |
1d8f1c |
warning("Grab keyboard failed! status = %d", status);
|
|
Packit Service |
1d8f1c |
status = seat.grab(get_window(),
|
|
Packit Service |
1d8f1c |
Gdk.SeatCapabilities.POINTER,
|
|
Packit Service |
1d8f1c |
true,
|
|
Packit Service |
1d8f1c |
null,
|
|
Packit Service |
1d8f1c |
event,
|
|
Packit Service |
1d8f1c |
null);
|
|
Packit Service |
1d8f1c |
if (status != Gdk.GrabStatus.SUCCESS)
|
|
Packit Service |
1d8f1c |
warning("Grab pointer failed! status = %d", status);
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
Gdk.Device device = event.get_device();
|
|
Packit Service |
1d8f1c |
if (device == null) {
|
|
Packit Service |
1d8f1c |
var display = get_display();
|
|
Packit Service |
1d8f1c |
var device_manager = display.get_device_manager();
|
|
Packit Service |
1d8f1c |
/* The macro VALA_X_Y supports even numbers.
|
|
Packit Service |
1d8f1c |
* http://git.gnome.org/browse/vala/commit/?id=294b374af6
|
|
Packit Service |
1d8f1c |
*/
|
|
Packit Service |
1d8f1c |
#if VALA_0_16
|
|
Packit Service |
1d8f1c |
device = device_manager.list_devices(Gdk.DeviceType.MASTER).data;
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
unowned GLib.List<Gdk.Device> devices =
|
|
Packit Service |
1d8f1c |
device_manager.list_devices(Gdk.DeviceType.MASTER);
|
|
Packit Service |
1d8f1c |
device = devices.data;
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
Gdk.Device keyboard;
|
|
Packit Service |
1d8f1c |
if (device.get_source() == Gdk.InputSource.KEYBOARD) {
|
|
Packit Service |
1d8f1c |
keyboard = device;
|
|
Packit Service |
1d8f1c |
pointer = device.get_associated_device();
|
|
Packit Service |
1d8f1c |
} else {
|
|
Packit Service |
1d8f1c |
pointer = device;
|
|
Packit Service |
1d8f1c |
keyboard = device.get_associated_device();
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
Gdk.GrabStatus status;
|
|
Packit Service |
1d8f1c |
// Grab all keyboard events
|
|
Packit Service |
1d8f1c |
status = keyboard.grab(get_window(),
|
|
Packit Service |
1d8f1c |
Gdk.GrabOwnership.NONE,
|
|
Packit Service |
1d8f1c |
true,
|
|
Packit Service |
1d8f1c |
Gdk.EventMask.KEY_PRESS_MASK |
|
|
Packit Service |
1d8f1c |
Gdk.EventMask.KEY_RELEASE_MASK,
|
|
Packit Service |
1d8f1c |
null,
|
|
Packit Service |
1d8f1c |
Gdk.CURRENT_TIME);
|
|
Packit Service |
1d8f1c |
if (status != Gdk.GrabStatus.SUCCESS)
|
|
Packit Service |
1d8f1c |
warning("Grab keyboard failed! status = %d", status);
|
|
Packit Service |
1d8f1c |
// Grab all pointer events
|
|
Packit Service |
1d8f1c |
status = pointer.grab(get_window(),
|
|
Packit Service |
1d8f1c |
Gdk.GrabOwnership.NONE,
|
|
Packit Service |
1d8f1c |
true,
|
|
Packit Service |
1d8f1c |
Gdk.EventMask.BUTTON_PRESS_MASK |
|
|
Packit Service |
1d8f1c |
Gdk.EventMask.BUTTON_RELEASE_MASK,
|
|
Packit Service |
1d8f1c |
null,
|
|
Packit Service |
1d8f1c |
Gdk.CURRENT_TIME);
|
|
Packit Service |
1d8f1c |
if (status != Gdk.GrabStatus.SUCCESS)
|
|
Packit Service |
1d8f1c |
warning("Grab pointer failed! status = %d", status);
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
// Probably we can delete m_popup_delay_time in 1.6
|
|
Packit Service |
1d8f1c |
pointer.get_position_double(null,
|
|
Packit Service |
1d8f1c |
out m_mouse_init_x,
|
|
Packit Service |
1d8f1c |
out m_mouse_init_y);
|
|
Packit Service |
1d8f1c |
m_mouse_moved = false;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_loop = new GLib.MainLoop();
|
|
Packit Service |
1d8f1c |
m_loop.run();
|
|
Packit Service |
1d8f1c |
m_loop = null;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
#if VALA_0_34
|
|
Packit Service |
1d8f1c |
seat.ungrab();
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
keyboard.ungrab(Gdk.CURRENT_TIME);
|
|
Packit Service |
1d8f1c |
pointer.ungrab(Gdk.CURRENT_TIME);
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
hide();
|
|
Packit Service |
1d8f1c |
// Make sure the switcher is hidden before returning from this function.
|
|
Packit Service |
1d8f1c |
while (Gtk.events_pending())
|
|
Packit Service |
1d8f1c |
Gtk.main_iteration ();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
GLib.assert(m_result < m_engines.length);
|
|
Packit Service |
1d8f1c |
m_result_engine = m_engines[m_result];
|
|
Packit Service |
1d8f1c |
m_is_running = false;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
return m_result;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* Based on metacity/src/ui/tabpopup.c:meta_ui_tab_popup_new */
|
|
Packit Service |
1d8f1c |
private void update_engines(IBus.EngineDesc[] engines) {
|
|
Packit Service |
1d8f1c |
foreach (var button in m_buttons) {
|
|
Packit Service |
1d8f1c |
button.destroy();
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
m_buttons = {};
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (engines == null) {
|
|
Packit Service |
1d8f1c |
m_engines = {};
|
|
Packit Service |
1d8f1c |
return;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_engines = engines;
|
|
Packit Service |
1d8f1c |
int max_label_width = 0;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
for (int i = 0; i < m_engines.length; i++) {
|
|
Packit Service |
1d8f1c |
var index = i;
|
|
Packit Service |
1d8f1c |
var engine = m_engines[i];
|
|
Packit Service |
1d8f1c |
var button = new IBusEngineButton(engine, this);
|
|
Packit Service |
1d8f1c |
var longname = engine.get_longname();
|
|
Packit Service |
1d8f1c |
var textdomain = engine.get_textdomain();
|
|
Packit Service |
1d8f1c |
var transname = GLib.dgettext(textdomain, longname);
|
|
Packit Service |
1d8f1c |
button.set_relief(Gtk.ReliefStyle.NONE);
|
|
Packit Service |
1d8f1c |
button.add_events(Gdk.EventMask.POINTER_MOTION_MASK);
|
|
Packit Service |
1d8f1c |
button.show();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
button.enter_notify_event.connect((e) => {
|
|
Packit Service |
1d8f1c |
// avoid gtk_button_update_state()
|
|
Packit Service |
1d8f1c |
return true;
|
|
Packit Service |
1d8f1c |
});
|
|
Packit Service |
1d8f1c |
button.motion_notify_event.connect((e) => {
|
|
Packit Service |
1d8f1c |
#if VALA_0_24
|
|
Packit Service |
1d8f1c |
Gdk.EventMotion pe = e;
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
Gdk.EventMotion *pe = &e;
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
if (m_selected_engine == index)
|
|
Packit Service |
1d8f1c |
return false;
|
|
Packit Service |
1d8f1c |
if (!m_mouse_moved &&
|
|
Packit Service |
1d8f1c |
m_mouse_init_x == pe.x_root &&
|
|
Packit Service |
1d8f1c |
m_mouse_init_y == pe.y_root) {
|
|
Packit Service |
1d8f1c |
return false;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
m_mouse_moved = true;
|
|
Packit Service |
1d8f1c |
button.grab_focus();
|
|
Packit Service |
1d8f1c |
m_selected_engine = index;
|
|
Packit Service |
1d8f1c |
return false;
|
|
Packit Service |
1d8f1c |
});
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
button.button_press_event.connect((e) => {
|
|
Packit Service |
1d8f1c |
m_selected_engine = index;
|
|
Packit Service |
1d8f1c |
m_result = (int)m_selected_engine;
|
|
Packit Service |
1d8f1c |
m_loop.quit();
|
|
Packit Service |
1d8f1c |
return true;
|
|
Packit Service |
1d8f1c |
});
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
button.transname = transname;
|
|
Packit Service |
1d8f1c |
m_label.set_label(transname);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
int width;
|
|
Packit Service |
1d8f1c |
m_label.get_preferred_width(null, out width);
|
|
Packit Service |
1d8f1c |
max_label_width = int.max(max_label_width, width);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_box.pack_start(button, true, true);
|
|
Packit Service |
1d8f1c |
m_buttons += button;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_label.set_text(m_buttons[0].transname);
|
|
Packit Service |
1d8f1c |
m_label.set_ellipsize(Pango.EllipsizeMode.END);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
Gdk.Display display = Gdk.Display.get_default();
|
|
Packit Service |
1d8f1c |
int screen_width = 0;
|
|
Packit Service |
1d8f1c |
#if VALA_0_34
|
|
Packit Service |
1d8f1c |
// display.get_monitor_at_window() is null because of unrealized window
|
|
Packit Service |
1d8f1c |
Gdk.Monitor monitor = display.get_primary_monitor();
|
|
Packit Service |
1d8f1c |
Gdk.Rectangle area = monitor.get_geometry();
|
|
Packit Service |
1d8f1c |
screen_width = area.width;
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
Gdk.Screen screen = (display != null) ?
|
|
Packit Service |
1d8f1c |
display.get_default_screen() : null;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (screen != null) {
|
|
Packit Service |
1d8f1c |
screen_width = screen.get_width();
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (screen_width > 0 && max_label_width > (screen_width / 4)) {
|
|
Packit Service |
1d8f1c |
max_label_width = screen_width / 4;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* add random padding */
|
|
Packit Service |
1d8f1c |
max_label_width += 20;
|
|
Packit Service |
1d8f1c |
set_default_size(max_label_width, -1);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
private void next_engine() {
|
|
Packit Service |
1d8f1c |
if (m_selected_engine == m_engines.length - 1)
|
|
Packit Service |
1d8f1c |
m_selected_engine = 0;
|
|
Packit Service |
1d8f1c |
else
|
|
Packit Service |
1d8f1c |
m_selected_engine ++;
|
|
Packit Service |
1d8f1c |
m_label.set_text(m_buttons[m_selected_engine].transname);
|
|
Packit Service |
1d8f1c |
set_focus(m_buttons[m_selected_engine]);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
private void previous_engine() {
|
|
Packit Service |
1d8f1c |
if (m_selected_engine == 0)
|
|
Packit Service |
1d8f1c |
m_selected_engine = m_engines.length - 1;
|
|
Packit Service |
1d8f1c |
else
|
|
Packit Service |
1d8f1c |
m_selected_engine --;
|
|
Packit Service |
1d8f1c |
m_label.set_text(m_buttons[m_selected_engine].transname);
|
|
Packit Service |
1d8f1c |
set_focus(m_buttons[m_selected_engine]);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
private void restore_window_position(string debug_str) {
|
|
Packit Service |
1d8f1c |
debug("restore_window_position %s: (%ld, %ld)\n",
|
|
Packit Service |
1d8f1c |
debug_str, m_root_x, m_root_y);
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (m_popup_delay_time_id == 0) {
|
|
Packit Service |
1d8f1c |
return;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
GLib.Source.remove(m_popup_delay_time_id);
|
|
Packit Service |
1d8f1c |
m_popup_delay_time_id = 0;
|
|
Packit Service |
1d8f1c |
move(m_root_x, m_root_y);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* override virtual functions */
|
|
Packit Service |
1d8f1c |
public override void show() {
|
|
Packit Service |
1d8f1c |
base.show();
|
|
Packit Service |
1d8f1c |
set_focus_visible(true);
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public override bool key_press_event(Gdk.EventKey e) {
|
|
Packit Service |
1d8f1c |
bool retval = true;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* Gdk.EventKey is changed to the pointer.
|
|
Packit Service |
1d8f1c |
* https://git.gnome.org/browse/vala/commit/?id=598942f1
|
|
Packit Service |
1d8f1c |
*/
|
|
Packit Service |
1d8f1c |
#if VALA_0_24
|
|
Packit Service |
1d8f1c |
Gdk.EventKey pe = e;
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
Gdk.EventKey *pe = &e;
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (m_popup_delay_time > 0) {
|
|
Packit Service |
1d8f1c |
restore_window_position("pressed");
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
do {
|
|
Packit Service |
1d8f1c |
uint modifiers = KeybindingManager.MODIFIER_FILTER & pe.state;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if ((modifiers != m_modifiers) &&
|
|
Packit Service |
1d8f1c |
(modifiers != (m_modifiers | Gdk.ModifierType.SHIFT_MASK))) {
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (pe.keyval == m_keyval) {
|
|
Packit Service |
1d8f1c |
if (modifiers == m_modifiers)
|
|
Packit Service |
1d8f1c |
next_engine();
|
|
Packit Service |
1d8f1c |
else // modififers == m_modifiers | SHIFT_MASK
|
|
Packit Service |
1d8f1c |
previous_engine();
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
switch (pe.keyval) {
|
|
Packit Service |
1d8f1c |
case 0x08fb: /* leftarrow */
|
|
Packit Service |
1d8f1c |
case 0xff51: /* Left */
|
|
Packit Service |
1d8f1c |
previous_engine();
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
case 0x08fc: /* uparrow */
|
|
Packit Service |
1d8f1c |
case 0xff52: /* Up */
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
case 0x08fd: /* rightarrow */
|
|
Packit Service |
1d8f1c |
case 0xff53: /* Right */
|
|
Packit Service |
1d8f1c |
next_engine();
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
case 0x08fe: /* downarrow */
|
|
Packit Service |
1d8f1c |
case 0xff54: /* Down */
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
default:
|
|
Packit Service |
1d8f1c |
debug("0x%04x", pe.keyval);
|
|
Packit Service |
1d8f1c |
break;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
} while (false);
|
|
Packit Service |
1d8f1c |
return retval;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public override bool key_release_event(Gdk.EventKey e) {
|
|
Packit Service |
1d8f1c |
#if VALA_0_24
|
|
Packit Service |
1d8f1c |
Gdk.EventKey pe = e;
|
|
Packit Service |
1d8f1c |
#else
|
|
Packit Service |
1d8f1c |
Gdk.EventKey *pe = &e;
|
|
Packit Service |
1d8f1c |
#endif
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (KeybindingManager.primary_modifier_still_pressed((Gdk.Event) pe,
|
|
Packit Service |
1d8f1c |
m_primary_modifier)) {
|
|
Packit Service |
1d8f1c |
return true;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
// if e.type == Gdk.EventType.KEY_RELEASE, m_loop is already null.
|
|
Packit Service |
1d8f1c |
if (m_loop == null) {
|
|
Packit Service |
1d8f1c |
return false;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (m_popup_delay_time > 0) {
|
|
Packit Service |
1d8f1c |
if (m_popup_delay_time_id != 0) {
|
|
Packit Service |
1d8f1c |
GLib.Source.remove(m_popup_delay_time_id);
|
|
Packit Service |
1d8f1c |
m_popup_delay_time_id = 0;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_loop.quit();
|
|
Packit Service |
1d8f1c |
m_result = (int)m_selected_engine;
|
|
Packit Service |
1d8f1c |
return true;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public void set_popup_delay_time(uint popup_delay_time) {
|
|
Packit Service |
1d8f1c |
m_popup_delay_time = popup_delay_time;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public string get_xkb_language(IBus.EngineDesc engine) {
|
|
Packit Service |
1d8f1c |
var name = engine.get_name();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
assert(name[0:4] == "xkb:");
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
var language = m_xkb_languages[name];
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (language != null)
|
|
Packit Service |
1d8f1c |
return language;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
language = engine.get_language();
|
|
Packit Service |
1d8f1c |
int length = language.length;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
/* Maybe invalid layout */
|
|
Packit Service |
1d8f1c |
if (length < 2)
|
|
Packit Service |
1d8f1c |
return language;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
language = language.up();
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
int index = 0;
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
foreach (var saved_language in m_xkb_languages.get_values()) {
|
|
Packit Service |
1d8f1c |
if (language == saved_language[0:length])
|
|
Packit Service |
1d8f1c |
index++;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
if (index > 0) {
|
|
Packit Service |
1d8f1c |
unichar u = 0x2081 + index;
|
|
Packit Service |
1d8f1c |
language = "%s%s".printf(language, u.to_string());
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
m_xkb_languages.insert(name, language);
|
|
Packit Service |
1d8f1c |
return language;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public bool is_running() {
|
|
Packit Service |
1d8f1c |
return m_is_running;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public string get_input_context_path() {
|
|
Packit Service |
1d8f1c |
return m_input_context_path;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public IBus.EngineDesc? get_selected_engine() {
|
|
Packit Service |
1d8f1c |
return m_result_engine;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
|
|
Packit Service |
1d8f1c |
public void reset() {
|
|
Packit Service |
1d8f1c |
m_input_context_path = "";
|
|
Packit Service |
1d8f1c |
m_result = -1;
|
|
Packit Service |
1d8f1c |
m_result_engine = null;
|
|
Packit Service |
1d8f1c |
}
|
|
Packit Service |
1d8f1c |
}
|