1 /*
2  * GTimer
3  *
4  * Copyright:
5  *	(C) 1999 Craig Knudsen, cknudsen@cknudsen.com
6  *	See accompanying file "COPYING".
7  *
8  *	This program is free software; you can redistribute it and/or
9  *	modify it under the terms of the GNU General Public License
10  *	as published by the Free Software Foundation; either version 2
11  *	of the License, or (at your option) any later version.
12  *
13  *	This program is distributed in the hope that it will be useful,
14  *	but WITHOUT ANY WARRANTY; without even the implied warranty of
15  *	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  *	GNU General Public License for more details.
17  *
18  *	You should have received a copy of the GNU General Public License
19  *	along with this program; if not, write to the
20  *	Free Software Foundation, Inc., 59 Temple Place,
21  *	Suite 330, Boston, MA  02111-1307, USA
22  *
23  * Description:
24  *	Helps you keep track of time spent on different tasks.
25  *
26  * Author:
27  *	Craig Knudsen, cknudsen@cknudsen.com, http://www.cknudsen.com
28  *
29  * Home Page:
30  *	http://www.cknudsen.com/gtimer/
31  *
32  * History:
33  *      07-Sep-2007	Updated to use GtkTreeView
34  *	09-Mar-2000	Updated call to create_confirm_window()
35  *	18-Mar-1999	Internationalization
36  *	16-Mar-1999	Add back support for GTK 1.0
37  *	16-Feb-1999	Created unhide window
38  *
39  ****************************************************************************/
40 
41 
42 #include <stdio.h>
43 #include <stdlib.h>
44 #if HAVE_UNISTD_H
45 #include <unistd.h>
46 #endif
47 #include <time.h>
48 #include <memory.h>
49 #include <ctype.h>
50 #include <errno.h>
51 #include <sys/types.h>
52 #include <sys/stat.h>
53 #include <fcntl.h>
54 
55 #include <gtk/gtk.h>
56 
57 #include "project.h"
58 #include "task.h"
59 #include "gtimer.h"
60 #include "config.h"
61 // PV:
62 #include "custom-list.h"
63 
64 #ifdef GTIMER_MEMDEBUG
65 #include "memdebug/memdebug.h"
66 #endif
67 
68 #define NO_TOOLTIPS	1
69 
70 extern TaskData **visible_tasks, **tasks;
71 extern int num_visible_tasks, num_tasks;
72 extern GtkWidget *main_window;
73 
74 typedef struct {
75   GtkWidget *window;
76   GtkWidget *task_list;     // PV: -
77 //GtkTreeView *task_list;   // PV: +
78   TaskData **tasks;
79   int num_tasks;
80 //GtkWidget **list_items;   // PV: -
81   GtkTreePath **list_items; // PV: +
82 } HideData;
83 
84 
85 
86 
87 
88 
ok_callback(widget,data)89 static void ok_callback ( widget, data )
90 GtkWidget *widget;
91 gpointer data;
92 {
93   HideData *hd = (HideData *) data;
94   GList *selected, *item;
95   int loop;
96   // PV:
97   GtkTreeSelection *select;
98 #if PV_DEBUG
99   volatile const char *s1;
100   volatile const char *s2;
101 #else
102   const char *s1, *s2;
103 #endif
104 
105 //  selected = GTK_LIST ( hd->task_list ) ->selection;
106 
107   select = gtk_tree_view_get_selection ( GTK_TREE_VIEW(hd->task_list) );
108   selected = gtk_tree_selection_get_selected_rows ( GTK_TREE_SELECTION(select), NULL );
109   // selected contains list of paths
110 
111   if ( ! selected ) {
112     create_confirm_window ( CONFIRM_ERROR,
113       gettext("Error"),
114       gettext("You have not selected any tasks"),
115       gettext("Ok"), NULL, NULL,
116       NULL, NULL, NULL,
117       NULL );
118     return;
119   }
120 
121   /* which tasks were selected... */
122   for ( item = selected; item != NULL; item = item->next ) {
123     s1 = gtk_tree_path_to_string(item->data);
124     for ( loop = 0; loop < hd->num_tasks; loop++ ) {
125       s2 = gtk_tree_path_to_string( hd->list_items[loop] );
126 //    if ( item->data == hd->list_items[loop] ) {
127       if ( strcmp (s1, s2) == 0 ) {
128         /* don't need to realloc visible_tasks[] */
129         visible_tasks[num_visible_tasks] = hd->tasks[loop];
130         visible_tasks[num_visible_tasks]->moved = 1;
131         visible_tasks[num_visible_tasks]->new_task = 1; /* add back */
132         taskUnsetOption ( visible_tasks[num_visible_tasks]->task,
133           GTIMER_TASK_OPTION_HIDDEN );
134         num_visible_tasks++;
135       }
136     }
137   }
138 
139   gtk_grab_remove ( hd->window );
140   gtk_widget_destroy ( hd->window );
141 
142   /* Free resources */
143   free ( hd->tasks );
144   free ( hd->list_items );
145   free ( hd );
146 
147   /* redraw the task list */
148   update_list ();
149 }
150 
151 
cancel_callback(widget,data)152 static void cancel_callback ( widget, data )
153 GtkWidget *widget;
154 gpointer data;
155 {
156   HideData *hd = (HideData *) data;
157   gtk_grab_remove ( hd->window );
158   gtk_widget_destroy ( hd->window );
159   free ( hd->tasks );
160   free ( hd->list_items );
161   free ( hd );
162 }
163 
164 
165 
select_all_callback(widget,data)166 static void select_all_callback ( widget, data )
167 GtkWidget *widget;
168 gpointer data;
169 {
170   HideData *hd = (HideData *) data;
171 
172   gtk_tree_selection_select_all (
173     gtk_tree_view_get_selection ( GTK_TREE_VIEW(hd->task_list) ) );
174 
175 }
176 
177 
178 
select_none_callback(widget,data)179 static void select_none_callback ( widget, data )
180 GtkWidget *widget;
181 gpointer data;
182 {
183   HideData *hd = (HideData *) data;
184 
185   gtk_tree_selection_unselect_all (
186     gtk_tree_view_get_selection ( GTK_TREE_VIEW(hd->task_list) ) );
187 
188 }
189 
190 
191 
192 
193 
194 /*
195 ** Create the unhide window.
196 */
create_unhide_window()197 GtkWidget *create_unhide_window ()
198 {
199   GtkWidget *hide_window;
200   /*GtkTooltips *tooltips;*/
201   GtkWidget *label, *button, *scrolled;
202   HideData *hd;
203   GList *items = NULL;
204   int loop, count;
205   char msg[100];
206   // PV:
207   char temp[512];
208   CustomList *customlist;
209   GtkCellRenderer *renderer;
210   GtkTreeViewColumn *col;
211   GtkTreeSelection *select;
212   gchar * xtaskname;
213 
214   customlist = custom_list_new();
215 
216   hd = (HideData *) malloc ( sizeof ( HideData ) );
217   memset ( hd, '\0', sizeof ( HideData ) );
218   hd->window = hide_window = gtk_dialog_new ();
219   gtk_window_set_wmclass ( GTK_WINDOW ( hd->window ), "GTimer", "gtimer" );
220   sprintf ( msg, "GTimer: %s", gettext("Unhide") );
221   gtk_window_set_title (GTK_WINDOW (hide_window), msg );
222   gtk_window_position ( GTK_WINDOW(hide_window), GTK_WIN_POS_MOUSE );
223   gtk_grab_add ( hide_window );
224   gtk_widget_realize ( hide_window );
225 
226   label = gtk_label_new ( gettext("Tasks to include:") );
227   gtk_label_set_justify ( GTK_LABEL ( label ), GTK_JUSTIFY_LEFT );
228   gtk_box_pack_start ( GTK_BOX ( GTK_DIALOG (hide_window)->vbox ),
229     label, FALSE, FALSE, 2 );
230   gtk_widget_show ( label );
231 
232   /* list of tasks */
233   scrolled = gtk_scrolled_window_new ( NULL, NULL );
234   gtk_widget_set_usize ( scrolled, 300, 200 );
235   gtk_scrolled_window_set_policy ( GTK_SCROLLED_WINDOW (scrolled),
236     GTK_POLICY_AUTOMATIC, GTK_POLICY_ALWAYS );
237   gtk_box_pack_start ( GTK_BOX ( GTK_DIALOG (hide_window)->vbox ),
238     scrolled, TRUE, TRUE, 2 );
239 
240   hd->tasks = (TaskData **) malloc ( sizeof ( TaskData * ) *
241     num_tasks ); /* more than we need... */
242   hd->list_items = (GtkWidget **) malloc ( sizeof ( GtkTreePath * ) *
243     num_tasks ); /* more than we need... */
244   for ( loop = 0, count = 0; loop < num_tasks; loop++ ) {
245     if ( taskOptionEnabled ( tasks[loop]->task, GTIMER_TASK_OPTION_HIDDEN ) ) {
246 
247       if (tasks[loop]->task->project_id < 0 )
248         snprintf ( temp, sizeof (temp), "%s", tasks[loop]->task->name );
249       else
250         snprintf ( temp, sizeof (temp), "[%s] %s", tasks[loop]->project_name,
251 	  tasks[loop]->task->name );
252       items = g_list_append ( items, hd->list_items[count] );
253       hd->tasks[count] = tasks[loop];
254       xtaskname = g_strdup_printf ("%s", temp);
255       hd->list_items[count] = custom_list_append_record( customlist, xtaskname);
256       count++;
257     }
258   }
259   hd->num_tasks = count;
260 // PV: TreeView
261   hd->task_list = gtk_tree_view_new_with_model(GTK_TREE_MODEL(customlist));
262   g_object_unref(customlist);
263 
264   renderer = gtk_cell_renderer_text_new();
265   col = gtk_tree_view_column_new();
266 
267   gtk_tree_view_column_pack_start ( col, renderer, TRUE );
268   gtk_tree_view_column_add_attribute ( col, renderer, "text", CUSTOM_LIST_COL_NAME );
269   gtk_tree_view_column_set_title ( col, gettext("[Project] Task") );
270   gtk_tree_view_append_column ( GTK_TREE_VIEW(hd->task_list), col );
271   select = gtk_tree_view_get_selection ( GTK_TREE_VIEW(hd->task_list) );
272   gtk_tree_selection_set_mode( select, GTK_SELECTION_MULTIPLE );
273 
274   gtk_scrolled_window_add_with_viewport ( GTK_SCROLLED_WINDOW ( scrolled ),
275     hd->task_list );
276 
277   gtk_tree_selection_select_all ( GTK_TREE_SELECTION(select) );
278   gtk_widget_show ( scrolled );
279   gtk_widget_show ( hd->task_list );
280 
281   /* add command buttons */
282   /*tooltips = gtk_tooltips_new ();*/
283 
284   gtk_box_set_homogeneous ( GTK_BOX ( GTK_DIALOG (hide_window)->action_area ),
285     1 );
286   button = gtk_button_new_with_label (gettext("Ok"));
287   gtk_box_pack_start (GTK_BOX (GTK_DIALOG (hide_window)->action_area),
288     button, TRUE, FALSE, 2);
289   gtk_box_set_spacing ( GTK_BOX (GTK_DIALOG (hide_window)->action_area),
290     2 );
291   gtk_signal_connect (GTK_OBJECT (button), "clicked",
292     GTK_SIGNAL_FUNC (ok_callback), hd);
293   GTK_WIDGET_SET_FLAGS (button, GTK_CAN_DEFAULT);
294   gtk_widget_grab_default (button);
295   gtk_widget_show (button);
296   /*gtk_tooltips_set_tips (tooltips, button, "Uhide selected tasks" );*/
297 
298   button = gtk_button_new_with_label ( gettext("Cancel") );
299   gtk_box_pack_start (GTK_BOX (GTK_DIALOG (hide_window)->action_area),
300     button, TRUE, FALSE, 2);
301   gtk_signal_connect (GTK_OBJECT (button), "clicked",
302     GTK_SIGNAL_FUNC (cancel_callback), hd);
303   gtk_widget_show (button);
304   /*gtk_tooltips_set_tips (tooltips, button,
305     "Cancel without unhiding taskst" );*/
306 
307   button = gtk_button_new_with_label ( gettext("Select all") );
308   gtk_box_pack_start (GTK_BOX (GTK_DIALOG (hide_window)->action_area),
309     button, TRUE, FALSE, 2);
310   gtk_signal_connect (GTK_OBJECT (button), "clicked",
311     GTK_SIGNAL_FUNC (select_all_callback), hd);
312   gtk_widget_show (button);
313   /*gtk_tooltips_set_tips (tooltips, button, "Select all tasks" );*/
314 
315   button = gtk_button_new_with_label ( gettext("Select none") );
316   gtk_box_pack_start (GTK_BOX (GTK_DIALOG (hide_window)->action_area),
317     button, TRUE, FALSE, 2);
318   gtk_signal_connect (GTK_OBJECT (button), "clicked",
319     GTK_SIGNAL_FUNC (select_none_callback), hd);
320   gtk_widget_show (button);
321   /*gtk_tooltips_set_tips (tooltips, button, "Unselect all tasks" );*/
322 
323   gtk_widget_show_all (hide_window);
324 
325   return ( hide_window );
326 }
327 
328 
329 
330 
331