2 * Routines for the file set dialog
6 * Wireshark - Network traffic analyzer
7 * By Gerald Combs <gerald@wireshark.org>
8 * Copyright 1998 Gerald Combs
10 * This program is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU General Public License
12 * as published by the Free Software Foundation; either version 2
13 * of the License, or (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
40 #include "compat_macros.h"
41 #include "simple_dialog.h"
43 #include "gui_utils.h"
44 #include "dlg_utils.h"
50 #include <epan/filesystem.h>
53 #include "fileset_dlg.h"
58 * Keep a static pointer to the current "File Set" window, if
59 * any, so that if somebody tries to do "File Set" while there's
60 * already a "File Set" window up, we just pop up the existing
61 * one, rather than creating a new one.
63 static GtkWidget *fs_w;
67 /* various widget related global data */
71 GtkTooltips *tooltips;
73 GtkWidget *fs_first_rb;
78 /* open the file corresponding to the given fileset entry */
80 fs_open_entry(fileset_entry *entry)
86 /* make a copy of the filename (cf_close will indirectly destroy it right now) */
87 fname = g_strdup(entry->fullname);
89 /* close the old and open the new file */
91 if (cf_open(&cfile, fname, FALSE, &err) == CF_OK) {
99 /* radio button was pressed/released */
101 fs_rb_cb(GtkWidget *open_bt, gpointer fs_data)
103 fileset_entry *entry = fs_data;
105 /* button release should have no effect */
106 if(!gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON(open_bt) )) {
110 fs_open_entry(entry);
114 /* the window was closed, cleanup things */
116 fs_destroy_cb(GtkWidget *win _U_, gpointer user_data _U_)
118 /* Note that we no longer have a "File Set" dialog box. */
123 /* get creation date (converted from filename) */
126 fileset_dlg_name2date_dup(const char * name) {
132 /* just to be sure ... */
133 if(!fileset_filename_match_pattern(name)) {
137 /* find char position behind the last underscore */
138 pfx = strrchr(name, '_');
142 /* start conversion behind that underscore */
143 filename = g_strdup_printf("%c%c%c%c.%c%c.%c%c %c%c:%c%c:%c%c",
144 /* year */ name[pos] , name[pos+1], name[pos+2], name[pos+3],
145 /* month */ name[pos+4], name[pos+5],
146 /* day */ name[pos+6], name[pos+7],
147 /* hour */ name[pos+8], name[pos+9],
148 /* min */ name[pos+10], name[pos+11],
149 /* second */ name[pos+12], name[pos+13]);
155 /* this file is a part of the current file set, add it to the dialog */
157 fileset_dlg_add_file(fileset_entry *entry) {
171 created = fileset_dlg_name2date_dup(entry->name);
173 /* if this file doesn't follow the file set pattern, */
174 /* use the creation time of that file */
175 local = localtime(&entry->ctime);
176 created = g_strdup_printf("%04u.%02u.%02u %02u:%02u:%02u",
177 local->tm_year+1900, local->tm_mon+1, local->tm_mday,
178 local->tm_hour, local->tm_min, local->tm_sec);
181 local = localtime(&entry->mtime);
182 modified = g_strdup_printf("%04u.%02u.%02u %02u:%02u:%02u",
183 local->tm_year+1900, local->tm_mon+1, local->tm_mday,
184 local->tm_hour, local->tm_min, local->tm_sec);
185 size = g_strdup_printf("%ld Bytes", entry->size);
187 fs_rb = gtk_radio_button_new_with_label_from_widget(
188 fs_first_rb ? GTK_RADIO_BUTTON(fs_first_rb) : NULL, entry->name);
193 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON (fs_rb), entry->current);
195 gtk_tooltips_set_tip(tooltips, fs_rb, "Open this capture file", NULL);
196 gtk_table_attach_defaults(GTK_TABLE(fs_tb), fs_rb, 0, 1, row, row+1);
197 SIGNAL_CONNECT(fs_rb, "toggled", fs_rb_cb, entry);
198 gtk_widget_show(fs_rb);
200 fs_lb = gtk_label_new(created);
201 gtk_table_attach_defaults(GTK_TABLE(fs_tb), fs_lb, 1, 2, row, row+1);
202 gtk_widget_set_sensitive(fs_lb, entry->current);
203 gtk_widget_show(fs_lb);
205 fs_lb = gtk_label_new(modified);
206 gtk_table_attach_defaults(GTK_TABLE(fs_tb), fs_lb, 2, 3, row, row+1);
207 gtk_widget_set_sensitive(fs_lb, entry->current);
208 gtk_widget_show(fs_lb);
210 fs_lb = gtk_label_new(size);
211 gtk_table_attach_defaults(GTK_TABLE(fs_tb), fs_lb, 3, 4, row, row+1);
212 gtk_widget_set_sensitive(fs_lb, entry->current);
213 gtk_widget_show(fs_lb);
215 title = g_strdup_printf("Wireshark: %u File%s in Set", row, plurality(row, "", "s"));
216 gtk_window_set_title(GTK_WINDOW(fs_w), title);
219 title = g_strdup_printf("... in directory: %s", fileset_get_dirname());
220 gtk_label_set(GTK_LABEL(fs_dir_lb), title);
223 gtk_widget_show_all(fs_tb);
225 /* resize the table until we use 18 rows (fits well into 800*600), if it's bigger use a scrollbar */
226 /* XXX - I didn't found a way to automatically shrink the table size again */
228 GtkRequisition requisition;
230 gtk_widget_size_request(fs_tb, &requisition);
231 WIDGET_SET_SIZE(GTK_WINDOW(fs_sw), -1, requisition.height);
232 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(fs_sw), GTK_POLICY_NEVER, GTK_POLICY_NEVER);
236 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(fs_sw), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC);
247 /* init the fileset table */
249 fileset_init_table(GtkWidget *parent)
254 fs_tb = gtk_table_new(6,1, FALSE);
255 gtk_table_set_row_spacings(GTK_TABLE(fs_tb), 1);
256 gtk_table_set_col_spacings(GTK_TABLE(fs_tb), 12);
257 gtk_container_add(GTK_CONTAINER(parent), fs_tb);
262 fs_lb = gtk_label_new("Filename");
263 gtk_table_attach(GTK_TABLE(fs_tb), fs_lb, 0, 1, row, row+1, GTK_EXPAND|GTK_FILL, 0, 0,0);
265 fs_lb = gtk_label_new("Created");
266 gtk_table_attach(GTK_TABLE(fs_tb), fs_lb, 1, 2, row, row+1, GTK_EXPAND|GTK_FILL, 0, 0,0);
268 fs_lb = gtk_label_new("Last Modified");
269 gtk_table_attach(GTK_TABLE(fs_tb), fs_lb, 2, 3, row, row+1, GTK_EXPAND|GTK_FILL, 0, 0,0);
271 fs_lb = gtk_label_new("Size");
272 gtk_table_attach(GTK_TABLE(fs_tb), fs_lb, 3, 4, row, row+1, GTK_EXPAND|GTK_FILL, 0, 0,0);
274 gtk_widget_hide(fs_tb);
276 gtk_window_set_title(GTK_WINDOW(fs_w), "Wireshark: 0 Files in Set");
278 gtk_label_set(GTK_LABEL(fs_dir_lb), "No capture file loaded!");
284 /* open the fileset dialog */
286 fileset_cb(GtkWidget *w _U_, gpointer d _U_)
288 GtkWidget *main_vb, *bbox, *close_bt, *help_bt;
292 /* There's already a "File Set" dialog box; reactivate it. */
293 reactivate_window(fs_w);
297 fs_w = window_new(GTK_WINDOW_TOPLEVEL, "");
299 tooltips = gtk_tooltips_new();
301 main_vb = gtk_vbox_new(FALSE, 5);
302 gtk_container_border_width(GTK_CONTAINER(main_vb), 5);
303 gtk_container_add(GTK_CONTAINER(fs_w), main_vb);
305 fs_sw = gtk_scrolled_window_new(NULL, NULL);
306 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(fs_sw), GTK_POLICY_NEVER, GTK_POLICY_NEVER);
307 gtk_box_pack_start(GTK_BOX(main_vb), fs_sw, TRUE, TRUE, 0);
309 /* add a dummy container, so we can replace the table later */
310 fs_tb_vb = gtk_vbox_new(FALSE, 0);
311 gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(fs_sw), fs_tb_vb);
313 fs_dir_lb = gtk_label_new("");
314 gtk_box_pack_start(GTK_BOX(main_vb), fs_dir_lb, FALSE, FALSE, 0);
316 fileset_init_table(fs_tb_vb);
318 /* Button row: close button */
319 if(topic_available(HELP_FILESET_DIALOG)) {
320 bbox = dlg_button_row_new(GTK_STOCK_CLOSE, GTK_STOCK_HELP, NULL);
322 bbox = dlg_button_row_new(GTK_STOCK_CLOSE, NULL);
324 gtk_box_pack_start(GTK_BOX(main_vb), bbox, FALSE, FALSE, 5);
326 close_bt = g_object_get_data(G_OBJECT(bbox), GTK_STOCK_CLOSE);
327 window_set_cancel_button(fs_w, close_bt, window_cancel_button_cb);
328 gtk_tooltips_set_tip(tooltips, close_bt, "Close this window.", NULL);
330 if(topic_available(HELP_FILESET_DIALOG)) {
331 help_bt = g_object_get_data(G_OBJECT(bbox), GTK_STOCK_HELP);
332 SIGNAL_CONNECT(help_bt, "clicked", topic_cb, HELP_FILESET_DIALOG);
335 gtk_widget_grab_default(close_bt);
337 SIGNAL_CONNECT(fs_w, "delete_event", window_delete_event_cb, NULL);
338 SIGNAL_CONNECT(fs_w, "destroy", fs_destroy_cb, NULL);
340 /* init the dialog content */
341 fileset_update_dlg();
343 gtk_widget_show_all(fs_w);
344 window_present(fs_w);
348 /* open the next file in the file set, or do nothing if already the last file */
350 fileset_next_cb(GtkWidget *w _U_, gpointer d _U_)
352 fileset_entry *entry;
354 entry = fileset_get_next();
357 fs_open_entry(entry);
362 /* open the previous file in the file set, or do nothing if already the first file */
364 fileset_previous_cb(GtkWidget *w _U_, gpointer d _U_)
366 fileset_entry *entry;
368 entry = fileset_get_previous();
371 fs_open_entry(entry);
376 /* a new capture file was opened, browse the dir and look for files matching the given file set */
378 fileset_file_opened(const char *fname) {
379 fileset_add_dir(fname);
381 window_present(fs_w);
384 /* update the menu */
385 set_menus_for_file_set(TRUE /* file_set */,
386 fileset_get_previous() != NULL, fileset_get_next() != NULL );
390 /* the capture file was closed */
392 fileset_file_closed(void)
395 /* reinit the table, title and alike */
396 gtk_widget_ref(fs_tb_vb);
397 gtk_widget_destroy(fs_tb);
399 fileset_init_table(fs_tb_vb);
400 window_present(fs_w);
405 /* update the menu */
406 set_menus_for_file_set(FALSE /* file_set */,
407 fileset_get_previous() != NULL, fileset_get_next() != NULL );