comparison src/main.c @ 9:d907d608745f

Sync to GQview 1.5.9 release. ######## DO NOT BASE ENHANCEMENTS OR TRANSLATION UPDATES ON CODE IN THIS CVS! This CVS is never up to date with current development and is provided solely for reference purposes, please use the latest official release package when making any changes or translation updates. ########
author gqview
date Sat, 26 Feb 2005 00:13:35 +0000
parents c0e337a01cb7
children 6d50eaba8e4b
comparison
equal deleted inserted replaced
8:e0d0593d519e 9:d907d608745f
1 /* 1 /*
2 * GQview image viewer 2 * GQview
3 * (C)2000 John Ellis 3 * (C) 2004 John Ellis
4 * 4 *
5 * Author: John Ellis 5 * Author: John Ellis
6 * 6 *
7 * This software is released under the GNU General Public License (GNU GPL).
8 * Please read the included file COPYING for more information.
9 * This software comes with no warranty of any kind, use at your own risk!
7 */ 10 */
8 11
12
9 #include "gqview.h" 13 #include "gqview.h"
14
15 #include "cache.h"
16 #include "collect.h"
17 #include "collect-io.h"
18 #include "dnd.h"
19 #include "editors.h"
20 #include "filelist.h"
21 #include "img-view.h"
22 #include "layout.h"
23 #include "layout_image.h"
24 #include "menu.h"
25 #include "preferences.h"
26 #include "rcfile.h"
27 #include "remote.h"
28 #include "similar.h"
29 #include "slideshow.h"
30 #include "utilops.h"
31 #include "ui_bookmark.h"
32 #include "ui_help.h"
33 #include "ui_fileops.h"
34 #include "ui_tabcomp.h"
35 #include "ui_utildlg.h"
36
10 #include <gdk/gdkkeysyms.h> /* for keyboard values */ 37 #include <gdk/gdkkeysyms.h> /* for keyboard values */
11 38
12 static void parse_command_line(int argc, char *argv[], gchar **path, gchar **file); 39 #include "icons/icon.xpm"
13 static void setup_default_options(); 40
41
42 #include <math.h>
43
44
45 static RemoteConnection *gqview_remote = NULL;
46 static CollectionData *gqview_command_collection = NULL;
47
14 48
15 /* 49 /*
16 *----------------------------------------------------------------------------- 50 *-----------------------------------------------------------------------------
17 * path manipulation routines (public) 51 * misc (public)
18 *----------------------------------------------------------------------------- 52 *-----------------------------------------------------------------------------
19 */ 53 */
20 54
21 gchar *filename_from_path(char *t) 55 typedef struct _WindowIconData WindowIconData;
22 { 56 struct _WindowIconData
23 char *p; 57 {
24 58 const char **icon;
25 p = t + strlen(t); 59 gchar *path;
26 while(p > t && p[0] != '/') p--; 60 };
27 if (p[0] == '/') p++; 61
28 return p; 62 static void window_set_icon_cb(GtkWidget *widget, gpointer data)
29 } 63 {
30 64 WindowIconData *wid = data;
31 gchar *remove_level_from_path(gchar *path) 65 GdkPixbuf *pb;
32 { 66 GdkPixmap *pixmap;
33 gchar *new_path; 67 GdkBitmap *mask;
34 gchar *ptr = path; 68
35 gint p; 69 if (wid->icon)
36 70 {
37 if (!path) return NULL; 71 pb = gdk_pixbuf_new_from_xpm_data(wid->icon);
38 72 }
39 p = strlen(path) - 1; 73 else
40 if (p < 0) return NULL; 74 {
41 while(ptr[p] != '/' && p > 0) p--; 75 pb = gdk_pixbuf_new_from_file(wid->path, NULL);
42 if (p == 0 && ptr[p] == '/') p++; 76 }
43 new_path = g_strndup(path, (guint)p); 77
44 return new_path; 78 g_free(wid->path);
45 } 79 g_free(wid);
46 80
47 void parse_out_relatives(gchar *path) 81 if (!pb) return;
48 { 82
49 gint s, t; 83 gdk_pixbuf_render_pixmap_and_mask(pb, &pixmap, &mask, 128);
50 84 gdk_pixbuf_unref(pb);
51 if (!path) return; 85
52 86 gdk_window_set_icon(widget->window, NULL, pixmap, mask);
53 s = t = 0; 87 /* apparently, gdk_window_set_icon does not ref the pixmap and mask, so don't unref it (leak?) */
54 88 }
55 while (path[s] != '\0') 89
56 { 90 void window_set_icon(GtkWidget *window, const char **icon, const gchar *file)
57 if (path[s] == '/' && path[s+1] == '.' && (path[s+2] == '/' || path[s+2] == '\0') ) 91 {
58 { 92 WindowIconData *wid;
59 s += 2; 93
60 } 94 if (!icon && !file) icon = (const char **)icon_xpm;
61 else if (path[s] == '/' && path[s+1] == '.' && path[s+2] == '.' && (path[s+3] == '/' || path[s+3] == '\0') ) 95
62 { 96 wid = g_new0(WindowIconData, 1);
63 s += 3; 97 wid->icon = icon;
64 if (t > 0) t--; 98 wid->path = g_strdup(file);
65 while (path[t] != '/' && t > 0) t--; 99
66 } 100 g_signal_connect(G_OBJECT(window), "realize",
67 else 101 G_CALLBACK(window_set_icon_cb), wid);
68 { 102 }
69 if (s != t) path[t] = path[s]; 103
70 t++; 104 gint window_maximized(GtkWidget *window)
71 s++; 105 {
72 } 106 GdkWindowState state;
73 } 107
74 if (t == 0 && path[t] == '/') t++; 108 if (!window || !window->window) return FALSE;
75 if (t > 1 && path[t-1] == '/') t--; 109
76 path[t] = '\0'; 110 state = gdk_window_get_state(window->window);
111 return (state & GDK_WINDOW_STATE_MAXIMIZED);
112 }
113
114 gdouble get_zoom_increment(void)
115 {
116 return ((zoom_increment != 0) ? (gdouble)zoom_increment / 10.0 : 1.0);
77 } 117 }
78 118
79 /* 119 /*
80 *----------------------------------------------------------------------------- 120 *-----------------------------------------------------------------------------
81 * external editor start routines (public) 121 * Open browser with the help Documentation
122 *-----------------------------------------------------------------------------
123 */
124
125 static gchar *command_result(const gchar *binary, const gchar *command)
126 {
127 gchar *result = NULL;
128 FILE *f;
129 char buf[2048];
130 int l;
131
132 if (!binary) return NULL;
133 if (!file_in_path(binary)) return NULL;
134
135 if (!command) return g_strdup(binary);
136 if (command[0] == '!') return g_strdup(command + 1);
137
138 f = popen(command, "r");
139 if (!f) return NULL;
140
141 while ((l = fread(buf, sizeof(char), sizeof(buf), f)) > 0)
142 {
143 if (!result)
144 {
145 int n = 0;
146
147 while (n < l && buf[n] != '\n' && buf[n] != '\r') n++;
148 if (n > 0) result = g_strndup(buf, n);
149 }
150 }
151
152 pclose(f);
153
154 return result;
155 }
156
157 static void help_browser_command(const gchar *command, const gchar *path)
158 {
159 gchar *result;
160 gchar *buf;
161 gchar *begin;
162 gchar *end;
163
164 if (!command || !path) return;
165
166 if (debug) printf("Help command pre \"%s\", \"%s\"\n", command, path);
167
168 buf = g_strdup(command);
169 begin = strstr(buf, "%s");
170 if (begin)
171 {
172 *begin = '\0';
173 end = begin + 2;
174 begin = buf;
175
176 result = g_strdup_printf("%s%s%s &", begin, path, end);
177 }
178 else
179 {
180 result = g_strdup_printf("%s \"%s\" &", command, path);
181 }
182 g_free(buf);
183
184 if (debug) printf("Help command post [%s]\n", result);
185
186 system(result);
187
188 g_free(result);
189 }
190
191 /*
192 * each set of 2 strings is one browser:
193 * the 1st is the binary to look for in the path
194 * the 2nd has 3 capabilities:
195 * NULL exec binary with html file path as command line
196 * string exec string and use results for command line
197 * !string use text following ! as command line, replacing optional %s with html file path
198 */
199 static gchar *html_browsers[] =
200 {
201 /* Redhat has a nifty htmlview script to start the user's preferred browser */
202 "htmlview", NULL,
203 /* GNOME 2 */
204 "gconftool-2", "gconftool-2 -g /desktop/gnome/url-handlers/http/command",
205 /* KDE */
206 "kfmclient", "!kfmclient exec \"%s\"",
207 /* use fallbacks */
208 "firefox", NULL,
209 "mozilla", NULL,
210 "konqueror", NULL,
211 "netscape", NULL,
212 NULL, NULL
213 };
214
215 static void help_browser_run(void)
216 {
217 gchar *result = NULL;
218 gint i;
219
220 i = 0;
221 while (!result && html_browsers[i])
222 {
223 result = command_result(html_browsers[i], html_browsers[i+1]);
224 i += 2;
225 }
226
227 if (!result)
228 {
229 printf("Unable to detect an installed browser.\n");
230 return;
231 }
232
233 help_browser_command(result, GQVIEW_HTMLDIR "/index.html");
234
235 g_free(result);
236 }
237
238 /*
239 *-----------------------------------------------------------------------------
240 * help window
82 *----------------------------------------------------------------------------- 241 *-----------------------------------------------------------------------------
83 */ 242 */
84 243
85 void start_editor_from_file(gint n, gchar *path) 244 static GtkWidget *help_window = NULL;
86 { 245
87 gchar *cmd; 246 static void help_window_destroy_cb(GtkWidget *window, gpointer data)
88 if (!path) return; 247 {
89 cmd = g_strdup_printf("%s \"%s\" &", editor_command[n], path); 248 help_window = NULL;
90 printf(_("GQview running: %s\n"),cmd); 249 }
91 system(cmd); 250
92 g_free(cmd); 251 void help_window_show(const gchar *key)
93 } 252 {
94 253 if (key && strcmp(key, "html_contents") == 0)
95 void start_editor_from_image(gint n) 254 {
96 { 255 help_browser_run();
97 start_editor_from_file(n, image_get_path()); 256 return;
98 } 257 }
99 258
100 void start_editor_from_list(gint n) 259 if (help_window)
101 { 260 {
102 gchar *cmd; 261 gtk_window_present(GTK_WINDOW(help_window));
103 gchar *buf; 262 if (key) help_window_set_key(help_window, key);
104 GList *list = file_get_selected_list(); 263 return;
105 GList *work; 264 }
106 if (!list) return; 265
107 work = list; 266 help_window = help_window_new(_("Help - GQview"), "GQview", "help",
108 cmd = g_strconcat(editor_command[n], " ", NULL); 267 GQVIEW_HELPDIR "/README", key);
109 while(work) 268 g_signal_connect(G_OBJECT(help_window), "destroy",
110 { 269 G_CALLBACK(help_window_destroy_cb), NULL);
111 buf = cmd; 270 }
112 cmd = g_strconcat(buf, "\"", work->data, "\" ", NULL); 271
113 g_free(buf);
114 work = work->next;
115 }
116 buf = cmd;
117 cmd = g_strconcat(buf, "&", NULL);
118 g_free(buf);
119 printf(_("GQview running: %s\n"),cmd);
120 system(cmd);
121 g_free(cmd);
122 free_selected_list(list);
123 }
124 272
125 /* 273 /*
126 *----------------------------------------------------------------------------- 274 *-----------------------------------------------------------------------------
127 * keyboard functions 275 * keyboard functions
128 *----------------------------------------------------------------------------- 276 *-----------------------------------------------------------------------------
132 { 280 {
133 static gint delta = 0; 281 static gint delta = 0;
134 static guint32 time_old = 0; 282 static guint32 time_old = 0;
135 static guint keyval_old = 0; 283 static guint keyval_old = 0;
136 284
285 if (event->state & GDK_CONTROL_MASK)
286 {
287 if (*x < 0) *x = G_MININT / 2;
288 if (*x > 0) *x = G_MAXINT / 2;
289 if (*y < 0) *y = G_MININT / 2;
290 if (*y > 0) *y = G_MAXINT / 2;
291
292 return;
293 }
294
137 if (progressive_key_scrolling) 295 if (progressive_key_scrolling)
138 { 296 {
139 guint32 time_diff; 297 guint32 time_diff;
140 298
141 time_diff = event->time - time_old; 299 time_diff = event->time - time_old;
155 313
156 *x = *x * delta; 314 *x = *x * delta;
157 *y = *y * delta; 315 *y = *y * delta;
158 } 316 }
159 317
160 gint key_press_cb(GtkWidget *widget, GdkEventKey *event) 318
161 { 319 /*
162 gint stop_signal = FALSE; 320 *-----------------------------------------------------------------------------
163 gint x = 0; 321 * remote functions
164 gint y = 0; 322 *-----------------------------------------------------------------------------
165 323 */
166 if (GTK_WIDGET_HAS_FOCUS(path_entry)) 324
167 { 325 static void gr_image_next(const gchar *text, gpointer data)
168 if (event->keyval == GDK_Escape) 326 {
169 gtk_entry_set_text(GTK_ENTRY(path_entry), current_path); 327 layout_image_next(NULL);
170 return stop_signal; 328 }
171 } 329
172 330 static void gr_image_prev(const gchar *text, gpointer data)
173 if (full_screen_window || GTK_WIDGET_HAS_FOCUS(main_image->viewport)) 331 {
174 { 332 layout_image_prev(NULL);
175 switch (event->keyval) 333 }
176 { 334
177 case GDK_Left: 335 static void gr_image_first(const gchar *text, gpointer data)
178 x -= 1; 336 {
179 stop_signal = TRUE; 337 layout_image_first(NULL);
180 break; 338 }
181 case GDK_Right: 339
182 x += 1; 340 static void gr_image_last(const gchar *text, gpointer data)
183 stop_signal = TRUE; 341 {
184 break; 342 layout_image_last(NULL);
185 case GDK_Up: 343 }
186 y -= 1; 344
187 stop_signal = TRUE; 345 static void gr_fullscreen_toggle(const gchar *text, gpointer data)
188 break; 346 {
189 case GDK_Down: 347 layout_image_full_screen_toggle(NULL);
190 y += 1; 348 }
191 stop_signal = TRUE; 349
192 break; 350 static void gr_fullscreen_start(const gchar *text, gpointer data)
193 case GDK_BackSpace: 351 {
194 file_prev_image(); 352 layout_image_full_screen_start(NULL);
195 stop_signal = TRUE; 353 }
196 break; 354
197 case GDK_space: 355 static void gr_fullscreen_stop(const gchar *text, gpointer data)
198 file_next_image(); 356 {
199 stop_signal = TRUE; 357 layout_image_full_screen_stop(NULL);
200 break; 358 }
201 } 359
202 } 360 static void gr_slideshow_start_rec(const gchar *text, gpointer data)
203 361 {
204 switch (event->keyval) 362 GList *list;
205 { 363
206 case '+': 364 list = path_list_recursive(text);
207 image_adjust_zoom(1); 365 if (!list) return;
208 break; 366 printf("length: %d\n", g_list_length(list));
209 case GDK_Page_Up: 367 layout_image_slideshow_stop(NULL);
210 file_prev_image(); 368 layout_image_slideshow_start_from_list(NULL, list);
211 stop_signal = TRUE; 369 }
212 break; 370
213 case GDK_Page_Down: 371 static void gr_slideshow_toggle(const gchar *text, gpointer data)
214 file_next_image(); 372 {
215 stop_signal = TRUE; 373 layout_image_slideshow_toggle(NULL);
216 break; 374 }
217 case GDK_Home: 375
218 file_first_image(); 376 static void gr_slideshow_start(const gchar *text, gpointer data)
219 stop_signal = TRUE; 377 {
220 break; 378 layout_image_slideshow_start(NULL);
221 case GDK_End: 379 }
222 file_last_image(); 380
223 stop_signal = TRUE; 381 static void gr_slideshow_stop(const gchar *text, gpointer data)
224 break; 382 {
225 case GDK_Delete: 383 layout_image_slideshow_stop(NULL);
226 file_util_delete(image_get_path(), NULL); 384 }
227 stop_signal = TRUE; 385
228 break; 386 static void gr_slideshow_delay(const gchar *text, gpointer data)
229 case GDK_Escape: 387 {
230 interrupt_thumbs(); 388 gdouble n;
231 stop_signal = TRUE; 389
232 break; 390 n = strtod(text, NULL);
233 case 'Q': case 'q': 391 if (n < SLIDESHOW_MIN_SECONDS || n > SLIDESHOW_MAX_SECONDS)
234 if (event->state == 0 || (event->state & GDK_MODIFIER_MASK) == GDK_LOCK_MASK) 392 {
235 { 393 gchar *buf;
236 exit_gqview(); 394
237 return FALSE; 395 buf = g_strdup_printf("Remote slideshow delay out of range (%.1f to %.1f)\n",
238 } 396 SLIDESHOW_MIN_SECONDS, SLIDESHOW_MAX_SECONDS);
239 break; 397 print_term(buf);
240 } 398 g_free(buf);
241 399
242 if (event->state & GDK_SHIFT_MASK) 400 return;
243 { 401 }
244 x *= 3; 402 slideshow_delay = (gint)(n * 10.0 + 0.01);
245 y *= 3; 403 }
246 } 404
247 405 static void gr_tools_show(const gchar *text, gpointer data)
248 if (x != 0 || y!= 0) 406 {
249 { 407 gint popped;
250 keyboard_scroll_calc(&x, &y, event); 408 gint hidden;
251 image_scroll(x, y); 409
252 } 410 if (layout_tools_float_get(NULL, &popped, &hidden) && hidden)
253 411 {
254 if (stop_signal) gtk_signal_emit_stop_by_name(GTK_OBJECT(widget), "key_press_event"); 412 layout_tools_float_set(NULL, popped, FALSE);
255 413 }
256 return stop_signal; 414 }
415
416 static void gr_tools_hide(const gchar *text, gpointer data)
417 {
418 gint popped;
419 gint hidden;
420
421 if (layout_tools_float_get(NULL, &popped, &hidden) && !hidden)
422 {
423 layout_tools_float_set(NULL, popped, TRUE);
424 }
425 }
426
427 static gint gr_quit_idle_cb(gpointer data)
428 {
429 exit_gqview();
430
431 return FALSE;
432 }
433
434 static void gr_quit(const gchar *text, gpointer data)
435 {
436 /* schedule exit when idle, if done from within a
437 * remote handler remote_close will crash
438 */
439 g_idle_add(gr_quit_idle_cb, NULL);
440 }
441
442 static void gr_file_load(const gchar *text, gpointer data)
443 {
444 if (isfile(text))
445 {
446 if (file_extension_match(text, ".gqv"))
447 {
448 collection_window_new(text);
449 }
450 else
451 {
452 layout_set_path(NULL, text);
453 }
454 }
455 else if (isdir(text))
456 {
457 layout_set_path(NULL, text);
458 }
459 else
460 {
461 printf("remote sent filename that does not exist:\"%s\"\n", text);
462 }
463 }
464
465 static void gr_file_view(const gchar *text, gpointer data)
466 {
467 view_window_new(text);
468 }
469
470 static void gr_list_clear(const gchar *text, gpointer data)
471 {
472 if (gqview_command_collection) collection_unref(gqview_command_collection);
473 gqview_command_collection = NULL;
474 }
475
476 static void gr_list_add(const gchar *text, gpointer data)
477 {
478 gint new = TRUE;
479
480 if (!gqview_command_collection)
481 {
482 CollectionData *cd;
483
484 cd = collection_new("");
485
486 g_free(cd->path);
487 cd->path = NULL;
488 g_free(cd->name);
489 cd->name = g_strdup(_("Command line"));
490
491 gqview_command_collection = cd;
492 }
493 else
494 {
495 new = (!collection_get_first(gqview_command_collection));
496 }
497
498 if (collection_add(gqview_command_collection, text, FALSE) && new)
499 {
500 layout_image_set_collection(NULL, gqview_command_collection,
501 collection_get_first(gqview_command_collection));
502 }
503 }
504
505 static void gr_raise(const gchar *text, gpointer data)
506 {
507 LayoutWindow *lw = NULL;
508
509 if (layout_valid(&lw))
510 {
511 gtk_window_present(GTK_WINDOW(lw->window));
512 }
513 }
514
515 typedef struct _RemoteCommandEntry RemoteCommandEntry;
516 struct _RemoteCommandEntry {
517 gchar *opt_s;
518 gchar *opt_l;
519 void (*func)(const gchar *text, gpointer data);
520 gint needs_extra;
521 gint prefer_command_line;
522 gchar *description;
523 };
524
525 static RemoteCommandEntry remote_commands[] = {
526 /* short, long callback, extra, prefer,description */
527 { "-n", "--next", gr_image_next, FALSE, FALSE, N_("next image") },
528 { "-b", "--back", gr_image_prev, FALSE, FALSE, N_("previous image") },
529 { NULL, "--first", gr_image_first, FALSE, FALSE, N_("first image") },
530 { NULL, "--last", gr_image_last, FALSE, FALSE, N_("last image") },
531 { "-f", "--fullscreen", gr_fullscreen_toggle, FALSE, TRUE, N_("toggle full screen") },
532 { "-fs","--fullscreen-start", gr_fullscreen_start, FALSE, FALSE, N_("start full screen") },
533 { "-fS","--fullscreen-stop", gr_fullscreen_stop, FALSE, FALSE, N_("stop full screen") },
534 { "-s", "--slideshow", gr_slideshow_toggle, FALSE, TRUE, N_("toggle slide show") },
535 { "-ss","--slideshow-start", gr_slideshow_start, FALSE, FALSE, N_("start slide show") },
536 { "-sS","--slideshow-stop", gr_slideshow_stop, FALSE, FALSE, N_("stop slide show") },
537 { "-sr","--slideshow-recurse", gr_slideshow_start_rec, TRUE, FALSE, N_("start recursive slide show") },
538 { "-d", "--delay=", gr_slideshow_delay, TRUE, FALSE, N_("set slide show delay in seconds") },
539 { "+t", "--tools-show", gr_tools_show, FALSE, TRUE, N_("show tools") },
540 { "-t", "--tools-hide", gr_tools_hide, FALSE, TRUE, N_("hide tools") },
541 { "-q", "--quit", gr_quit, FALSE, FALSE, N_("quit") },
542 { NULL, "file:", gr_file_load, TRUE, FALSE, N_("open file") },
543 { NULL, "view:", gr_file_view, TRUE, FALSE, N_("open file in new window") },
544 { NULL, "--list-clear", gr_list_clear, FALSE, FALSE, NULL },
545 { NULL, "--list-add:", gr_list_add, TRUE, FALSE, NULL },
546 { NULL, "raise", gr_raise, FALSE, FALSE, NULL },
547 { NULL, NULL, NULL, FALSE, FALSE, NULL }
548 };
549
550 static RemoteCommandEntry *gqview_remote_command_find(const gchar *text, const gchar **offset)
551 {
552 gint match = FALSE;
553 gint i;
554
555 i = 0;
556 while (!match && remote_commands[i].func != NULL)
557 {
558 if (remote_commands[i].needs_extra)
559 {
560 if (remote_commands[i].opt_s &&
561 strncmp(remote_commands[i].opt_s, text, strlen(remote_commands[i].opt_s)) == 0)
562 {
563 if (offset) *offset = text + strlen(remote_commands[i].opt_s);
564 return &remote_commands[i];
565 }
566 else if (remote_commands[i].opt_l &&
567 strncmp(remote_commands[i].opt_l, text, strlen(remote_commands[i].opt_l)) == 0)
568 {
569 if (offset) *offset = text + strlen(remote_commands[i].opt_l);
570 return &remote_commands[i];
571 }
572 }
573 else
574 {
575 if ((remote_commands[i].opt_s && strcmp(remote_commands[i].opt_s, text) == 0) ||
576 (remote_commands[i].opt_l && strcmp(remote_commands[i].opt_l, text) == 0))
577 {
578 if (offset) *offset = text;
579 return &remote_commands[i];
580 }
581 }
582
583 i++;
584 }
585
586 return NULL;
587 }
588
589 static void gqview_remote_cb(RemoteConnection *rc, const gchar *text, gpointer data)
590 {
591 RemoteCommandEntry *entry;
592 const gchar *offset;
593
594 entry = gqview_remote_command_find(text, &offset);
595 if (entry && entry->func)
596 {
597 entry->func(offset, data);
598 }
599 else
600 {
601 printf("unknown remote command:%s\n", text);
602 }
603 }
604
605 static void gqview_remote_help(void)
606 {
607 gint i;
608
609 print_term(_("Remote command list:\n"));
610
611 i = 0;
612 while (remote_commands[i].func != NULL)
613 {
614 if (remote_commands[i].description)
615 {
616 gchar *buf;
617
618 buf = g_strdup_printf(" %-3s%s %-20s %s\n",
619 (remote_commands[i].opt_s) ? remote_commands[i].opt_s : "",
620 (remote_commands[i].opt_s && remote_commands[i].opt_l) ? "," : " ",
621 (remote_commands[i].opt_l) ? remote_commands[i].opt_l : "",
622 _(remote_commands[i].description));
623
624 print_term(buf);
625 g_free(buf);
626 }
627 i++;
628 }
629 }
630
631 static GList *gqview_remote_build_list(GList *list, int argc, char *argv[])
632 {
633 gint i;
634
635 i = 1;
636 while (i < argc)
637 {
638 RemoteCommandEntry *entry;
639
640 entry = gqview_remote_command_find(argv[i], NULL);
641 if (entry)
642 {
643 list = g_list_append(list, argv[i]);
644 }
645 i++;
646 }
647
648 return list;
649 }
650
651 static void gqview_remote_control(const gchar *arg_exec, GList *remote_list, const gchar *path,
652 GList *cmd_list, GList *collection_list)
653 {
654 RemoteConnection *rc;
655 gint started = FALSE;
656 gchar *buf;
657
658 buf = g_strconcat(homedir(), "/", GQVIEW_RC_DIR, "/.command", NULL);
659 rc = remote_client_open(buf);
660 if (!rc)
661 {
662 GString *command;
663 GList *work;
664 gint retry_count = 12;
665 gint blank = FALSE;
666
667 print_term(_("Remote GQview not running, starting..."));
668 command = g_string_new(arg_exec);
669
670 work = remote_list;
671 while (work)
672 {
673 gchar *text;
674 RemoteCommandEntry *entry;
675
676 text = work->data;
677 work = work->next;
678
679 entry = gqview_remote_command_find(text, NULL);
680 if (entry)
681 {
682 if (entry->prefer_command_line)
683 {
684 remote_list = g_list_remove(remote_list, text);
685 g_string_append(command, " ");
686 g_string_append(command, text);
687 }
688 if (entry->opt_l && strcmp(entry->opt_l, "file:") == 0)
689 {
690 blank = TRUE;
691 }
692 }
693 }
694
695 if (blank || cmd_list || path) g_string_append(command, " --blank");
696 if (debug) g_string_append(command, " --debug");
697
698 g_string_append(command, " &");
699 system(command->str);
700 g_string_free(command, TRUE);
701
702 while (!rc && retry_count > 0)
703 {
704 usleep((retry_count > 10) ? 500000 : 1000000);
705 rc = remote_client_open(buf);
706 if (!rc) print_term(".");
707 retry_count--;
708 }
709
710 print_term("\n");
711
712 started = TRUE;
713 }
714 g_free(buf);
715
716 if (rc)
717 {
718 GList *work;
719 const gchar *prefix;
720 gint use_path = TRUE;
721 gint sent = FALSE;
722
723 work = remote_list;
724 while (work)
725 {
726 gchar *text;
727 RemoteCommandEntry *entry;
728
729 text = work->data;
730 work = work->next;
731
732 entry = gqview_remote_command_find(text, NULL);
733 if (entry &&
734 entry->opt_l &&
735 strcmp(entry->opt_l, "file:") == 0) use_path = FALSE;
736
737 remote_client_send(rc, text);
738
739 sent = TRUE;
740 }
741
742 if (cmd_list && cmd_list->next)
743 {
744 prefix = "--list-add:";
745 remote_client_send(rc, "--list-clear");
746 }
747 else
748 {
749 prefix = "file:";
750 }
751
752 work = cmd_list;
753 while (work)
754 {
755 const gchar *name;
756 gchar *text;
757
758 name = work->data;
759 work = work->next;
760
761 text = g_strconcat(prefix, name, NULL);
762 remote_client_send(rc, text);
763 g_free(text);
764
765 sent = TRUE;
766 }
767
768 if (path && !cmd_list && use_path)
769 {
770 gchar *text;
771
772 text = g_strdup_printf("file:%s", path);
773 remote_client_send(rc, text);
774 g_free(text);
775
776 sent = TRUE;
777 }
778
779 work = collection_list;
780 while (work)
781 {
782 const gchar *name;
783 gchar *text;
784
785 name = work->data;
786 work = work->next;
787
788 text = g_strdup_printf("file:%s", name);
789 remote_client_send(rc, text);
790 g_free(text);
791
792 sent = TRUE;
793 }
794
795 if (!started && !sent)
796 {
797 remote_client_send(rc, "raise");
798 }
799 }
800 else
801 {
802 print_term(_("Remote not available\n"));
803 }
804
805 _exit(0);
257 } 806 }
258 807
259 /* 808 /*
260 *----------------------------------------------------------------------------- 809 *-----------------------------------------------------------------------------
261 * command line parser (private) hehe, who needs popt anyway? 810 * command line parser (private) hehe, who needs popt anyway?
262 *----------------------------------------------------------------------------- 811 *-----------------------------------------------------------------------------
263 */ 812 */
264 813
814 static gint startup_blank = FALSE;
265 static gint startup_full_screen = FALSE; 815 static gint startup_full_screen = FALSE;
266 static gint startup_in_slideshow = FALSE; 816 static gint startup_in_slideshow = FALSE;
267 817 static gint startup_command_line_collection = FALSE;
268 static void parse_command_line(int argc, char *argv[], gchar **path, gchar **file) 818
269 { 819
820 static void parse_command_line_add_file(const gchar *new_path, gchar **path, gchar **file,
821 GList **list, GList **collection_list)
822 {
823 gchar *path_parsed;
824
825 path_parsed = g_strdup(new_path);
826 parse_out_relatives(path_parsed);
827
828 if (file_extension_match(new_path, ".gqv"))
829 {
830 *collection_list = g_list_append(*collection_list, path_parsed);
831 }
832 else
833 {
834 if (!*path) *path = remove_level_from_path(path_parsed);
835 if (!*file) *file = g_strdup(path_parsed);
836 *list = g_list_append(*list, path_parsed);
837 }
838 }
839
840 static void parse_command_line(int argc, char *argv[], gchar **path, gchar **file,
841 GList **cmd_list, GList **collection_list)
842 {
843 GList *list = NULL;
844 GList *remote_list = NULL;
845 gint remote_do = FALSE;
846
270 if (argc > 1) 847 if (argc > 1)
271 { 848 {
272 gint i; 849 gint i;
273 gchar *base_dir = get_current_dir(); 850 gchar *base_dir = get_current_dir();
274 i = 1; 851 i = 1;
275 while (i < argc) 852 while (i < argc)
276 { 853 {
277 gchar *cmd_line = argv[i]; 854 const gchar *cmd_line = argv[i];
278 gchar *cmd_all = g_strconcat(base_dir, "/", cmd_line, NULL); 855 gchar *cmd_all = concat_dir_and_file(base_dir, cmd_line);
279 856
280 if (!*path && cmd_line[0] == '/' && isdir(cmd_line)) 857 if (!*path && cmd_line[0] == '/' && isdir(cmd_line))
281 { 858 {
282 *path = g_strdup(cmd_line); 859 *path = g_strdup(cmd_line);
283 } 860 }
284 else if (!*path && isdir(cmd_all)) 861 else if (!*path && isdir(cmd_all))
285 { 862 {
286 *path = g_strdup(cmd_all); 863 *path = g_strdup(cmd_all);
287 } 864 }
288 else if (!*file && cmd_line[0] == '/' && isfile(cmd_line)) 865 else if (cmd_line[0] == '/' && isfile(cmd_line))
289 { 866 {
290 g_free(*path); 867 parse_command_line_add_file(cmd_line, path, file, &list, collection_list);
291 *path = remove_level_from_path(cmd_line); 868 }
292 *file = g_strdup(cmd_line); 869 else if (isfile(cmd_all))
293 } 870 {
294 else if (!*file && isfile(cmd_all)) 871 parse_command_line_add_file(cmd_all, path, file, &list, collection_list);
295 {
296 g_free(*path);
297 *path = remove_level_from_path(cmd_all);
298 *file = g_strdup(cmd_all);
299 } 872 }
300 else if (strcmp(cmd_line, "--debug") == 0) 873 else if (strcmp(cmd_line, "--debug") == 0)
301 { 874 {
302 debug = TRUE; 875 /* we now increment the debug state for verbosity */
303 printf("debugging output enabled\n"); 876 debug++;
877 printf("debugging output enabled (level %d)\n", debug);
304 } 878 }
305 else if (strcmp(cmd_line, "+t") == 0 || 879 else if (strcmp(cmd_line, "+t") == 0 ||
306 strcmp(cmd_line, "--with-tools") == 0) 880 strcmp(cmd_line, "--with-tools") == 0)
307 { 881 {
308 tools_float = FALSE; 882 tools_float = FALSE;
309 tools_hidden = FALSE; 883 tools_hidden = FALSE;
884
885 remote_list = g_list_append(remote_list, "+t");
310 } 886 }
311 else if (strcmp(cmd_line, "-t") == 0 || 887 else if (strcmp(cmd_line, "-t") == 0 ||
312 strcmp(cmd_line, "--without-tools") == 0) 888 strcmp(cmd_line, "--without-tools") == 0)
313 { 889 {
314 tools_hidden = TRUE; 890 tools_hidden = TRUE;
891
892 remote_list = g_list_append(remote_list, "-t");
315 } 893 }
316 else if (strcmp(cmd_line, "-f") == 0 || 894 else if (strcmp(cmd_line, "-f") == 0 ||
317 strcmp(cmd_line, "--fullscreen") == 0) 895 strcmp(cmd_line, "--fullscreen") == 0)
318 { 896 {
319 startup_full_screen = TRUE; 897 startup_full_screen = TRUE;
321 else if (strcmp(cmd_line, "-s") == 0 || 899 else if (strcmp(cmd_line, "-s") == 0 ||
322 strcmp(cmd_line, "--slideshow") == 0) 900 strcmp(cmd_line, "--slideshow") == 0)
323 { 901 {
324 startup_in_slideshow = TRUE; 902 startup_in_slideshow = TRUE;
325 } 903 }
904 else if (strcmp(cmd_line, "-l") == 0 ||
905 strcmp(cmd_line, "--list") == 0)
906 {
907 startup_command_line_collection = TRUE;
908 }
909 else if (strcmp(cmd_line, "-r") == 0 ||
910 strcmp(cmd_line, "--remote") == 0)
911 {
912 if (!remote_do)
913 {
914 remote_do = TRUE;
915 remote_list = gqview_remote_build_list(remote_list, argc, argv);
916 }
917 }
918 else if (strcmp(cmd_line, "-rh") == 0 ||
919 strcmp(cmd_line, "--remote-help") == 0)
920 {
921 gqview_remote_help();
922 exit (0);
923 }
924 else if (strcmp(cmd_line, "--blank") == 0)
925 {
926 startup_blank = TRUE;
927 }
928 else if (strcmp(cmd_line, "-v") == 0 ||
929 strcmp(cmd_line, "--version") == 0)
930 {
931 printf("GQview %s\n", VERSION);
932 exit (0);
933 }
934 else if (strcmp(cmd_line, "--alternate") == 0)
935 {
936 /* enable faster experimental algorithm */
937 printf("Alternate similarity algorithm enabled\n");
938 image_sim_alternate_set(TRUE);
939 }
326 else if (strcmp(cmd_line, "-h") == 0 || 940 else if (strcmp(cmd_line, "-h") == 0 ||
327 strcmp(cmd_line, "--help") == 0) 941 strcmp(cmd_line, "--help") == 0)
328 { 942 {
329 printf("GQview version %s\n", VERSION); 943 printf("GQview %s\n", VERSION);
330 printf(_("Usage: gqview [options] [path]\n\n")); 944 print_term(_("Usage: gqview [options] [path]\n\n"));
331 printf(_("valid options are:\n")); 945 print_term(_("valid options are:\n"));
332 printf(_(" +t, --with-tools force show of tools\n")); 946 print_term(_(" +t, --with-tools force show of tools\n"));
333 printf(_(" -t, --without-tools force hide of tools\n")); 947 print_term(_(" -t, --without-tools force hide of tools\n"));
334 printf(_(" -f, --fullscreen start in full screen mode\n")); 948 print_term(_(" -f, --fullscreen start in full screen mode\n"));
335 printf(_(" -s, --slideshow start in slideshow mode\n")); 949 print_term(_(" -s, --slideshow start in slideshow mode\n"));
336 printf(_(" --debug turn on debug output\n")); 950 print_term(_(" -l, --list open collection window for command line\n"));
337 printf(_(" -h, --help show this message\n\n")); 951 print_term(_(" -r, --remote send following commands to open window\n"));
952 print_term(_(" -rh,--remote-help print remote command list\n"));
953 print_term(_(" --debug turn on debug output\n"));
954 print_term(_(" -v, --version print version info\n"));
955 print_term(_(" -h, --help show this message\n\n"));
956
957 #if 0
958 /* these options are not officially supported!
959 * only for testing new features, no need to translate them */
960 print_term( " --alternate use alternate similarity algorithm\n");
961 #endif
962
338 exit (0); 963 exit (0);
339 } 964 }
340 else 965 else if (!remote_do)
341 { 966 {
342 printf(_("invalid or ignored: %s\nUse -help for options\n"), cmd_line); 967 gchar *buf;
343 } 968
969 buf = g_strdup_printf(_("invalid or ignored: %s\nUse --help for options\n"), cmd_line);
970 print_term(buf);
971 g_free(buf);
972 }
973
344 g_free(cmd_all); 974 g_free(cmd_all);
345 i++; 975 i++;
346 } 976 }
347 g_free(base_dir); 977 g_free(base_dir);
348 parse_out_relatives(*path); 978 parse_out_relatives(*path);
349 parse_out_relatives(*file); 979 parse_out_relatives(*file);
980 }
981
982 if (remote_do)
983 {
984 gqview_remote_control(argv[0], remote_list, *path, list, *collection_list);
985 }
986 g_list_free(remote_list);
987
988 if (list && list->next)
989 {
990 *cmd_list = list;
991 }
992 else
993 {
994 path_list_free(list);
995 *cmd_list = NULL;
350 } 996 }
351 } 997 }
352 998
353 /* 999 /*
354 *----------------------------------------------------------------------------- 1000 *-----------------------------------------------------------------------------
355 * startup, init, and exit 1001 * startup, init, and exit
356 *----------------------------------------------------------------------------- 1002 *-----------------------------------------------------------------------------
357 */ 1003 */
358 1004
359 static void setup_default_options() 1005 #define RC_HISTORY_NAME "history"
360 { 1006
1007 static void keys_load(void)
1008 {
1009 gchar *path;
1010
1011 path = g_strconcat(homedir(), "/", GQVIEW_RC_DIR, "/", RC_HISTORY_NAME, NULL);
1012 history_list_load(path);
1013 g_free(path);
1014 }
1015
1016 static void keys_save(void)
1017 {
1018 gchar *path;
1019
1020 path = g_strconcat(homedir(), "/", GQVIEW_RC_DIR, "/", RC_HISTORY_NAME, NULL);
1021 history_list_save(path);
1022 g_free(path);
1023 }
1024
1025 static void check_for_home_path(gchar *path)
1026 {
1027 gchar *buf;
1028
1029 buf = g_strconcat(homedir(), "/", path, NULL);
1030 if (!isdir(buf))
1031 {
1032 gchar *tmp;
1033
1034 tmp = g_strdup_printf(_("Creating GQview dir:%s\n"), buf);
1035 print_term(tmp);
1036 g_free(tmp);
1037
1038 if (!mkdir_utf8(buf, 0755))
1039 {
1040 tmp = g_strdup_printf(_("Could not create dir:%s\n"), buf);
1041 print_term(tmp);
1042 g_free(tmp);
1043 }
1044 }
1045 g_free(buf);
1046 }
1047
1048 static void setup_default_options(void)
1049 {
1050 gchar *path;
361 gint i; 1051 gint i;
362 1052
363 for(i=0; i<8; i++) 1053 for (i = 0; i < GQVIEW_EDITOR_SLOTS; i++)
364 { 1054 {
365 editor_name[i] = NULL; 1055 editor_name[i] = NULL;
366 editor_command[i] = NULL; 1056 editor_command[i] = NULL;
367 } 1057 }
368 1058
369 editor_name[0] = g_strdup(_("The Gimp")); 1059 editor_reset_defaults();
370 editor_command[0] = g_strdup("gimp"); 1060
371 1061 bookmark_add_default(_("Home"), homedir());
372 editor_name[1] = g_strdup(_("Electric Eyes")); 1062 path = concat_dir_and_file(homedir(), "Desktop");
373 editor_command[1] = g_strdup("ee"); 1063 bookmark_add_default(_("Desktop"), path);
374 1064 g_free(path);
375 editor_name[2] = g_strdup(_("XV")); 1065 path = concat_dir_and_file(homedir(), GQVIEW_RC_DIR_COLLECTIONS);
376 editor_command[2] = g_strdup("xv"); 1066 bookmark_add_default(_("Collections"), path);
377 1067 g_free(path);
378 editor_name[3] = g_strdup(_("Xpaint")); 1068
379 editor_command[3] = g_strdup("xpaint"); 1069 g_free(safe_delete_path);
380 1070 safe_delete_path = concat_dir_and_file(homedir(), GQVIEW_RC_DIR_TRASH);
381 custom_filter = g_strdup(".eim;"); 1071 }
382 } 1072
383 1073 static void exit_gqview_final(void)
384 void exit_gqview() 1074 {
385 { 1075 gchar *path;
386 full_screen_stop(); 1076 gchar *pathl;
387 1077 LayoutWindow *lw = NULL;
388 gdk_window_get_position (mainwindow->window, &main_window_x, &main_window_y); 1078
389 gdk_window_get_size(mainwindow->window, &main_window_w, &main_window_h); 1079 remote_close(gqview_remote);
390 1080
391 if (toolwindow) 1081 collect_manager_flush();
392 { 1082
393 gdk_window_get_position (toolwindow->window, &float_window_x, &float_window_y); 1083 if (layout_valid(&lw))
394 gdk_window_get_size(toolwindow->window, &float_window_w, &float_window_h); 1084 {
395 } 1085 main_window_maximized = window_maximized(lw->window);
1086 if (!main_window_maximized)
1087 {
1088 layout_geometry_get(NULL, &main_window_x, &main_window_y,
1089 &main_window_w, &main_window_h);
1090 }
1091 }
1092
1093 layout_geometry_get_dividers(NULL, &window_hdivider_pos, &window_vdivider_pos);
1094
1095 layout_views_get(NULL, &layout_view_tree, &layout_view_icons);
1096
1097 thumbnails_enabled = layout_thumb_get(NULL);
1098 layout_sort_get(NULL, &file_sort_method, &file_sort_ascending);
1099
1100 layout_geometry_get_tools(NULL, &float_window_x, &float_window_y,
1101 &float_window_w, &float_window_h, &float_window_divider);
1102 layout_tools_float_get(NULL, &tools_float, &tools_hidden);
1103 toolbar_hidden = layout_toolbar_hidden(NULL);
1104
396 save_options(); 1105 save_options();
1106 keys_save();
1107
1108 path = g_strconcat(homedir(), "/", GQVIEW_RC_DIR, "/accels", NULL);
1109 pathl = path_from_utf8(path);
1110 gtk_accel_map_save(pathl);
1111 g_free(pathl);
1112 g_free(path);
397 1113
398 gtk_main_quit(); 1114 gtk_main_quit();
399 } 1115 }
400 1116
1117 static GenericDialog *exit_dialog = NULL;
1118
1119 static void exit_confirm_cancel_cb(GenericDialog *gd, gpointer data)
1120 {
1121 exit_dialog = NULL;
1122 generic_dialog_close(gd);
1123 }
1124
1125 static void exit_confirm_exit_cb(GenericDialog *gd, gpointer data)
1126 {
1127 exit_dialog = NULL;
1128 generic_dialog_close(gd);
1129 exit_gqview_final();
1130 }
1131
1132 static gint exit_confirm_dlg(void)
1133 {
1134 GtkWidget *parent;
1135 LayoutWindow *lw;
1136
1137 if (exit_dialog)
1138 {
1139 gtk_window_present(GTK_WINDOW(exit_dialog->dialog));
1140 return TRUE;
1141 }
1142
1143 if (!collection_window_modified_exists()) return FALSE;
1144
1145 parent = NULL;
1146 lw = NULL;
1147 if (layout_valid(&lw))
1148 {
1149 parent = lw->window;
1150 }
1151
1152 exit_dialog = generic_dialog_new(_("GQview - exit"),
1153 "GQview", "exit", parent, FALSE,
1154 exit_confirm_cancel_cb, NULL);
1155 generic_dialog_add_message(exit_dialog, GTK_STOCK_DIALOG_QUESTION,
1156 _("Quit GQview"), _("Collections have been modified. Quit anyway?"));
1157 generic_dialog_add_button(exit_dialog, GTK_STOCK_QUIT, NULL, exit_confirm_exit_cb, TRUE);
1158
1159 gtk_widget_show(exit_dialog->dialog);
1160
1161 return TRUE;
1162 }
1163
1164 void exit_gqview(void)
1165 {
1166 layout_image_full_screen_stop(NULL);
1167
1168 if (exit_confirm_dlg()) return;
1169
1170 exit_gqview_final();
1171 }
1172
401 int main (int argc, char *argv[]) 1173 int main (int argc, char *argv[])
402 { 1174 {
1175 LayoutWindow *lw;
1176 gchar *path = NULL;
403 gchar *cmd_path = NULL; 1177 gchar *cmd_path = NULL;
404 gchar *cmd_file = NULL; 1178 gchar *cmd_file = NULL;
1179 GList *cmd_list = NULL;
1180 GList *collection_list = NULL;
1181 CollectionData *first_collection = NULL;
1182 gchar *buf;
1183 gchar *bufl;
405 1184
406 /* setup locale, i18n */ 1185 /* setup locale, i18n */
407 gtk_set_locale(); 1186 gtk_set_locale();
408 bindtextdomain (PACKAGE, LOCALEDIR); 1187 bindtextdomain (PACKAGE, LOCALEDIR);
1188 bind_textdomain_codeset (PACKAGE, "UTF-8");
409 textdomain (PACKAGE); 1189 textdomain (PACKAGE);
410 1190
411 /* setup random seed for random slideshow */ 1191 /* setup random seed for random slideshow */
412 srand (time (0)); 1192 srand(time(NULL));
413 1193
414 gtk_init (&argc, &argv); 1194 #if 0
415 gdk_imlib_init(); 1195 printf("GQview %s, This is a beta release.\n", VERSION);
416 1196 #endif
417 /* push the correct color depths to gtk, (for 8-bit psuedo color displays) 1197
418 * they should be popped, too, I guess... 1198 layout_order = g_strdup("123");
419 */
420 gtk_widget_push_visual(gdk_imlib_get_visual());
421 gtk_widget_push_colormap(gdk_imlib_get_colormap());
422
423 setup_default_options(); 1199 setup_default_options();
424 load_options(); 1200 load_options();
425 1201
426 parse_command_line(argc, argv, &cmd_path, &cmd_file); 1202 parse_command_line(argc, argv, &cmd_path, &cmd_file, &cmd_list, &collection_list);
427 1203
428 if (cmd_path) 1204 gtk_init (&argc, &argv);
429 current_path = g_strdup(cmd_path); 1205
1206 if (gtk_major_version < GTK_MAJOR_VERSION ||
1207 (gtk_major_version == GTK_MAJOR_VERSION && gtk_minor_version < GTK_MINOR_VERSION) )
1208 {
1209 gchar *msg;
1210 print_term("!!! This is a friendly warning.\n");
1211 print_term("!!! The version of GTK+ in use now is older than when GQview was compiled.\n");
1212 msg = g_strdup_printf("!!! compiled with GTK+-%d.%d\n", GTK_MAJOR_VERSION, GTK_MINOR_VERSION);
1213 print_term(msg);
1214 g_free(msg);
1215 msg = g_strdup_printf("!!! running with GTK+-%d.%d\n", gtk_major_version, gtk_minor_version);
1216 print_term(msg);
1217 g_free(msg);
1218 print_term("!!! GQview may quit unexpectedly with a relocation error.\n");
1219 }
1220
1221 check_for_home_path(GQVIEW_RC_DIR);
1222 check_for_home_path(GQVIEW_RC_DIR_COLLECTIONS);
1223 check_for_home_path(GQVIEW_CACHE_RC_THUMB);
1224 check_for_home_path(GQVIEW_CACHE_RC_METADATA);
1225
1226 keys_load();
1227 filter_add_defaults();
1228 filter_rebuild();
1229
1230 buf = g_strconcat(homedir(), "/", GQVIEW_RC_DIR, "/accels", NULL);
1231 bufl = path_from_utf8(buf);
1232 gtk_accel_map_load(bufl);
1233 g_free(bufl);
1234 g_free(buf);
1235
1236 if (startup_blank)
1237 {
1238 g_free(cmd_path);
1239 cmd_path = NULL;
1240 g_free(cmd_file);
1241 cmd_file = NULL;
1242 path_list_free(cmd_list);
1243 cmd_list = NULL;
1244 path_list_free(collection_list);
1245 collection_list = NULL;
1246
1247 path = NULL;
1248 }
1249 else if (cmd_path)
1250 {
1251 path = g_strdup(cmd_path);
1252 }
430 else if (startup_path_enable && startup_path && isdir(startup_path)) 1253 else if (startup_path_enable && startup_path && isdir(startup_path))
431 current_path = g_strdup(startup_path); 1254 {
1255 path = g_strdup(startup_path);
1256 }
432 else 1257 else
433 current_path = get_current_dir(); 1258 {
434 1259 path = get_current_dir();
435 create_main_window(); 1260 }
436 update_edit_menus(mainwindow_accel_grp); 1261
437 rebuild_file_filter(); 1262 lw = layout_new(NULL, tools_float, tools_hidden);
438 filelist_refresh(); 1263 layout_sort_set(lw, file_sort_method, file_sort_ascending);
439 1264
440 init_dnd(); 1265 if (collection_list && !startup_command_line_collection)
441 1266 {
442 while(gtk_events_pending()) gtk_main_iteration(); 1267 GList *work;
443 image_change_to(cmd_file); 1268
1269 work = collection_list;
1270 while (work)
1271 {
1272 CollectWindow *cw;
1273 const gchar *path;
1274
1275 path = work->data;
1276 work = work->next;
1277
1278 cw = collection_window_new(path);
1279 if (!first_collection && cw) first_collection = cw->cd;
1280 }
1281 }
1282
1283 if (cmd_list ||
1284 (startup_command_line_collection && collection_list))
1285 {
1286 CollectionData *cd;
1287 GList *work;
1288
1289 if (startup_command_line_collection)
1290 {
1291 CollectWindow *cw;
1292
1293 cw = collection_window_new("");
1294 cd = cw->cd;
1295 }
1296 else
1297 {
1298 cd = collection_new(""); /* if we pass NULL, untitled counter is falsely increm. */
1299 gqview_command_collection = cd;
1300 }
1301
1302 g_free(cd->path);
1303 cd->path = NULL;
1304 g_free(cd->name);
1305 cd->name = g_strdup(_("Command line"));
1306
1307 collection_path_changed(cd);
1308
1309 work = cmd_list;
1310 while (work)
1311 {
1312 collection_add(cd, (gchar *)work->data, FALSE);
1313 work = work->next;
1314 }
1315
1316 work = collection_list;
1317 while (work)
1318 {
1319 collection_load(cd, (gchar *)work->data, TRUE);
1320 work = work->next;
1321 }
1322
1323 layout_set_path(lw, path);
1324 if (cd->list) layout_image_set_collection(lw, cd, cd->list->data);
1325
1326 /* mem leak, we never unref this collection when !startup_command_line_collection
1327 * (the image view of the main window does not hold a ref to the collection)
1328 * this is sort of unavoidable, for if it did hold a ref, next/back
1329 * may not work as expected when closing collection windows.
1330 *
1331 * collection_unref(cd);
1332 */
1333
1334 }
1335 else if (cmd_file)
1336 {
1337 layout_set_path(lw, cmd_file);
1338 }
1339 else
1340 {
1341 layout_set_path(lw, path);
1342 if (first_collection)
1343 {
1344 layout_image_set_collection(lw, first_collection,
1345 collection_get_first(first_collection));
1346 }
1347 }
444 1348
445 g_free(cmd_path); 1349 g_free(cmd_path);
446 g_free(cmd_file); 1350 g_free(cmd_file);
447 1351 path_list_free(cmd_list);
448 if (startup_full_screen) full_screen_toggle(); 1352 path_list_free(collection_list);
449 if (startup_in_slideshow) slideshow_start(); 1353 g_free(path);
1354
1355 if (startup_full_screen) layout_image_full_screen_start(lw);
1356 if (startup_in_slideshow) layout_image_slideshow_start(lw);
1357
1358 buf = g_strconcat(homedir(), "/", GQVIEW_RC_DIR, "/.command", NULL);
1359 gqview_remote = remote_server_open(buf);
1360 remote_server_subscribe(gqview_remote, gqview_remote_cb, NULL);
1361 g_free(buf);
450 1362
451 gtk_main (); 1363 gtk_main ();
452 return 0; 1364 return 0;
453 } 1365 }
454 1366
455