L10N: Updated Persian Translation
[gcalctool.git] / src / math-converter.vala
blob15eba6fec3c7cab64f39ecb73126bd76f4d3bec3
1 /*
2 * Copyright (C) 2008-2012 Robert Ancell
4 * This program is free software: you can redistribute it and/or modify it under
5 * the terms of the GNU General Public License as published by the Free Software
6 * Foundation, either version 2 of the License, or (at your option) any later
7 * version. See http://www.gnu.org/copyleft/gpl.html the full text of the
8 * license.
9 */
11 public class MathConverter : Gtk.Box
13 private MathEquation equation;
15 private string category;
17 private Gtk.ComboBox from_combo;
18 private Gtk.ComboBox to_combo;
20 private Gtk.Label result_label;
22 public signal void changed ();
24 public MathConverter (MathEquation equation)
26 Object (orientation: Gtk.Orientation.HORIZONTAL);
27 this.equation = equation;
29 spacing = 6;
31 var hbox = new Gtk.Box (Gtk.Orientation.HORIZONTAL, 0);
32 hbox.show ();
33 pack_start (hbox, false, true, 0);
35 from_combo = new Gtk.ComboBox ();
37 var renderer = new Gtk.CellRendererText ();
38 from_combo.pack_start (renderer, true);
39 from_combo.add_attribute (renderer, "text", 0);
40 from_combo.set_cell_data_func (renderer, from_cell_data_func);
41 from_combo.changed.connect (from_combobox_changed_cb);
42 from_combo.show ();
43 hbox.pack_start (from_combo, false, true, 0);
45 var label = new Gtk.Label (/* Label that is displayed between the two conversion combo boxes, e.g. "[degrees] in [radians]" */
46 _(" in "));
47 label.show ();
48 hbox.pack_start (label, false, true, 5);
50 to_combo = new Gtk.ComboBox ();
51 renderer = new Gtk.CellRendererText ();
52 to_combo.pack_start (renderer, true);
53 to_combo.add_attribute (renderer, "text", 0);
54 to_combo.changed.connect (to_combobox_changed_cb);
55 to_combo.show ();
56 hbox.pack_start (to_combo, false, true, 0);
58 var swap_button = new Gtk.Button.with_label ("⇆");
59 swap_button.set_tooltip_text (/* Tooltip for swap conversion button */
60 _("Switch conversion units"));
61 swap_button.set_relief (Gtk.ReliefStyle.NONE);
62 swap_button.clicked.connect (swap_button_clicked_cb);
63 swap_button.show ();
64 hbox.pack_start (swap_button, false, true, 0);
66 result_label = new Gtk.Label ("");
67 result_label.set_alignment (1.0f, 0.5f);
68 result_label.sensitive = false;
69 result_label.show ();
70 pack_start (result_label, true, true, 0);
72 CurrencyManager.get_default ().updated.connect (() => { update_result_label (); });
73 equation.notify["display"].connect ((pspec) => { update_result_label (); });
75 update_from_model ();
78 public void set_category (string? category)
80 if (this.category == category)
81 return;
82 this.category = category;
84 update_from_model ();
87 public string get_category ()
89 return category;
92 public void set_conversion (/*string category,*/ string unit_a, string unit_b)
94 var ua = UnitManager.get_default ().get_unit_by_name (unit_a);
95 var ub = UnitManager.get_default ().get_unit_by_name (unit_b);
96 if (ua == null || ub == null)
98 /* Select the first unit */
99 var model = from_combo.get_model ();
100 Gtk.TreeIter iter;
101 if (model.get_iter_first (out iter))
103 Gtk.TreeIter child_iter;
104 while (model.iter_children (out child_iter, iter))
105 iter = child_iter;
106 from_combo.set_active_iter (iter);
108 return;
111 set_active_unit (from_combo, null, ua);
112 set_active_unit (to_combo, null, ub);
115 public void get_conversion (out Unit from_unit, out Unit to_unit)
117 Gtk.TreeIter from_iter, to_iter;
119 from_combo.get_active_iter (out from_iter);
120 to_combo.get_active_iter (out to_iter);
122 from_combo.get_model ().get (from_iter, 2, out from_unit, -1);
123 to_combo.get_model ().get (to_iter, 2, out to_unit, -1);
126 private void update_result_label ()
128 var x = equation.number;
129 if (x == null)
130 return;
132 var z = convert_equation (x);
133 result_label.sensitive = z != null;
134 if (z != null)
136 Unit source_unit, target_unit;
137 get_conversion (out source_unit, out target_unit);
139 var source_text = source_unit.format (x);
140 var target_text = target_unit.format (z);
141 result_label.set_text ("%s = %s".printf (source_text, target_text));
145 private void update_from_model ()
147 var from_model = new Gtk.TreeStore (3, typeof (string), typeof (UnitCategory), typeof (Unit));
149 if (category == null)
151 var categories = UnitManager.get_default ().get_categories ();
152 foreach (var category in categories)
154 Gtk.TreeIter parent;
155 from_model.append (out parent, null);
156 from_model.set (parent, 0, category.display_name, 1, category, -1);
158 foreach (var unit in category.get_units ())
160 Gtk.TreeIter iter;
161 from_model.append (out iter, parent);
162 from_model.set (iter, 0, unit.display_name, 1, category, 2, unit, -1);
166 else
168 var c = UnitManager.get_default ().get_category (category);
169 foreach (var unit in c.get_units ())
171 Gtk.TreeIter iter;
172 from_model.append (out iter, null);
173 from_model.set (iter, 0, unit.display_name, 1, c, 2, unit, -1);
177 from_combo.model = from_model;
180 private bool iter_is_unit (Gtk.TreeModel model, Gtk.TreeIter iter, Unit unit)
182 Unit u;
183 model.get (iter, 2, out u, -1);
184 return u == unit;
187 private bool set_active_unit (Gtk.ComboBox combo, Gtk.TreeIter? iter, Unit unit)
189 var model = combo.get_model ();
190 if (iter != null && iter_is_unit (model, iter, unit))
192 combo.set_active_iter (iter);
193 return true;
196 Gtk.TreeIter child_iter;
197 if (!model.iter_children (out child_iter, iter))
198 return false;
202 if (set_active_unit (combo, child_iter, unit))
203 return true;
204 } while (model.iter_next (ref child_iter));
206 return false;
209 private void from_combobox_changed_cb ()
211 var model = from_combo.get_model ();
212 Gtk.TreeIter iter;
213 if (!from_combo.get_active_iter (out iter))
214 return;
215 UnitCategory category;
216 Unit unit;
217 model.get (iter, 1, out category, 2, out unit, -1);
219 /* Set the to combobox to be the list of units can be converted to */
220 var to_model = new Gtk.ListStore (3, typeof (string), typeof (UnitCategory), typeof (Unit));
221 foreach (var u in category.get_units ())
223 if (u == unit)
224 continue;
225 to_model.append (out iter);
226 to_model.set (iter, 0, u.display_name, 1, category, 2, u, -1);
228 to_combo.model = to_model;
230 /* Select the first possible unit */
231 to_combo.set_active (0);
234 private void to_combobox_changed_cb ()
236 /* Conversion must have changed */
237 update_result_label ();
238 changed ();
241 private void from_cell_data_func (Gtk.CellLayout cell_layout, Gtk.CellRenderer cell, Gtk.TreeModel tree_model, Gtk.TreeIter iter)
243 cell.set ("sensitive", !tree_model.iter_has_child (iter));
246 private void swap_button_clicked_cb ()
248 var x = equation.number;
249 if (x != null)
251 var z = convert_equation (x);
252 if (z != null)
253 equation.set_number (z);
256 Unit from_unit, to_unit;
257 get_conversion (out from_unit, out to_unit);
258 set_active_unit (from_combo, null, to_unit);
259 set_active_unit (to_combo, null, from_unit);
261 update_result_label ();
264 private Number? convert_equation (Number x)
266 Gtk.TreeIter from_iter, to_iter;
267 if (!from_combo.get_active_iter (out from_iter))
268 return null;
269 if (!to_combo.get_active_iter (out to_iter))
270 return null;
272 UnitCategory category;
273 Unit source_unit, target_unit;
274 from_combo.model.get (from_iter, 1, out category, 2, out source_unit, -1);
275 to_combo.model.get (to_iter, 2, out target_unit, -1);
277 return category.convert (x, source_unit, target_unit);