ardour
floating_text_entry.cc
Go to the documentation of this file.
1 /*
2  Copyright (C) 2014 Paul Davis
3 
4  This program is free software; you can redistribute it and/or modify
5  it under the terms of the GNU General Public License as published by
6  the Free Software Foundation; either version 2 of the License, or
7  (at your option) any later version.
8 
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY; without even the implied warranty of
11  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  GNU General Public License for more details.
13 
14  You should have received a copy of the GNU General Public License
15  along with this program; if not, write to the Free Software
16  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17 
18 */
19 
20 #include "pbd/stacktrace.h"
21 #include "public_editor.h"
22 
23 
24 #include "floating_text_entry.h"
25 #include "gtkmm2ext/doi.h"
26 #include "gtkmm2ext/utils.h"
27 
28 #include "i18n.h"
29 
30 FloatingTextEntry::FloatingTextEntry (const std::string& initial_contents)
31  : Gtk::Window (Gtk::WINDOW_POPUP)
32  , entry_changed (false)
33 {
34  set_name (X_("FloatingTextEntry"));
35  set_position (Gtk::WIN_POS_MOUSE);
36  set_border_width (0);
37 
38  if (!initial_contents.empty()) {
39  entry.set_text (initial_contents);
40  }
41 
42  entry.show ();
43  entry.signal_changed().connect (sigc::mem_fun (*this, &FloatingTextEntry::changed));
44  entry.signal_activate().connect (sigc::mem_fun (*this, &FloatingTextEntry::activated));
45  entry.signal_key_press_event().connect (sigc::mem_fun (*this, &FloatingTextEntry::key_press));
46  entry.signal_button_press_event().connect (sigc::mem_fun (*this, &FloatingTextEntry::button_press));
47  PublicEditor::instance ().signal_focus_out_event().connect (sigc::mem_fun (*this, &FloatingTextEntry::entry_focus_out));
48 
49  add (entry);
50 }
51 
52 void
54 {
55  entry_changed = true;
56 }
57 
58 void
60 {
61  Gtk::Window::on_realize ();
62  get_window()->set_decorations (Gdk::WMDecoration (0));
63  entry.add_modal_grab ();
64 }
65 
66 bool
68 {
69  entry.remove_modal_grab ();
70  if (entry_changed) {
71  use_text (entry.get_text ());
72  }
73 
74  delete_when_idle ( this);
75  return false;
76 }
77 
78 bool
79 FloatingTextEntry::button_press (GdkEventButton* ev)
80 {
81  if (Gtkmm2ext::event_inside_widget_window (*this, (GdkEvent*) ev)) {
82  return true;
83  }
84 
85  /* Clicked outside widget window - edit is done */
86  entry.remove_modal_grab ();
87 
88  /* arrange re-propagation of the event once we go idle */
89  Glib::signal_idle().connect (sigc::bind_return (sigc::bind (sigc::ptr_fun (gtk_main_do_event), gdk_event_copy ((GdkEvent*) ev)), false));
90 
91  if (entry_changed) {
92  use_text (entry.get_text ());
93  }
94 
95  delete_when_idle ( this);
96 
97  return false;
98 }
99 
100 void
102 {
103  use_text (entry.get_text()); // EMIT SIGNAL
104  delete_when_idle (this);
105 }
106 
107 bool
109 {
110  switch (ev->keyval) {
111  case GDK_Escape:
112  delete_when_idle (this);
113  return true;
114  break;
115  default:
116  break;
117  }
118  return false;
119 }
120 
121 void
123 {
124  entry.remove_modal_grab ();
125 
126  /* No hide button is shown (no decoration on the window),
127  so being hidden is equivalent to the Escape key or any other
128  method of cancelling the edit.
129  */
130 
131  delete_when_idle (this);
132  Gtk::Window::on_hide ();
133 }
sigc::signal1< void, std::string > use_text
LIBGTKMM2EXT_API bool event_inside_widget_window(Gtk::Widget &widget, GdkEvent *ev)
Definition: utils.cc:816
Definition: ardour_ui.h:130
FloatingTextEntry(const std::string &initial_contents)
#define X_(Text)
Definition: i18n.h:13
bool entry_focus_out(GdkEventFocus *)
void delete_when_idle(T *obj)
Definition: doi.h:34
bool key_press(GdkEventKey *)
bool button_press(GdkEventButton *)
static PublicEditor & instance()