LEFT | RIGHT |
1 /* vim:set et sts=4 sw=4: | 1 /* vim:set et sts=4 sw=4: |
2 * | 2 * |
3 * ibus - The Input Bus | 3 * ibus - The Input Bus |
4 * | 4 * |
5 * Copyright (c) 2017 Takao Fujiwara <takao.fujiwara1@gmail.com> | 5 * Copyright (c) 2017 Takao Fujiwara <takao.fujiwara1@gmail.com> |
6 * | 6 * |
7 * This library is free software; you can redistribute it and/or | 7 * This library is free software; you can redistribute it and/or |
8 * modify it under the terms of the GNU Lesser General Public | 8 * modify it under the terms of the GNU Lesser General Public |
9 * License as published by the Free Software Foundation; either | 9 * License as published by the Free Software Foundation; either |
10 * version 2.1 of the License, or (at your option) any later version. | 10 * version 2.1 of the License, or (at your option) any later version. |
(...skipping 21 matching lines...) Expand all Loading... |
32 ); | 32 ); |
33 } | 33 } |
34 } | 34 } |
35 private class EListBox : Gtk.ListBox { | 35 private class EListBox : Gtk.ListBox { |
36 public EListBox() { | 36 public EListBox() { |
37 GLib.Object( | 37 GLib.Object( |
38 vexpand : true, | 38 vexpand : true, |
39 halign : Gtk.Align.FILL, | 39 halign : Gtk.Align.FILL, |
40 valign : Gtk.Align.FILL | 40 valign : Gtk.Align.FILL |
41 ); | 41 ); |
| 42 this.motion_notify_event.connect((e) => { |
| 43 #if VALA_0_24 |
| 44 Gdk.EventMotion pe = e; |
| 45 #else |
| 46 Gdk.EventMotion *pe = &e; |
| 47 #endif |
| 48 if (m_mouse_x == pe.x_root && m_mouse_y == pe.y_root) |
| 49 return false; |
| 50 m_mouse_x = pe.x_root; |
| 51 m_mouse_y = pe.y_root; |
| 52 var row = this.get_row_at_y((int)e.y); |
| 53 if (row != null) |
| 54 this.select_row(row); |
| 55 return false; |
| 56 }); |
| 57 this.enter_notify_event.connect((e) => { |
| 58 // avoid gtk_button_update_state() |
| 59 return true; |
| 60 }); |
42 } | 61 } |
43 } | 62 } |
44 private class EBoxRow : Gtk.ListBoxRow { | 63 private class EBoxRow : Gtk.ListBoxRow { |
45 public EBoxRow(string text) { | 64 public EBoxRow(string text) { |
46 this.text = text; | 65 this.text = text; |
47 } | 66 } |
48 | 67 |
49 public string text { get; set; } | 68 public string text { get; set; } |
50 } | 69 } |
51 private class EScrolledWindow : Gtk.ScrolledWindow { | 70 private class EScrolledWindow : Gtk.ScrolledWindow { |
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
121 public override void get_preferred_height(out int minimum_height, | 140 public override void get_preferred_height(out int minimum_height, |
122 out int natural_height) { | 141 out int natural_height) { |
123 get_preferred_size_with_hb(null, null, | 142 get_preferred_size_with_hb(null, null, |
124 out minimum_height, | 143 out minimum_height, |
125 out natural_height); | 144 out natural_height); |
126 } | 145 } |
127 public override bool draw(Cairo.Context cr) { | 146 public override bool draw(Cairo.Context cr) { |
128 if (m_fontset == null) | 147 if (m_fontset == null) |
129 return true; | 148 return true; |
130 if (m_requisition == null) | 149 if (m_requisition == null) |
131 return true; | 150 return true; |
132 if (m_requisition.cairo_lines == null) | 151 if (m_requisition.cairo_lines == null) |
133 return true; | 152 return true; |
134 var style_context = get_style_context(); | 153 var style_context = get_style_context(); |
135 Gtk.Allocation allocation; | 154 Gtk.Allocation allocation; |
136 get_allocation(out allocation); | 155 get_allocation(out allocation); |
137 style_context.render_background(cr, | 156 style_context.render_background(cr, |
138 0, 0, | 157 0, 0, |
139 allocation.width, | 158 allocation.width, |
140 allocation.height); | 159 allocation.height); |
141 Gdk.RGBA *normal_fg = null; | 160 Gdk.RGBA *normal_fg = null; |
142 style_context.get(Gtk.StateFlags.NORMAL, | 161 style_context.get(Gtk.StateFlags.NORMAL, |
143 "color", | 162 "color", |
(...skipping 10 matching lines...) Expand all Loading... |
154 y = (allocation.height - m_requisition.height) / 2.0; | 173 y = (allocation.height - m_requisition.height) / 2.0; |
155 cr.translate(x, y); | 174 cr.translate(x, y); |
156 m_fontset.draw_cairo_with_requisition_ex(cr, m_requisition); | 175 m_fontset.draw_cairo_with_requisition_ex(cr, m_requisition); |
157 cr.restore(); | 176 cr.restore(); |
158 normal_fg.free(); | 177 normal_fg.free(); |
159 normal_fg = null; | 178 normal_fg = null; |
160 return true; | 179 return true; |
161 } | 180 } |
162 #endif | 181 #endif |
163 } | 182 } |
164 //private class ESelectedLabel : Gtk.Label { | |
165 private class ESelectedLabel : EWhiteLabel { | 183 private class ESelectedLabel : EWhiteLabel { |
166 public ESelectedLabel(string text) { | 184 public ESelectedLabel(string text) { |
167 GLib.Object( | 185 GLib.Object( |
168 name : "IBusEmojierSelectedLabel" | 186 name : "IBusEmojierSelectedLabel" |
169 ); | 187 ); |
170 if (text != "") | 188 if (text != "") |
171 set_label(text); | 189 set_label(text); |
172 } | 190 } |
173 } | 191 } |
174 //private class EGoldLabel : Gtk.Label { | |
175 private class EGoldLabel : EWhiteLabel { | 192 private class EGoldLabel : EWhiteLabel { |
176 public EGoldLabel(string text) { | 193 public EGoldLabel(string text) { |
177 GLib.Object( | 194 GLib.Object( |
178 name : "IBusEmojierGoldLabel" | 195 name : "IBusEmojierGoldLabel" |
179 ); | 196 ); |
180 if (text != "") | 197 if (text != "") |
181 set_label(text); | 198 set_label(text); |
182 } | 199 } |
183 } | 200 } |
184 private class EPaddedLabel : Gtk.Label { | 201 private class EPaddedLabel : Gtk.Label { |
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
304 private GLib.MainLoop? m_loop; | 321 private GLib.MainLoop? m_loop; |
305 private string? m_result; | 322 private string? m_result; |
306 private string? m_unicode_point = null; | 323 private string? m_unicode_point = null; |
307 private bool m_candidate_panel_is_visible; | 324 private bool m_candidate_panel_is_visible; |
308 private int m_category_active_index; | 325 private int m_category_active_index; |
309 private IBus.LookupTable m_lookup_table; | 326 private IBus.LookupTable m_lookup_table; |
310 private Gtk.Label[] m_candidates; | 327 private Gtk.Label[] m_candidates; |
311 private bool m_enter_notify_enable = true; | 328 private bool m_enter_notify_enable = true; |
312 private uint m_entry_notify_show_id; | 329 private uint m_entry_notify_show_id; |
313 private uint m_entry_notify_disable_id; | 330 private uint m_entry_notify_disable_id; |
| 331 protected static double m_mouse_x; |
| 332 protected static double m_mouse_y; |
314 | 333 |
315 public signal void candidate_clicked(uint index, uint button, uint state); | 334 public signal void candidate_clicked(uint index, uint button, uint state); |
316 | 335 |
317 public IBusEmojier() { | 336 public IBusEmojier() { |
318 GLib.Object( | 337 GLib.Object( |
319 type : Gtk.WindowType.TOPLEVEL, | 338 type : Gtk.WindowType.TOPLEVEL, |
320 events : Gdk.EventMask.KEY_PRESS_MASK | | 339 events : Gdk.EventMask.KEY_PRESS_MASK | |
321 Gdk.EventMask.KEY_RELEASE_MASK | | 340 Gdk.EventMask.KEY_RELEASE_MASK | |
322 Gdk.EventMask.BUTTON_PRESS_MASK | | 341 Gdk.EventMask.BUTTON_PRESS_MASK | |
323 Gdk.EventMask.BUTTON_RELEASE_MASK, | 342 Gdk.EventMask.BUTTON_RELEASE_MASK, |
(...skipping 22 matching lines...) Expand all Loading... |
346 if (m_favorite_annotations == null) | 365 if (m_favorite_annotations == null) |
347 m_favorite_annotations = {}; | 366 m_favorite_annotations = {}; |
348 | 367 |
349 Gdk.Display display = Gdk.Display.get_default(); | 368 Gdk.Display display = Gdk.Display.get_default(); |
350 Gdk.Screen screen = (display != null) ? | 369 Gdk.Screen screen = (display != null) ? |
351 display.get_default_screen() : null; | 370 display.get_default_screen() : null; |
352 | 371 |
353 if (screen == null) { | 372 if (screen == null) { |
354 warning("Could not open display."); | 373 warning("Could not open display."); |
355 return; | 374 return; |
| 375 } |
| 376 // Set en locale because de_DE's decimal_point is ',' instead of '.' |
| 377 string? backup_locale = |
| 378 Intl.setlocale(LocaleCategory.NUMERIC, null).dup(); |
| 379 if (Intl.setlocale(LocaleCategory.NUMERIC, "en_US.UTF-8") == null) { |
| 380 if (Intl.setlocale(LocaleCategory.NUMERIC, "C.UTF-8") == null) { |
| 381 if (Intl.setlocale(LocaleCategory.NUMERIC, "C") == null) { |
| 382 warning("You don't install either en_US.UTF-8 or C.UTF-8 " + |
| 383 "or C locale"); |
| 384 } |
| 385 } |
356 } | 386 } |
357 m_rgba = new ThemedRGBA(this); | 387 m_rgba = new ThemedRGBA(this); |
358 uint bg_red = (uint)(m_rgba.normal_bg.red * 255); | 388 uint bg_red = (uint)(m_rgba.normal_bg.red * 255); |
359 uint bg_green = (uint)(m_rgba.normal_bg.green * 255); | 389 uint bg_green = (uint)(m_rgba.normal_bg.green * 255); |
360 uint bg_blue = (uint)(m_rgba.normal_bg.blue * 255); | 390 uint bg_blue = (uint)(m_rgba.normal_bg.blue * 255); |
361 double bg_alpha = m_rgba.normal_bg.alpha; | 391 double bg_alpha = m_rgba.normal_bg.alpha; |
362 string data = | 392 string data = |
363 "#IBusEmojierWhiteLabel { background-color: " + | 393 "#IBusEmojierWhiteLabel { background-color: " + |
364 "rgba(%u, %u, %u, %lf); ".printf( | 394 "rgba(%u, %u, %u, %lf); ".printf( |
365 bg_red, bg_green, bg_blue, bg_alpha) + | 395 bg_red, bg_green, bg_blue, bg_alpha) + |
(...skipping 26 matching lines...) Expand all Loading... |
392 "background-color: #b09c5f; " + | 422 "background-color: #b09c5f; " + |
393 "border-width: 4px; border-radius: 3px; }"; | 423 "border-width: 4px; border-radius: 3px; }"; |
394 | 424 |
395 Gtk.CssProvider css_provider = new Gtk.CssProvider(); | 425 Gtk.CssProvider css_provider = new Gtk.CssProvider(); |
396 try { | 426 try { |
397 css_provider.load_from_data(data, -1); | 427 css_provider.load_from_data(data, -1); |
398 } catch (GLib.Error e) { | 428 } catch (GLib.Error e) { |
399 warning("Failed css_provider_from_data: %s", e.message); | 429 warning("Failed css_provider_from_data: %s", e.message); |
400 return; | 430 return; |
401 } | 431 } |
| 432 if (backup_locale != null) |
| 433 Intl.setlocale(LocaleCategory.NUMERIC, backup_locale); |
| 434 else |
| 435 Intl.setlocale(LocaleCategory.NUMERIC, ""); |
402 | 436 |
403 Gtk.StyleContext.add_provider_for_screen( | 437 Gtk.StyleContext.add_provider_for_screen( |
404 screen, | 438 screen, |
405 css_provider, | 439 css_provider, |
406 Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION); | 440 Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION); |
407 | 441 |
408 m_title = new ETitleLabelBox(_("Emoji Choice")); | 442 m_title = new ETitleLabelBox(_("Emoji Choice")); |
409 set_titlebar(m_title); | 443 set_titlebar(m_title); |
410 m_vbox = new Gtk.Box(Gtk.Orientation.VERTICAL, 0); | 444 m_vbox = new Gtk.Box(Gtk.Orientation.VERTICAL, 0); |
411 add(m_vbox); | 445 add(m_vbox); |
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
495 m_emoji_max_seq_len = annotation.length; | 529 m_emoji_max_seq_len = annotation.length; |
496 } | 530 } |
497 } | 531 } |
498 | 532 |
499 | 533 |
500 private static void update_annotation_to_emojis_dict(IBus.EmojiData data) { | 534 private static void update_annotation_to_emojis_dict(IBus.EmojiData data) { |
501 string emoji = data.get_emoji(); | 535 string emoji = data.get_emoji(); |
502 unowned GLib.SList<string> annotations = data.get_annotations(); | 536 unowned GLib.SList<string> annotations = data.get_annotations(); |
503 foreach (string annotation in annotations) { | 537 foreach (string annotation in annotations) { |
504 bool has_emoji = false; | 538 bool has_emoji = false; |
505 unowned GLib.SList<string> hits = | 539 GLib.SList<string> hits = |
506 m_annotation_to_emojis_dict.lookup(annotation); | 540 m_annotation_to_emojis_dict.lookup(annotation).copy_deep( |
| 541 GLib.strdup); |
507 foreach (string hit_emoji in hits) { | 542 foreach (string hit_emoji in hits) { |
508 if (hit_emoji == emoji) { | 543 if (hit_emoji == emoji) { |
509 has_emoji = true; | 544 has_emoji = true; |
510 break; | 545 break; |
511 } | 546 } |
512 } | 547 } |
513 if (!has_emoji) { | 548 if (!has_emoji) { |
514 hits.append(emoji); | 549 hits.append(emoji); |
515 m_annotation_to_emojis_dict.replace( | 550 m_annotation_to_emojis_dict.replace( |
516 annotation, | 551 annotation, |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
556 } | 591 } |
557 str = str.next_char(); | 592 str = str.next_char(); |
558 } | 593 } |
559 return buff.str; | 594 return buff.str; |
560 } | 595 } |
561 | 596 |
562 | 597 |
563 private static void | 598 private static void |
564 update_annotations_with_description (IBus.EmojiData data, | 599 update_annotations_with_description (IBus.EmojiData data, |
565 string description) { | 600 string description) { |
566 unowned GLib.SList<string> annotations = data.get_annotations(); | 601 GLib.SList<string> annotations = |
| 602 data.get_annotations().copy_deep(GLib.strdup); |
567 bool update_annotations = false; | 603 bool update_annotations = false; |
568 string former = null; | 604 string former = null; |
569 string later = null; | 605 string later = null; |
570 int index = description.index_of(": "); | 606 int index = description.index_of(": "); |
571 if (index > 0) { | 607 if (index > 0) { |
572 former = description.substring(0, index); | 608 former = description.substring(0, index); |
573 if (annotations.find_custom(former, GLib.strcmp) == null) { | 609 if (annotations.find_custom(former, GLib.strcmp) == null) { |
574 annotations.append(former); | 610 annotations.append(former); |
575 update_annotations = true; | 611 update_annotations = true; |
576 } | 612 } |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
629 | 665 |
630 private static void update_category_to_emojis_dict(IBus.EmojiData data, | 666 private static void update_category_to_emojis_dict(IBus.EmojiData data, |
631 string lang) { | 667 string lang) { |
632 string emoji = data.get_emoji(); | 668 string emoji = data.get_emoji(); |
633 string category = data.get_category(); | 669 string category = data.get_category(); |
634 if (category == "") | 670 if (category == "") |
635 category = EMOJI_CATEGORY_OTHERS; | 671 category = EMOJI_CATEGORY_OTHERS; |
636 if (lang == "en") { | 672 if (lang == "en") { |
637 bool has_variant = false; | 673 bool has_variant = false; |
638 foreach (unichar ch in EMOJI_VARIANT_LIST) { | 674 foreach (unichar ch in EMOJI_VARIANT_LIST) { |
639 if (emoji.chr(-1, ch) != null) { | 675 if (emoji.index_of_char(ch) >= 0) { |
640 has_variant = true; | 676 has_variant = true; |
641 break; | 677 break; |
642 } | 678 } |
643 } | 679 } |
644 // If emoji includes variants (skin colors and items), | 680 // If emoji includes variants (skin colors and items), |
645 // it's escaped in m_emoji_to_emoji_variants_dict and | 681 // it's escaped in m_emoji_to_emoji_variants_dict and |
646 // not shown by default. | 682 // not shown by default. |
647 if (has_variant) { | 683 if (has_variant) { |
648 unichar base_ch = emoji.get_char(); | 684 unichar base_ch = emoji.get_char(); |
649 string base_emoji = base_ch.to_string(); | 685 string base_emoji = base_ch.to_string(); |
650 var buff = new GLib.StringBuilder(); | 686 var buff = new GLib.StringBuilder(); |
651 buff.append_unichar(base_ch); | 687 buff.append_unichar(base_ch); |
652 buff.append_unichar(0xfe0f); | 688 buff.append_unichar(0xfe0f); |
653 if (m_emoji_to_data_dict.lookup(buff.str) != null) | 689 if (m_emoji_to_data_dict.lookup(buff.str) != null) |
654 base_emoji = buff.str; | 690 base_emoji = buff.str; |
655 unowned GLib.SList<string>? variants = | 691 GLib.SList<string>? variants = |
656 m_emoji_to_emoji_variants_dict.lookup(base_emoji); | 692 m_emoji_to_emoji_variants_dict.lookup( |
| 693 base_emoji).copy_deep(GLib.strdup); |
657 if (variants.find_custom(emoji, GLib.strcmp) == null) { | 694 if (variants.find_custom(emoji, GLib.strcmp) == null) { |
658 if (variants == null) | 695 if (variants == null) |
659 variants.append(base_emoji); | 696 variants.append(base_emoji); |
660 variants.append(emoji); | 697 variants.append(emoji); |
661 m_emoji_to_emoji_variants_dict.replace( | 698 m_emoji_to_emoji_variants_dict.replace( |
662 base_emoji, | 699 base_emoji, |
663 variants.copy_deep(GLib.strdup)); | 700 variants.copy_deep(GLib.strdup)); |
664 } | 701 } |
665 return; | 702 return; |
666 } | 703 } |
667 bool has_emoji = false; | 704 bool has_emoji = false; |
668 unowned GLib.SList<string> hits = | 705 GLib.SList<string> hits = |
669 m_category_to_emojis_dict.lookup(category); | 706 m_category_to_emojis_dict.lookup(category).copy_deep( |
| 707 GLib.strdup); |
670 foreach (string hit_emoji in hits) { | 708 foreach (string hit_emoji in hits) { |
671 if (hit_emoji == emoji) { | 709 if (hit_emoji == emoji) { |
672 has_emoji = true; | 710 has_emoji = true; |
673 break; | 711 break; |
674 } | 712 } |
675 } | 713 } |
676 if (!has_emoji) { | 714 if (!has_emoji) { |
677 hits.append(emoji); | 715 hits.append(emoji); |
678 m_category_to_emojis_dict.replace(category, | 716 m_category_to_emojis_dict.replace(category, |
679 hits.copy_deep(GLib.strdup)); | 717 hits.copy_deep(GLib.strdup)); |
(...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
834 buttons_hbox.pack_start(prev_button, false, false, 0); | 872 buttons_hbox.pack_start(prev_button, false, false, 0); |
835 buttons_hbox.pack_start(next_button, false, false, 0); | 873 buttons_hbox.pack_start(next_button, false, false, 0); |
836 m_vbox.pack_start(buttons_hbox, false, false, 0); | 874 m_vbox.pack_start(buttons_hbox, false, false, 0); |
837 buttons_hbox.show_all(); | 875 buttons_hbox.show_all(); |
838 } | 876 } |
839 | 877 |
840 | 878 |
841 private bool check_unicode_point() { | 879 private bool check_unicode_point() { |
842 string annotation = m_entry.get_text(); | 880 string annotation = m_entry.get_text(); |
843 m_unicode_point = null; | 881 m_unicode_point = null; |
844 var buff = new GLib.StringBuilder(); | 882 // Add "0x" because uint64.ascii_strtoull() is not accessible |
| 883 // and need to use uint64.parse() |
| 884 var buff = new GLib.StringBuilder("0x"); |
845 var retval = new GLib.StringBuilder(); | 885 var retval = new GLib.StringBuilder(); |
846 for (int i = 0; i < annotation.char_count(); i++) { | 886 for (int i = 0; i < annotation.char_count(); i++) { |
847 unichar ch = annotation.get_char(i); | 887 unichar ch = annotation.get_char(i); |
848 if (ch == 0) | 888 if (ch == 0) |
849 return false; | 889 return false; |
850 if (ch.isspace()) { | 890 if (ch.isspace()) { |
851 unichar code = (unichar)buff.str.to_ulong(null, 16); | 891 unichar code = (unichar)uint64.parse(buff.str); |
852 buff.erase(); | 892 buff.assign("0x"); |
853 if (!code.validate()) | 893 if (!code.validate()) |
854 return false; | 894 return false; |
855 retval.append(code.to_string()); | 895 retval.append(code.to_string()); |
856 continue; | 896 continue; |
857 } | 897 } |
858 if (!ch.isxdigit()) | 898 if (!ch.isxdigit()) |
859 return false; | 899 return false; |
860 buff.append_unichar(ch); | 900 buff.append_unichar(ch); |
861 } | 901 } |
862 unichar code = (unichar)buff.str.to_ulong(null, 16); | 902 unichar code = (unichar)uint64.parse(buff.str); |
863 if (!code.validate()) | 903 if (!code.validate()) |
864 return false; | 904 return false; |
865 retval.append(code.to_string()); | 905 retval.append(code.to_string()); |
866 m_unicode_point = retval.str; | 906 m_unicode_point = retval.str; |
867 if (m_unicode_point == null) | 907 if (m_unicode_point == null) |
868 return true; | 908 return true; |
869 IBus.Text text = new IBus.Text.from_string(m_unicode_point); | 909 IBus.Text text = new IBus.Text.from_string(m_unicode_point); |
870 m_lookup_table.append_candidate(text); | 910 m_lookup_table.append_candidate(text); |
871 return true; | 911 return true; |
872 } | 912 } |
(...skipping 13 matching lines...) Expand all Loading... |
886 switch(m_partial_match_condition) { | 926 switch(m_partial_match_condition) { |
887 case 0: | 927 case 0: |
888 if (key.has_prefix(annotation)) | 928 if (key.has_prefix(annotation)) |
889 matched = true; | 929 matched = true; |
890 break; | 930 break; |
891 case 1: | 931 case 1: |
892 if (key.has_suffix(annotation)) | 932 if (key.has_suffix(annotation)) |
893 matched = true; | 933 matched = true; |
894 break; | 934 break; |
895 case 2: | 935 case 2: |
896 if (key.str(annotation) != null) | 936 if (key.index_of(annotation) >= 0) |
897 matched = true; | 937 matched = true; |
898 break; | 938 break; |
899 default: | 939 default: |
900 break; | 940 break; |
901 } | 941 } |
902 if (!matched) | 942 if (!matched) |
903 continue; | 943 continue; |
904 sub_emojis = m_annotation_to_emojis_dict.lookup(key); | 944 sub_emojis = m_annotation_to_emojis_dict.lookup(key); |
905 foreach (unowned string emoji in sub_emojis) { | 945 foreach (unowned string emoji in sub_emojis) { |
906 if (total_emojis.find_custom(emoji, GLib.strcmp) == null) { | 946 if (total_emojis.find_custom(emoji, GLib.strcmp) == null) { |
(...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1024 string font_family = m_emoji_font_family; | 1064 string font_family = m_emoji_font_family; |
1025 int font_size = m_emoji_font_size - 2; | 1065 int font_size = m_emoji_font_size - 2; |
1026 string emoji_font = "%s %d".printf(font_family, font_size); | 1066 string emoji_font = "%s %d".printf(font_family, font_size); |
1027 string markup = "<span font=\"%s\">%s</span>". | 1067 string markup = "<span font=\"%s\">%s</span>". |
1028 printf(emoji_font, utf8_entity(text)); | 1068 printf(emoji_font, utf8_entity(text)); |
1029 label.set_markup(markup); | 1069 label.set_markup(markup); |
1030 } | 1070 } |
1031 label.set_halign(Gtk.Align.FILL); | 1071 label.set_halign(Gtk.Align.FILL); |
1032 label.set_valign(Gtk.Align.FILL); | 1072 label.set_valign(Gtk.Align.FILL); |
1033 Gtk.EventBox candidate_ebox = new Gtk.EventBox(); | 1073 Gtk.EventBox candidate_ebox = new Gtk.EventBox(); |
| 1074 candidate_ebox.add_events(Gdk.EventMask.POINTER_MOTION_MASK); |
1034 candidate_ebox.add(label); | 1075 candidate_ebox.add(label); |
1035 // Make a copy of i to workaround a bug in vala. | 1076 // Make a copy of i to workaround a bug in vala. |
1036 // https://bugzilla.gnome.org/show_bug.cgi?id=628336 | 1077 // https://bugzilla.gnome.org/show_bug.cgi?id=628336 |
1037 uint index = i; | 1078 uint index = i; |
1038 candidate_ebox.button_press_event.connect((w, e) => { | 1079 candidate_ebox.button_press_event.connect((w, e) => { |
1039 candidate_clicked(index, e.button, e.state); | 1080 candidate_clicked(index, e.button, e.state); |
1040 return true; | 1081 return true; |
1041 }); | 1082 }); |
1042 candidate_ebox.enter_notify_event.connect((e) => { | 1083 candidate_ebox.motion_notify_event.connect((e) => { |
1043 // m_enter_notify_enable is added because | 1084 // m_enter_notify_enable is added because |
1044 // enter_notify_event conflicts with keyboard operations. | 1085 // enter_notify_event conflicts with keyboard operations. |
1045 if (!m_enter_notify_enable) | 1086 if (!m_enter_notify_enable) |
1046 return true; | 1087 return false; |
1047 if (m_lookup_table.get_cursor_pos() == index) | 1088 if (m_lookup_table.get_cursor_pos() == index) |
1048 return true; | 1089 return false; |
| 1090 #if VALA_0_24 |
| 1091 Gdk.EventMotion pe = e; |
| 1092 #else |
| 1093 Gdk.EventMotion *pe = &e; |
| 1094 #endif |
| 1095 if (m_mouse_x == pe.x_root && m_mouse_y == pe.y_root) |
| 1096 return false; |
| 1097 m_mouse_x = pe.x_root; |
| 1098 m_mouse_y = pe.y_root; |
| 1099 |
1049 m_lookup_table.set_cursor_pos(index); | 1100 m_lookup_table.set_cursor_pos(index); |
1050 if (m_entry_notify_show_id > 0) { | 1101 if (m_entry_notify_show_id > 0 && |
| 1102 GLib.MainContext.default().find_source_by_id( |
| 1103 m_entry_notify_show_id) != null) { |
1051 GLib.Source.remove(m_entry_notify_show_id); | 1104 GLib.Source.remove(m_entry_notify_show_id); |
1052 } | 1105 } |
1053 // If timeout is not added, memory leak happens and | 1106 // If timeout is not added, memory leak happens and |
1054 // button_press_event signal does not work above. | 1107 // button_press_event signal does not work above. |
1055 m_entry_notify_show_id = GLib.Timeout.add(100, () => { | 1108 m_entry_notify_show_id = GLib.Timeout.add(100, () => { |
1056 show_candidate_panel(); | 1109 show_candidate_panel(); |
1057 return false; | 1110 return false; |
1058 }); | 1111 }); |
1059 return true; | 1112 return false; |
1060 }); | 1113 }); |
1061 grid.attach(candidate_ebox, | 1114 grid.attach(candidate_ebox, |
1062 n % (int)EMOJI_GRID_PAGE, n / (int)EMOJI_GRID_PAGE, | 1115 n % (int)EMOJI_GRID_PAGE, n / (int)EMOJI_GRID_PAGE, |
1063 1, 1); | 1116 1, 1); |
1064 n++; | 1117 n++; |
1065 | 1118 |
1066 m_candidates += label; | 1119 m_candidates += label; |
1067 } | 1120 } |
1068 if (n > 0) { | 1121 if (n > 0) { |
1069 m_candidate_panel_is_visible = true; | 1122 m_candidate_panel_is_visible = true; |
(...skipping 347 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1417 * does not give the keyboard focus when Emojier is lauched | 1470 * does not give the keyboard focus when Emojier is lauched |
1418 * twice with Ctrl-Shift-e via XIEvent, if present_with_time() | 1471 * twice with Ctrl-Shift-e via XIEvent, if present_with_time() |
1419 * is not applied. | 1472 * is not applied. |
1420 * But XFCE4 desktop does not effect this bug. | 1473 * But XFCE4 desktop does not effect this bug. |
1421 * Seems this is caused by the window manager's focus stealing | 1474 * Seems this is caused by the window manager's focus stealing |
1422 * prevention logic: | 1475 * prevention logic: |
1423 * https://mail.gnome.org/archives/gtk-devel-list/2017-May/msg00026.html | 1476 * https://mail.gnome.org/archives/gtk-devel-list/2017-May/msg00026.html |
1424 */ | 1477 */ |
1425 uint32 timestamp = event.get_time(); | 1478 uint32 timestamp = event.get_time(); |
1426 present_with_time(timestamp); | 1479 present_with_time(timestamp); |
| 1480 |
| 1481 Gdk.Device pointer; |
| 1482 #if VALA_0_34 |
| 1483 Gdk.Seat seat = event.get_seat(); |
| 1484 if (seat == null) { |
| 1485 var display = get_display(); |
| 1486 seat = display.get_default_seat(); |
| 1487 } |
| 1488 pointer = seat.get_pointer(); |
| 1489 #else |
| 1490 Gdk.Device device = event.get_device(); |
| 1491 if (device == null) { |
| 1492 var display = get_display(); |
| 1493 device = display.list_devices().data; |
| 1494 } |
| 1495 if (device.get_source() == Gdk.InputSource.KEYBOARD) |
| 1496 pointer = device.get_associated_device(); |
| 1497 else |
| 1498 pointer = device; |
| 1499 #endif |
| 1500 pointer.get_position_double(null, |
| 1501 out m_mouse_x, |
| 1502 out m_mouse_y); |
1427 | 1503 |
1428 m_loop = new GLib.MainLoop(); | 1504 m_loop = new GLib.MainLoop(); |
1429 m_loop.run(); | 1505 m_loop.run(); |
1430 m_loop = null; | 1506 m_loop = null; |
1431 | 1507 |
1432 // Need focus-out on Gtk.Entry to send the emoji to applications. | 1508 // Need focus-out on Gtk.Entry to send the emoji to applications. |
1433 Gdk.Event fevent = new Gdk.Event(Gdk.EventType.FOCUS_CHANGE); | 1509 Gdk.Event fevent = new Gdk.Event(Gdk.EventType.FOCUS_CHANGE); |
1434 fevent.focus_change.in = 0; | 1510 fevent.focus_change.in = 0; |
1435 fevent.focus_change.window = get_window(); | 1511 fevent.focus_change.window = get_window(); |
1436 m_entry.send_focus_change(fevent); | 1512 m_entry.send_focus_change(fevent); |
(...skipping 201 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1638 | 1714 |
1639 public void reset() { | 1715 public void reset() { |
1640 m_input_context_path = ""; | 1716 m_input_context_path = ""; |
1641 m_result = null; | 1717 m_result = null; |
1642 } | 1718 } |
1643 | 1719 |
1644 | 1720 |
1645 public void present_centralize(Gdk.Event event) { | 1721 public void present_centralize(Gdk.Event event) { |
1646 Gtk.Allocation allocation; | 1722 Gtk.Allocation allocation; |
1647 get_allocation(out allocation); | 1723 get_allocation(out allocation); |
| 1724 Gdk.Rectangle monitor_area; |
| 1725 #if VALA_0_34 |
| 1726 Gdk.Display display = Gdk.Display.get_default(); |
| 1727 Gdk.Monitor monitor = display.get_monitor_at_window(this.get_window()); |
| 1728 monitor_area = monitor.get_geometry(); |
| 1729 #else |
1648 Gdk.Screen screen = Gdk.Screen.get_default(); | 1730 Gdk.Screen screen = Gdk.Screen.get_default(); |
1649 int monitor_num = screen.get_monitor_at_window(get_window()); | 1731 int monitor_num = screen.get_monitor_at_window(this.get_window()); |
1650 Gdk.Rectangle monitor_area; | |
1651 screen.get_monitor_geometry(monitor_num, out monitor_area); | 1732 screen.get_monitor_geometry(monitor_num, out monitor_area); |
| 1733 #endif |
1652 int x = (monitor_area.x + monitor_area.width - allocation.width)/2; | 1734 int x = (monitor_area.x + monitor_area.width - allocation.width)/2; |
1653 int y = (monitor_area.y + monitor_area.height | 1735 int y = (monitor_area.y + monitor_area.height |
1654 - allocation.height)/2; | 1736 - allocation.height)/2; |
1655 move(x, y); | 1737 move(x, y); |
1656 | 1738 |
1657 uint32 timestamp = event.get_time(); | 1739 uint32 timestamp = event.get_time(); |
1658 present_with_time(timestamp); | 1740 present_with_time(timestamp); |
1659 m_entry.set_activates_default(true); | 1741 m_entry.set_activates_default(true); |
1660 } | 1742 } |
1661 | 1743 |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1741 m_favorites += favorite; | 1823 m_favorites += favorite; |
1742 } | 1824 } |
1743 for(int i = 0; i < unowned_favorite_annotations.length; i++) { | 1825 for(int i = 0; i < unowned_favorite_annotations.length; i++) { |
1744 string? favorite_annotation = unowned_favorite_annotations[i]; | 1826 string? favorite_annotation = unowned_favorite_annotations[i]; |
1745 GLib.return_if_fail(favorite_annotation != null); | 1827 GLib.return_if_fail(favorite_annotation != null); |
1746 m_favorite_annotations += favorite_annotation; | 1828 m_favorite_annotations += favorite_annotation; |
1747 } | 1829 } |
1748 update_favorite_emoji_dict(); | 1830 update_favorite_emoji_dict(); |
1749 } | 1831 } |
1750 } | 1832 } |
LEFT | RIGHT |