1 //
2 // ResizeCanvasDialog.cs
3 //
4 // Author:
5 //       Jonathan Pobst <monkey@jpobst.com>
6 //
7 // Copyright (c) 2010 Jonathan Pobst
8 //
9 // Permission is hereby granted, free of charge, to any person obtaining a copy
10 // of this software and associated documentation files (the "Software"), to deal
11 // in the Software without restriction, including without limitation the rights
12 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13 // copies of the Software, and to permit persons to whom the Software is
14 // furnished to do so, subject to the following conditions:
15 //
16 // The above copyright notice and this permission notice shall be included in
17 // all copies or substantial portions of the Software.
18 //
19 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
25 // THE SOFTWARE.
26 
27 using System;
28 using Gtk;
29 using Mono.Unix;
30 using Pinta.Core;
31 
32 namespace Pinta
33 {
34 	public class ResizeCanvasDialog : Dialog
35 	{
36 		private RadioButton percentageRadio;
37 		private RadioButton absoluteRadio;
38 		private SpinButton percentageSpinner;
39 		private SpinButton widthSpinner;
40 		private SpinButton heightSpinner;
41 		private CheckButton aspectCheckbox;
42 
43         private Button NWButton;
44         private Button NButton;
45         private Button NEButton;
46         private Button WButton;
47         private Button EButton;
48         private Button CenterButton;
49         private Button SWButton;
50         private Button SButton;
51         private Button SEButton;
52 
53 		private bool value_changing;
54 		private Anchor anchor;
55 
ResizeCanvasDialog()56 		public ResizeCanvasDialog () : base (Catalog.GetString ("Resize Canvas"), PintaCore.Chrome.MainWindow,
57 		                                     DialogFlags.Modal,
58 											 Gtk.Stock.Cancel, Gtk.ResponseType.Cancel,
59 											 Gtk.Stock.Ok, Gtk.ResponseType.Ok)
60 		{
61 			Build ();
62 
63 			Icon = PintaCore.Resources.GetIcon ("Menu.Image.CanvasSize.png");
64 
65 			aspectCheckbox.Active = true;
66 
67 			widthSpinner.Value = PintaCore.Workspace.ImageSize.Width;
68 			heightSpinner.Value = PintaCore.Workspace.ImageSize.Height;
69 
70 			percentageRadio.Toggled += new EventHandler (percentageRadio_Toggled);
71 			absoluteRadio.Toggled += new EventHandler (absoluteRadio_Toggled);
72 			percentageRadio.Toggle ();
73 
74 			percentageSpinner.Value = 100;
75 			percentageSpinner.ValueChanged += new EventHandler (percentageSpinner_ValueChanged);
76 
77 			widthSpinner.ValueChanged += new EventHandler (widthSpinner_ValueChanged);
78 			heightSpinner.ValueChanged += new EventHandler (heightSpinner_ValueChanged);
79 
80 			NWButton.Clicked += HandleNWButtonClicked;
81 			NButton.Clicked += HandleNButtonClicked;
82 			NEButton.Clicked += HandleNEButtonClicked;
83 			WButton.Clicked += HandleWButtonClicked;
84 			CenterButton.Clicked += HandleCenterButtonClicked;
85 			EButton.Clicked += HandleEButtonClicked;
86 			SWButton.Clicked += HandleSWButtonClicked;
87 			SButton.Clicked += HandleSButtonClicked;
88 			SEButton.Clicked += HandleSEButtonClicked;
89 
90 			SetAnchor (Anchor.Center);
91 			AlternativeButtonOrder = new int[] { (int) Gtk.ResponseType.Ok, (int) Gtk.ResponseType.Cancel };
92 			DefaultResponse = Gtk.ResponseType.Ok;
93 
94 			widthSpinner.ActivatesDefault = true;
95 			heightSpinner.ActivatesDefault = true;
96 			percentageSpinner.ActivatesDefault = true;
97 			percentageSpinner.GrabFocus();
98 		}
99 
100 		#region Public Methods
SaveChanges()101 		public void SaveChanges ()
102 		{
103 			PintaCore.Workspace.ResizeCanvas (widthSpinner.ValueAsInt, heightSpinner.ValueAsInt, anchor, null);
104 		}
105 		#endregion
106 
107 		#region Private Methods
heightSpinner_ValueChanged(object sender, EventArgs e)108 		private void heightSpinner_ValueChanged (object sender, EventArgs e)
109 		{
110 			if (value_changing)
111 				return;
112 
113 			if (aspectCheckbox.Active) {
114 				value_changing = true;
115 				widthSpinner.Value = (int)((heightSpinner.Value * PintaCore.Workspace.ImageSize.Width) / PintaCore.Workspace.ImageSize.Height);
116 				value_changing = false;
117 			}
118 		}
119 
widthSpinner_ValueChanged(object sender, EventArgs e)120 		private void widthSpinner_ValueChanged (object sender, EventArgs e)
121 		{
122 			if (value_changing)
123 				return;
124 
125 			if (aspectCheckbox.Active) {
126 				value_changing = true;
127 				heightSpinner.Value = (int)((widthSpinner.Value * PintaCore.Workspace.ImageSize.Height) / PintaCore.Workspace.ImageSize.Width);
128 				value_changing = false;
129 			}
130 		}
131 
percentageSpinner_ValueChanged(object sender, EventArgs e)132 		private void percentageSpinner_ValueChanged (object sender, EventArgs e)
133 		{
134 			widthSpinner.Value = (int)(PintaCore.Workspace.ImageSize.Width * (percentageSpinner.ValueAsInt / 100f));
135 			heightSpinner.Value = (int)(PintaCore.Workspace.ImageSize.Height * (percentageSpinner.ValueAsInt / 100f));
136 		}
137 
absoluteRadio_Toggled(object sender, EventArgs e)138 		private void absoluteRadio_Toggled (object sender, EventArgs e)
139 		{
140 			RadioToggle ();
141 		}
142 
percentageRadio_Toggled(object sender, EventArgs e)143 		private void percentageRadio_Toggled (object sender, EventArgs e)
144 		{
145 			RadioToggle ();
146 		}
147 
RadioToggle()148 		private void RadioToggle ()
149 		{
150 			if (percentageRadio.Active) {
151 				percentageSpinner.Sensitive = true;
152 
153 				widthSpinner.Sensitive = false;
154 				heightSpinner.Sensitive = false;
155 				aspectCheckbox.Sensitive = false;
156 			} else {
157 				percentageSpinner.Sensitive = false;
158 
159 				widthSpinner.Sensitive = true;
160 				heightSpinner.Sensitive = true;
161 				aspectCheckbox.Sensitive = true;
162 			}
163 		}
164 
HandleSEButtonClicked(object sender, EventArgs e)165 		private void HandleSEButtonClicked (object sender, EventArgs e)
166 		{
167 			SetAnchor (Anchor.SE);
168 		}
169 
HandleSButtonClicked(object sender, EventArgs e)170 		private void HandleSButtonClicked (object sender, EventArgs e)
171 		{
172 			SetAnchor (Anchor.S);
173 		}
174 
HandleSWButtonClicked(object sender, EventArgs e)175 		private void HandleSWButtonClicked (object sender, EventArgs e)
176 		{
177 			SetAnchor (Anchor.SW);
178 		}
179 
HandleEButtonClicked(object sender, EventArgs e)180 		private void HandleEButtonClicked (object sender, EventArgs e)
181 		{
182 			SetAnchor (Anchor.E);
183 		}
184 
HandleCenterButtonClicked(object sender, EventArgs e)185 		private void HandleCenterButtonClicked (object sender, EventArgs e)
186 		{
187 			SetAnchor (Anchor.Center);
188 		}
189 
HandleWButtonClicked(object sender, EventArgs e)190 		private void HandleWButtonClicked (object sender, EventArgs e)
191 		{
192 			SetAnchor (Anchor.W);
193 		}
194 
HandleNEButtonClicked(object sender, EventArgs e)195 		private void HandleNEButtonClicked (object sender, EventArgs e)
196 		{
197 			SetAnchor (Anchor.NE);
198 		}
199 
HandleNButtonClicked(object sender, EventArgs e)200 		private void HandleNButtonClicked (object sender, EventArgs e)
201 		{
202 			SetAnchor (Anchor.N);
203 		}
204 
HandleNWButtonClicked(object sender, EventArgs e)205 		private void HandleNWButtonClicked (object sender, EventArgs e)
206 		{
207 			SetAnchor (Anchor.NW);
208 		}
209 
SetAnchor(Anchor anchor)210 		private void SetAnchor (Anchor anchor)
211 		{
212 			this.anchor = anchor;
213 
214 			NWButton.Image = null;
215 			NButton.Image = null;
216 			NEButton.Image = null;
217 			WButton.Image = null;
218 			EButton.Image = null;
219 			CenterButton.Image = null;
220 			SWButton.Image = null;
221 			SButton.Image = null;
222 			SEButton.Image = null;
223 
224 			switch (anchor) {
225 
226 			case Anchor.NW:
227 				NWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
228 				NButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.RightArrow.png"));
229 				WButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.DownArrow.png"));
230 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthEast.png"));
231 				break;
232 
233 			case Anchor.N:
234 				NWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.LeftArrow.png"));
235 				NButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
236 				NEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.RightArrow.png"));
237 				WButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthWest.png"));
238 				EButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthEast.png"));
239 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.DownArrow.png"));
240 				break;
241 
242 			case Anchor.NE:
243 				NEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
244 				NButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.LeftArrow.png"));
245 				EButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.DownArrow.png"));
246 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthWest.png"));
247 				break;
248 
249 			case Anchor.W:
250 				NWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.UpArrow.png"));
251 				NButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthEast.png"));
252 				SWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.DownArrow.png"));
253 				WButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
254 				SButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthEast.png"));
255 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.RightArrow.png"));
256 				break;
257 
258 			case Anchor.Center:
259 				NWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthWest.png"));
260 				NButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.UpArrow.png"));
261 				NEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthEast.png"));
262 				WButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.LeftArrow.png"));
263 				EButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.RightArrow.png"));
264 				SWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthWest.png"));
265 				SButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.DownArrow.png"));
266 				SEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthEast.png"));
267 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
268 				break;
269 
270 			case Anchor.E:
271 				NEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.UpArrow.png"));
272 				NButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthWest.png"));
273 				SEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.DownArrow.png"));
274 				EButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
275 				SButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.SouthWest.png"));
276 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.LeftArrow.png"));
277 				break;
278 
279 			case Anchor.SW:
280 				SWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
281 				SButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.RightArrow.png"));
282 				WButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.UpArrow.png"));
283 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthEast.png"));
284 				break;
285 
286 			case Anchor.S:
287 				SWButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.LeftArrow.png"));
288 				SButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
289 				SEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.RightArrow.png"));
290 				WButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthWest.png"));
291 				EButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthEast.png"));
292 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.UpArrow.png"));
293 				break;
294 
295 			case Anchor.SE:
296 				SEButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.Image.png"));
297 				SButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.LeftArrow.png"));
298 				EButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.UpArrow.png"));
299 				CenterButton.Image = new Gtk.Image (PintaCore.Resources.GetIcon ("ResizeCanvas.NorthWest.png"));
300 				break;
301 			}
302 		}
303 
Build()304 		private void Build()
305         {
306 			Icon = PintaCore.Resources.GetIcon ("Menu.Image.CanvasSize.png");
307 
308 			WindowPosition = WindowPosition.CenterOnParent;
309 
310 			DefaultWidth = 300;
311 			DefaultHeight = 200;
312 
313 			percentageRadio = new RadioButton (Catalog.GetString ("By percentage:"));
314 			absoluteRadio = new RadioButton (percentageRadio, Catalog.GetString ("By absolute size:"));
315 
316 			percentageSpinner = new SpinButton (1, 1000, 1);
317 			widthSpinner = new SpinButton (1, 10000, 1);
318 			heightSpinner = new SpinButton (1, 10000, 1);
319 
320 			aspectCheckbox = new CheckButton (Catalog.GetString ("Maintain aspect ratio"));
321 
322 			const int spacing = 6;
323 			var main_vbox = new VBox () { Spacing = spacing, BorderWidth = 12 };
324 
325 			var hbox_percent = new HBox () { Spacing = spacing };
326 			hbox_percent.PackStart (percentageRadio, true, true, 0);
327 			hbox_percent.PackStart (percentageSpinner, false, false, 0);
328 			hbox_percent.PackEnd (new Label ("%"), false, false, 0);
329 			main_vbox.PackStart (hbox_percent, false, false, 0);
330 
331 			main_vbox.PackStart (absoluteRadio, false, false, 0);
332 
333 			var hbox_width = new HBox () { Spacing = spacing };
334 			hbox_width.PackStart (new Label (Catalog.GetString ("Width:")), false, false, 0);
335 			hbox_width.PackStart (widthSpinner, false, false, 0);
336 			hbox_width.PackStart (new Label (Catalog.GetString ("pixels")), false, false, 0);
337 			main_vbox.PackStart (hbox_width, false, false, 0);
338 
339 			var hbox_height = new HBox () { Spacing = spacing };
340 			hbox_height.PackStart (new Label (Catalog.GetString ("Height:")), false, false, 0);
341 			hbox_height.PackStart (heightSpinner, false, false, 0);
342 			hbox_height.PackStart (new Label (Catalog.GetString ("pixels")), false, false, 0);
343 			main_vbox.PackStart (hbox_height, false, false, 0);
344 
345 			main_vbox.PackStart (aspectCheckbox, false, false, 0);
346 			main_vbox.PackStart (new HSeparator (), false, false, 0);
347 
348 			var align_label = new Label (Catalog.GetString ("Anchor:")) { Xalign = 0 };
349 			main_vbox.PackStart (align_label, false, false, 0);
350 
351 			NWButton = CreateAnchorButton ();
352 			NButton = CreateAnchorButton ();
353 			NEButton = CreateAnchorButton ();
354 			WButton = CreateAnchorButton ();
355 			EButton = CreateAnchorButton ();
356 			CenterButton = CreateAnchorButton ();
357 			SWButton = CreateAnchorButton ();
358 			SButton = CreateAnchorButton ();
359 			SEButton = CreateAnchorButton ();
360 
361 			var grid = new Table (3, 3, false) { RowSpacing = spacing, ColumnSpacing = spacing };
362 			grid.Attach (NWButton, 0, 1, 0, 1);
363 			grid.Attach (NButton, 1, 2, 0, 1);
364 			grid.Attach (NEButton, 2, 3, 0, 1);
365 			grid.Attach (WButton, 0, 1, 1, 2);
366 			grid.Attach (CenterButton, 1, 2, 1, 2);
367 			grid.Attach (EButton, 2, 3, 1, 2);
368 			grid.Attach (SWButton, 0, 1, 2, 3);
369 			grid.Attach (SButton, 1, 2, 2, 3);
370 			grid.Attach (SEButton, 2, 3, 2, 3);
371 
372 			var grid_align = new Alignment (0.5f, 0.5f, 0, 0);
373 			grid_align.Add (grid);
374 
375 			main_vbox.PackStart (grid_align, false, false, 0);
376 
377 			VBox.BorderWidth = 2;
378 			VBox.Add (main_vbox);
379 
380 			ShowAll ();
381 		}
382 
CreateAnchorButton()383 		private Button CreateAnchorButton()
384         {
385 			return new Button () { WidthRequest = 30, HeightRequest = 30 };
386         }
387 		#endregion
388 	}
389 }
390 
391