7dc4f9638af0d93964b041cd257df0f35acd901f
[gregoa/zavai.git] / src / app_main.vala
1 /*
2  * app_main - zavai main status display
3  *
4  * Copyright (C) 2009  Enrico Zini <enrico@enricozini.org>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  */
20
21 using GLib;
22
23 namespace zavai {
24 namespace ui {
25 namespace main {
26
27 /*
28 public class StatusBar : Gtk.HBox
29 {
30     void StatusBar()
31     {
32     }
33 }
34 */
35
36 public class Clock : Gtk.VBox
37 {
38     protected Gtk.Label l_date;
39     protected Gtk.Label l_time;
40     protected Gtk.Label l_deadline;
41     protected time_t last_time;
42     protected zavai.clock.SourceType last_time_type;
43     protected time_t last_deadline;
44     protected string last_deadline_label;
45
46     public Clock()
47     {
48         last_time = time_t();
49         last_time_type = zavai.clock.SourceType.SYSTEM;
50         last_deadline = 0;
51         last_deadline_label = "";
52
53         l_date = new Gtk.Label("--");
54         l_date.modify_font(Pango.FontDescription.from_string("Sans 40"));
55         pack_start(l_date, false, false, 0);
56         l_time = new Gtk.Label("--:--");
57         l_time.modify_font(Pango.FontDescription.from_string("Sans 60"));
58         pack_start(l_time, false, false, 0);
59         l_deadline = new Gtk.Label("");
60         l_deadline.modify_font(Pango.FontDescription.from_string("Sans 30"));
61         l_deadline.set_justify(Gtk.Justification.CENTER);
62         pack_start(l_deadline, false, false, 0);
63
64         zavai.clock.clock.minute_changed += on_minute_changed;
65         zavai.clock.clock.schedule_changed += on_schedule_changed;
66
67         zavai.clock.clock.request("ui.main.clock");
68     }
69
70     private void on_schedule_changed()
71     {
72         zavai.clock.Alarm a = zavai.clock.clock.next_alarm();
73         if (a == null)
74         {
75             last_deadline = 0;
76             last_deadline_label = "";
77         }
78         else
79         {
80             last_deadline = a.deadline;
81             last_deadline_label = a.label;
82         }
83         on_minute_changed((long)last_time, last_time_type);
84     }
85
86     private void on_minute_changed(long ts, zavai.clock.SourceType type)
87     {
88         last_time = (time_t)ts;
89         last_time_type = type;
90
91         string typetag = "unknown";
92         switch (type)
93         {
94             case zavai.clock.SourceType.GPS:
95                 typetag = "gps";
96                 break;
97             case zavai.clock.SourceType.SYSTEM:
98                 typetag = "sys";
99                 break;
100         }
101                 
102         var t = Time.local((time_t)ts);
103         l_date.set_text(t.format("%a %d %b"));
104         l_time.set_text("%2d:%02d (%s)".printf(t.hour, t.minute, typetag));
105
106         if (last_deadline == 0)
107             l_deadline.set_text("");
108         else
109         {
110             int remaining = (int)(last_deadline - last_time);
111             int hours = remaining / 3600;
112             int minutes = (remaining % 3600) / 60;
113             if (hours == 0 && minutes == 0)
114                 l_deadline.set_text(last_deadline_label + "\nanytime now");
115             else
116                 l_deadline.set_text("%s\non %02dh %02dm".printf(last_deadline_label, hours, minutes));
117         }
118     }
119 }
120
121 public class Status : Applet
122 {
123     public Gtk.HBox status_icons;
124     public Clock clock;
125     public AppletPushLink menu;
126
127         public Status(string label)
128         {
129                 _label = label;
130         status_icons = new Gtk.HBox(false, 0);
131         clock = new Clock();
132         menu = new AppletPushLink("menu.main");
133
134                 pack_start(status_icons, false, false, 0);
135                 pack_start(clock, false, false, 0);
136                 pack_end(menu, false, false, 0);
137         }
138 }
139
140 public class IncDec : Gtk.HButtonBox
141 {
142     protected Gtk.Button b_dec;
143     protected Gtk.Button b_inc;
144
145     public signal void tweaked(IncDec id, int amount);
146
147     public IncDec()
148     {
149         b_dec = new Gtk.Button.with_label("-");
150         b_inc = new Gtk.Button.with_label("+");
151         pack_start(b_dec, false, false, 0);
152         pack_start(b_inc, false, false, 0);
153         b_dec.clicked += on_clicked;
154         b_inc.clicked += on_clicked;
155     }
156
157     protected void on_clicked(Gtk.Button b)
158     {
159         tweaked(this, b == b_dec ? -1 : 1);
160     }
161 }
162
163 public class LabelEntry : Gtk.Entry
164 {
165     public LabelEntry()
166     {
167     }
168 }
169
170 public class AddAbsoluteDeadline : Applet
171 {
172     protected LabelEntry dl_label;
173     protected Gtk.Label dl_day;
174     protected IncDec dl_day_tweak;
175     protected Gtk.Label dl_hour;
176     protected IncDec dl_hour_tweak;
177     protected Gtk.Label dl_min;
178     protected IncDec dl_min_tweak;
179     protected time_t dl_time;
180     protected Gtk.Button dl_submit;
181
182     public AddAbsoluteDeadline()
183     {
184         _label = "Add absolute deadline";
185         dl_time = 0;
186
187         dl_label = new LabelEntry();
188         dl_label.changed += on_label_changed;
189         var hbox = new Gtk.HBox(false, 0);
190         hbox.pack_start(new Gtk.Label("Label: "), false, false, 0);
191         hbox.pack_start(dl_label, true, true, 0);
192         pack_start(hbox, false, false, 0);
193
194         dl_day = new Gtk.Label("");
195         dl_day_tweak = new IncDec();
196         dl_day_tweak.tweaked += on_tweak;
197         hbox = new Gtk.HBox(false, 0);
198         hbox.pack_start(new Gtk.Label("Day: "), false, false, 0);
199         hbox.pack_start(dl_day, true, true, 0);
200         hbox.pack_start(dl_day_tweak, false, false, 0);
201         pack_start(hbox, false, false, 0);
202
203         dl_hour = new Gtk.Label("");
204         dl_hour_tweak = new IncDec();
205         dl_hour_tweak.tweaked += on_tweak;
206         hbox = new Gtk.HBox(false, 0);
207         hbox.pack_start(new Gtk.Label("Hour: "), false, false, 0);
208         hbox.pack_start(dl_hour, true, true, 0);
209         hbox.pack_start(dl_hour_tweak, false, false, 0);
210         pack_start(hbox, false, false, 0);
211
212         dl_min = new Gtk.Label("");
213         dl_min_tweak = new IncDec();
214         dl_min_tweak.tweaked += on_tweak;
215         hbox = new Gtk.HBox(false, 0);
216         hbox.pack_start(new Gtk.Label("Minute: "), false, false, 0);
217         hbox.pack_start(dl_min, true, true, 0);
218         hbox.pack_start(dl_min_tweak, false, false, 0);
219         pack_start(hbox, false, false, 0);
220
221         dl_submit = new Gtk.Button.with_label("Activate");
222         dl_submit.set_sensitive(false);
223         dl_submit.clicked += on_submit;
224         button_box.pack_start(dl_submit, true, true, 0);
225     }
226
227         public override void start()
228     {
229         dl_time = time_t();
230         dl_label.set_text("");
231         update();
232     }
233
234     protected void update()
235     {
236         Time t = Time.local(dl_time);
237         dl_day.set_text(t.format("%a %d %b"));
238         dl_hour.set_text(t.format("%H"));
239         dl_min.set_text(t.format("%M"));
240         dl_submit.set_sensitive(dl_label.text == "" ? false : true);
241     }
242
243     protected void on_tweak(IncDec id, int amount)
244     {
245         time_t old = dl_time;
246         if (id == dl_day_tweak)
247             dl_time += amount * 3600 * 24;
248         else if (id == dl_hour_tweak)
249             dl_time += amount * 3600;
250         else if (id == dl_min_tweak)
251             dl_time += amount * 60;
252         time_t now = time_t();
253         if (dl_time < now)
254             dl_time = old;
255         update();
256     }
257
258     protected void on_submit(Gtk.Button b)
259     {
260         zavai.clock.clock.schedule(new zavai.clock.Alarm(dl_time, dl_label.text));
261         back();
262     }
263
264     protected void on_label_changed(LabelEntry e)
265     {
266         update();
267     }
268 }
269
270 public class AddRelativeDeadline : Applet
271 {
272     public AddRelativeDeadline()
273     {
274         _label = "Add relative deadline";
275     }
276 }
277
278 public class AddDailyDeadline : Applet
279 {
280     public AddDailyDeadline()
281     {
282         _label = "Add daily deadline";
283     }
284 }
285
286 Status status;
287 AddAbsoluteDeadline aad;
288 AddRelativeDeadline ard;
289 AddDailyDeadline add;
290
291 public void init()
292 {
293     status = new Status("Zavai");
294     zavai.registry.register_applet("zavai.status", status);
295
296     aad = new AddAbsoluteDeadline();
297     zavai.registry.register_applet("clock.addabsolute", aad);
298     ard = new AddRelativeDeadline();
299     zavai.registry.register_applet("clock.addrelative", ard);
300     add = new AddDailyDeadline();
301     zavai.registry.register_applet("clock.adddaily", add);
302
303     var menu_misc = zavai.registry.getmenu("menu.misc");
304         menu_misc.add_applet("clock.addabsolute");
305         menu_misc.add_applet("clock.addrelative");
306         menu_misc.add_applet("clock.adddaily");
307 }
308
309 }
310 }
311 }