9
9
10
10
namespace horizon {
11
11
12
- class LayerDisplayButton : public Gtk ::DrawingArea {
12
+ class LayerDisplayPreview : public Gtk ::DrawingArea {
13
13
public:
14
- LayerDisplayButton ();
15
-
16
- typedef Glib::Property<Gdk::RGBA> type_property_color;
17
- Glib::PropertyProxy<Gdk::RGBA> property_color ()
18
- {
19
- return p_property_color.get_proxy ();
20
- }
21
- typedef Glib::Property<LayerDisplay::Mode> type_property_display_mode;
22
- Glib::PropertyProxy<LayerDisplay::Mode> property_display_mode ()
23
- {
24
- return p_property_display_mode.get_proxy ();
25
- }
26
- void set_color (const Color &c);
14
+ LayerDisplayPreview (const Glib::PropertyProxy<Gdk::RGBA> &property_color, LayerDisplay::Mode display_mode);
15
+ LayerDisplayPreview (const Glib::PropertyProxy<Gdk::RGBA> &property_color,
16
+ Glib::PropertyProxy<LayerDisplay::Mode> property_display_mode);
27
17
28
18
private:
29
19
bool on_draw (const Cairo::RefPtr<::Cairo::Context> &cr) override ;
30
- bool on_button_press_event (GdkEventButton *ev) override ;
31
- type_property_color p_property_color;
32
- type_property_display_mode p_property_display_mode;
20
+ Glib::PropertyProxy<Gdk::RGBA> property_color;
21
+ LayerDisplay::Mode dm;
33
22
};
34
23
35
- LayerDisplayButton::LayerDisplayButton ()
36
- : Glib::ObjectBase(typeid (LayerDisplayButton)), Gtk::DrawingArea(),
37
- p_property_color (*this , " color" , Gdk::RGBA(" #ff0000" )), p_property_display_mode(*this , " display-mode" )
24
+ LayerDisplayPreview::LayerDisplayPreview (const Glib::PropertyProxy<Gdk::RGBA> &color, LayerDisplay::Mode mode)
25
+ : Glib::ObjectBase(typeid (LayerDisplayPreview)), Gtk::DrawingArea(), property_color(color), dm(mode)
38
26
{
39
27
set_size_request (18 , 18 );
40
- add_events (Gdk::BUTTON_PRESS_MASK);
41
- property_display_mode ().signal_changed ().connect ([this ] { queue_draw (); });
42
- property_color ().signal_changed ().connect ([this ] { queue_draw (); });
28
+ property_color.signal_changed ().connect ([this ] { queue_draw (); });
29
+ }
30
+
31
+ LayerDisplayPreview::LayerDisplayPreview (const Glib::PropertyProxy<Gdk::RGBA> &color,
32
+ Glib::PropertyProxy<LayerDisplay::Mode> property_display_mode)
33
+ : LayerDisplayPreview(color, property_display_mode.get_value())
34
+ {
35
+ property_display_mode.signal_changed ().connect ([this , property_display_mode] {
36
+ dm = property_display_mode.get_value ();
37
+ queue_draw ();
38
+ });
43
39
}
44
40
45
- bool LayerDisplayButton ::on_draw (const Cairo::RefPtr<::Cairo::Context> &cr)
41
+ bool LayerDisplayPreview ::on_draw (const Cairo::RefPtr<::Cairo::Context> &cr)
46
42
{
47
43
48
- const auto c = p_property_color .get_value ();
44
+ const auto c = property_color .get_value ();
49
45
cr->save ();
50
46
cr->translate (1 , 1 );
51
47
cr->rectangle (0 , 0 , 16 , 16 );
52
48
cr->set_source_rgb (0 , 0 , 0 );
53
49
cr->fill_preserve ();
54
50
cr->set_source_rgb (c.get_red (), c.get_green (), c.get_blue ());
55
51
cr->set_line_width (2 );
56
- LayerDisplay::Mode dm = p_property_display_mode.get_value ();
57
- if (dm == LayerDisplay::Mode::FILL || dm == LayerDisplay::Mode::FILL_ONLY) {
52
+ if (dm == LayerDisplay::Mode::FILL || dm == LayerDisplay::Mode::FILL_ONLY || dm == LayerDisplay::Mode::DOTTED) {
58
53
cr->fill_preserve ();
59
54
}
60
55
@@ -76,20 +71,75 @@ bool LayerDisplayButton::on_draw(const Cairo::RefPtr<::Cairo::Context> &cr)
76
71
cr->line_to (16 , 7 );
77
72
cr->stroke ();
78
73
}
74
+ if (dm == LayerDisplay::Mode::DOTTED) {
75
+ cr->save ();
76
+ cr->set_source_rgb (0 , 0 , 0 );
77
+ cr->begin_new_sub_path ();
78
+ cr->arc (8 , 1 , 2 , 0 , 2 * M_PI);
79
+ cr->begin_new_sub_path ();
80
+ cr->arc (8 , 8 , 2 , 0 , 2 * M_PI);
81
+ cr->begin_new_sub_path ();
82
+ cr->arc (8 , 15 , 2 , 0 , 2 * M_PI);
83
+ cr->begin_new_sub_path ();
84
+ cr->arc (2 , 4.5 , 2 , 0 , 2 * M_PI);
85
+ cr->begin_new_sub_path ();
86
+ cr->arc (2 , 12.5 , 2 , 0 , 2 * M_PI);
87
+ cr->begin_new_sub_path ();
88
+ cr->arc (14 , 4.5 , 2 , 0 , 2 * M_PI);
89
+ cr->begin_new_sub_path ();
90
+ cr->arc (14 , 12.5 , 2 , 0 , 2 * M_PI);
91
+ cr->fill ();
92
+ cr->restore ();
93
+ cr->rectangle (0 , 0 , 16 , 16 );
94
+ cr->stroke ();
95
+ }
79
96
80
97
cr->restore ();
81
98
Gtk::DrawingArea::on_draw (cr);
82
99
return true ;
83
100
}
84
101
85
- bool LayerDisplayButton::on_button_press_event (GdkEventButton *ev)
102
+
103
+ class LayerDisplayButton : public Gtk ::EventBox {
104
+ public:
105
+ LayerDisplayButton ();
106
+ void set_color (const Color &c);
107
+
108
+ Glib::PropertyProxy<Gdk::RGBA> property_color ()
109
+ {
110
+ return p_property_color.get_proxy ();
111
+ }
112
+
113
+ Glib::PropertyProxy<LayerDisplay::Mode> property_display_mode ()
114
+ {
115
+ return p_property_display_mode.get_proxy ();
116
+ }
117
+
118
+ private:
119
+ void append_context_menu_item (const std::string &name, LayerDisplay::Mode mode);
120
+ bool on_button_press_event (GdkEventButton *ev) override ;
121
+ Gtk::Menu context_menu;
122
+ Gtk::RadioButtonGroup context_menu_group;
123
+ std::map<LayerDisplay::Mode, Gtk::RadioMenuItem *> layer_mode_menu_items;
124
+
125
+ Glib::Property<Gdk::RGBA> p_property_color;
126
+ Glib::Property<LayerDisplay::Mode> p_property_display_mode;
127
+
128
+ LayerDisplayPreview button_face;
129
+ };
130
+
131
+ LayerDisplayButton::LayerDisplayButton ()
132
+ : Glib::ObjectBase(typeid (LayerDisplayButton)), Gtk::EventBox(),
133
+ p_property_color (*this , " color" , Gdk::RGBA(" #ff0000" )), p_property_display_mode(*this , " display-mode" ),
134
+ button_face(p_property_color.get_proxy(), p_property_display_mode.get_proxy())
86
135
{
87
- if (ev->button != 1 )
88
- return false ;
89
- auto old_mode = static_cast <int >(static_cast <LayerDisplay::Mode>(property_display_mode ()));
90
- auto new_mode = static_cast <LayerDisplay::Mode>((old_mode + 1 ) % static_cast <int >(LayerDisplay::Mode::N_MODES));
91
- p_property_display_mode = new_mode;
92
- return true ;
136
+ add (button_face);
137
+ add_events (Gdk::BUTTON_PRESS_MASK);
138
+ append_context_menu_item (" Outline" , LayerDisplay::Mode::OUTLINE);
139
+ append_context_menu_item (" Hatched" , LayerDisplay::Mode::HATCH);
140
+ append_context_menu_item (" Fill" , LayerDisplay::Mode::FILL);
141
+ append_context_menu_item (" Fill only" , LayerDisplay::Mode::FILL_ONLY);
142
+ append_context_menu_item (" Dotted" , LayerDisplay::Mode::DOTTED);
93
143
}
94
144
95
145
void LayerDisplayButton::set_color (const Color &c)
@@ -101,6 +151,46 @@ void LayerDisplayButton::set_color(const Color &c)
101
151
property_color () = rgba;
102
152
}
103
153
154
+ void LayerDisplayButton::append_context_menu_item (const std::string &name, LayerDisplay::Mode mode)
155
+ {
156
+ auto it = Gtk::manage (new Gtk::RadioMenuItem (context_menu_group));
157
+
158
+ auto *hbox = Gtk::manage (new Gtk::Box (Gtk::ORIENTATION_HORIZONTAL, 8 ));
159
+ auto *preview = Gtk::manage (new LayerDisplayPreview (property_color (), mode));
160
+ hbox->pack_start (*preview, false , false , 0 );
161
+ preview->show ();
162
+ auto *label = Gtk::manage (new Gtk::Label (name));
163
+ hbox->pack_start (*label, false , false , 0 );
164
+ label->show ();
165
+
166
+ it->add (*hbox);
167
+ hbox->show ();
168
+
169
+ it->signal_activate ().connect ([this , mode] { p_property_display_mode = mode; });
170
+ context_menu.append (*it);
171
+ it->show ();
172
+ layer_mode_menu_items.emplace (mode, it);
173
+ }
174
+
175
+ bool LayerDisplayButton::on_button_press_event (GdkEventButton *ev)
176
+ {
177
+ if (gdk_event_triggers_context_menu ((GdkEvent *)ev)) {
178
+ layer_mode_menu_items.at (p_property_display_mode)->set_active ();
179
+ #if GTK_CHECK_VERSION(3, 22, 0)
180
+ context_menu.popup_at_pointer ((GdkEvent *)ev);
181
+ #else
182
+ context_menu.popup (ev->button , gtk_get_current_event_time ());
183
+ #endif
184
+ return true ;
185
+ }
186
+ if (ev->button != 1 )
187
+ return false ;
188
+ auto old_mode = static_cast <int >(static_cast <LayerDisplay::Mode>(property_display_mode ()));
189
+ auto new_mode = static_cast <LayerDisplay::Mode>((old_mode + 1 ) % static_cast <int >(LayerDisplay::Mode::N_MODES));
190
+ p_property_display_mode = new_mode;
191
+ return true ;
192
+ }
193
+
104
194
105
195
class LayerBoxRow : public Gtk ::Box {
106
196
public:
@@ -321,13 +411,15 @@ void LayerBox::update()
321
411
update_work_layer ();
322
412
}
323
413
414
+ // clang-format off
324
415
static const LutEnumStr<LayerDisplay::Mode> dm_lut = {
325
416
{" outline" , LayerDisplay::Mode::OUTLINE},
326
417
{" hatch" , LayerDisplay::Mode::HATCH},
327
418
{" fill" , LayerDisplay::Mode::FILL},
328
419
{" fill_only" , LayerDisplay::Mode::FILL_ONLY},
420
+ {" dotted" , LayerDisplay::Mode::DOTTED},
329
421
};
330
-
422
+ // clang-format on
331
423
332
424
void LayerBox::update_work_layer ()
333
425
{
0 commit comments