1dc23cb2b3654315bf1c0f00ee315e81ec792fa4
1 #define __GUIDELINE_CPP__
3 /*
4 * simple guideline dialog
5 *
6 * Authors:
7 * Lauris Kaplinski <lauris@kaplinski.com>
8 * Andrius R. <knutux@gmail.com>
9 * Johan Engelen
10 *
11 * Copyright (C) 1999-2007 Authors
12 *
13 * Released under GNU GPL, read the file 'COPYING' for more information
14 */
16 #ifdef HAVE_CONFIG_H
17 # include <config.h>
18 #endif
19 #include "display/guideline.h"
20 #include "helper/unit-menu.h"
21 #include "helper/units.h"
22 #include "desktop.h"
23 #include "document.h"
24 #include "sp-guide.h"
25 #include "sp-namedview.h"
26 #include "desktop-handles.h"
27 #include "event-context.h"
28 #include "widgets/desktop-widget.h"
29 #include "sp-metrics.h"
30 #include <glibmm/i18n.h>
31 #include "dialogs/dialog-events.h"
32 #include "message-context.h"
33 #include "xml/repr.h"
34 #include <2geom/point.h>
35 #include <2geom/angle.h>
36 #include "guidelinedialog.h"
38 namespace Inkscape {
39 namespace UI {
40 namespace Dialogs {
42 GuidelinePropertiesDialog::GuidelinePropertiesDialog(SPGuide *guide, SPDesktop *desktop)
43 : _desktop(desktop), _guide(guide),
44 _label_units(_("Unit:")),
45 _label_X(_("X:")),
46 _label_Y(_("Y:")),
47 _label_degrees(_("Angle (degrees):")),
48 _relative_toggle(_("Rela_tive change"), _("Move and/or rotate the guide relative to current settings")),
49 _adjustment_x(0.0, -1e6, 1e6, 1.0, 10.0, 10.0),
50 _adjustment_y(0.0, -1e6, 1e6, 1.0, 10.0, 10.0),
51 _adj_angle(0.0, -360, 360, 1.0, 10.0, 10.0),
52 _unit_selector(NULL), _mode(true), _oldpos(0.,0.), _oldangle(0.0)
53 {
54 }
56 GuidelinePropertiesDialog::~GuidelinePropertiesDialog() {
57 }
59 void GuidelinePropertiesDialog::showDialog(SPGuide *guide, SPDesktop *desktop) {
60 GuidelinePropertiesDialog dialog(guide, desktop);
61 dialog._setup();
62 dialog.run();
63 }
65 void GuidelinePropertiesDialog::_modeChanged()
66 {
67 _mode = !_relative_toggle.get_active();
68 if (!_mode) {
69 // relative
70 _spin_angle.set_value(0);
72 _spin_button_y.set_value(0);
73 _spin_button_x.set_value(0);
74 } else {
75 // absolute
76 _spin_angle.set_value(_oldangle);
78 SPUnit const &unit = *sp_unit_selector_get_unit(SP_UNIT_SELECTOR(_unit_selector->gobj()));
79 gdouble const val_y = sp_pixels_get_units(_oldpos[Geom::Y], unit);
80 _spin_button_y.set_value(val_y);
81 gdouble const val_x = sp_pixels_get_units(_oldpos[Geom::X], unit);
82 _spin_button_x.set_value(val_x);
83 }
84 }
86 void GuidelinePropertiesDialog::_onApply()
87 {
88 double deg_angle = _spin_angle.get_value();
89 if (!_mode)
90 deg_angle += _oldangle;
91 Geom::Point normal;
92 if ( deg_angle == 90. || deg_angle == 270. || deg_angle == -90. || deg_angle == -270.) {
93 normal = Geom::Point(1.,0.);
94 } else if ( deg_angle == 0. || deg_angle == 180. || deg_angle == -180.) {
95 normal = Geom::Point(0.,1.);
96 } else {
97 double rad_angle = Geom::deg_to_rad( deg_angle );
98 normal = Geom::rot90(Geom::Point::polar(rad_angle, 1.0));
99 }
100 sp_guide_set_normal(*_guide, normal, true);
102 SPUnit const &unit = *sp_unit_selector_get_unit(SP_UNIT_SELECTOR(_unit_selector->gobj()));
103 gdouble const raw_dist_x = _spin_button_x.get_value();
104 gdouble const points_x = sp_units_get_pixels(raw_dist_x, unit);
105 gdouble const raw_dist_y = _spin_button_y.get_value();
106 gdouble const points_y = sp_units_get_pixels(raw_dist_y, unit);
107 Geom::Point newpos(points_x, points_y);
108 if (!_mode)
109 newpos += _oldpos;
111 sp_guide_moveto(*_guide, newpos, true);
113 sp_document_done(SP_OBJECT_DOCUMENT(_guide), SP_VERB_NONE,
114 _("Set guide properties"));
115 }
117 void GuidelinePropertiesDialog::_onOK()
118 {
119 _onApply();
120 }
122 void GuidelinePropertiesDialog::_onDelete()
123 {
124 SPDocument *doc = SP_OBJECT_DOCUMENT(_guide);
125 sp_guide_remove(_guide);
126 sp_document_done(doc, SP_VERB_NONE,
127 _("Delete guide"));
128 }
130 void GuidelinePropertiesDialog::_response(gint response)
131 {
132 switch (response) {
133 case Gtk::RESPONSE_OK:
134 _onOK();
135 break;
136 case -12:
137 _onDelete();
138 break;
139 case Gtk::RESPONSE_CANCEL:
140 break;
141 case Gtk::RESPONSE_DELETE_EVENT:
142 break;
143 /* case GTK_RESPONSE_APPLY:
144 _onApply();
145 break;
146 */
147 default:
148 g_assert_not_reached();
149 }
150 }
152 void GuidelinePropertiesDialog::_setup() {
153 set_title(_("Guideline"));
154 add_button(Gtk::Stock::OK, Gtk::RESPONSE_OK);
155 add_button(Gtk::Stock::DELETE, -12);
156 add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
158 Gtk::VBox *mainVBox = get_vbox();
160 _layout_table.set_spacings(4);
161 _layout_table.resize (3, 4);
163 mainVBox->pack_start(_layout_table, false, false, 0);
165 _label_name.set_label("foo0");
166 _layout_table.attach(_label_name,
167 0, 3, 0, 1, Gtk::FILL, Gtk::FILL);
168 _label_name.set_alignment(0, 0.5);
170 _label_descr.set_label("foo1");
171 _layout_table.attach(_label_descr,
172 0, 3, 1, 2, Gtk::FILL, Gtk::FILL);
173 _label_descr.set_alignment(0, 0.5);
175 // indent
176 _layout_table.attach(*manage(new Gtk::Label(" ")),
177 0, 1, 2, 3, Gtk::FILL, Gtk::FILL, 10);
179 // mode radio button
180 _layout_table.attach(_relative_toggle,
181 1, 3, 9, 10, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
182 _relative_toggle.signal_toggled().connect(sigc::mem_fun(*this, &GuidelinePropertiesDialog::_modeChanged));
184 // unitmenu
185 /* fixme: We should allow percents here too, as percents of the canvas size */
186 GtkWidget *unit_selector = sp_unit_selector_new(SP_UNIT_ABSOLUTE | SP_UNIT_DEVICE);
187 sp_unit_selector_set_unit(SP_UNIT_SELECTOR(unit_selector), _desktop->namedview->doc_units);
188 _unit_selector = Gtk::manage(Glib::wrap(unit_selector));
190 // position spinbuttons
191 sp_unit_selector_add_adjustment(SP_UNIT_SELECTOR(unit_selector), GTK_ADJUSTMENT(_adjustment_x.gobj()));
192 sp_unit_selector_add_adjustment(SP_UNIT_SELECTOR(unit_selector), GTK_ADJUSTMENT(_adjustment_y.gobj()));
193 _spin_button_x.configure(_adjustment_x, 1.0 , 3);
194 _spin_button_x.set_numeric();
195 _spin_button_y.configure(_adjustment_y, 1.0 , 3);
196 _spin_button_y.set_numeric();
197 _layout_table.attach(_label_X,
198 1, 2, 4, 5, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
199 _layout_table.attach(_spin_button_x,
200 2, 3, 4, 5, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
201 _layout_table.attach(_label_Y,
202 1, 2, 5, 6, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
203 _layout_table.attach(_spin_button_y,
204 2, 3, 5, 6, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
205 gtk_signal_connect_object(GTK_OBJECT(_spin_button_x.gobj()), "activate",
206 GTK_SIGNAL_FUNC(gtk_window_activate_default),
207 gobj());
209 _layout_table.attach(_label_units,
210 1, 2, 6, 7, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
211 _layout_table.attach(*_unit_selector,
212 2, 3, 6, 7, Gtk::FILL, Gtk::FILL);
214 // angle spinbutton
215 _spin_angle.configure(_adj_angle, 5.0 , 3);
216 _spin_angle.set_numeric();
217 _spin_angle.show();
218 _layout_table.attach(_label_degrees,
219 1, 2, 8, 9, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
220 _layout_table.attach(_spin_angle,
221 2, 3, 8, 9, Gtk::EXPAND | Gtk::FILL, Gtk::FILL);
224 // dialog
225 set_default_response(Gtk::RESPONSE_OK);
226 signal_response().connect(sigc::mem_fun(*this, &GuidelinePropertiesDialog::_response));
228 // initialize dialog
229 _oldpos = _guide->point_on_line;
230 if (_guide->is_vertical()) {
231 _oldangle = 90;
232 } else if (_guide->is_horizontal()) {
233 _oldangle = 0;
234 } else {
235 _oldangle = Geom::rad_to_deg( std::atan2( - _guide->normal_to_line[Geom::X], _guide->normal_to_line[Geom::Y] ) );
236 }
238 {
239 Inkscape::XML::Node *repr = SP_OBJECT_REPR (_guide);
240 const gchar *guide_id = repr->attribute("id");
241 gchar *label = g_strdup_printf(_("Guideline ID: %s"), guide_id);
242 _label_name.set_label(label);
243 g_free(label);
244 }
245 {
246 gchar *guide_description = sp_guide_description(_guide);
247 gchar *label = g_strdup_printf(_("Current: %s"), guide_description);
248 g_free(guide_description);
249 _label_descr.set_markup(label);
250 g_free(label);
251 }
253 _modeChanged(); // sets values of spinboxes.
255 if ( _oldangle == 90. || _oldangle == 270. || _oldangle == -90. || _oldangle == -270.) {
256 _spin_button_x.grab_focus();
257 _spin_button_x.select_region(0, 20);
258 } else if ( _oldangle == 0. || _oldangle == 180. || _oldangle == -180.) {
259 _spin_button_y.grab_focus();
260 _spin_button_y.select_region(0, 20);
261 } else {
262 _spin_angle.grab_focus();
263 _spin_angle.select_region(0, 20);
264 }
266 set_position(Gtk::WIN_POS_MOUSE);
268 show_all_children();
269 set_modal(true);
270 _desktop->setWindowTransient (gobj());
271 property_destroy_with_parent() = true;
272 }
274 }
275 }
276 }
278 /*
279 Local Variables:
280 mode:c++
281 c-file-style:"stroustrup"
282 c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
283 indent-tabs-mode:nil
284 fill-column:99
285 End:
286 */
287 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=99 :