1 /* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 4; tab-width: 4 -*- */
4 * Copyright (C) 2000 Naba Kumar <naba@gnome.org>
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the Free
8 * Software Foundation; either version 2 of the License, or (at your option)
11 * This program is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
13 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22 #include <libanjuta/anjuta-shell.h>
23 #include <libanjuta/anjuta-debug.h>
24 #include <libanjuta/anjuta-utils.h>
25 #include <libanjuta/anjuta-save-prompt.h>
26 #include <libanjuta/anjuta-plugin-manager.h>
27 #include <libanjuta/resources.h>
28 #include <libanjuta/interfaces/ianjuta-file-loader.h>
29 #include <libanjuta/interfaces/ianjuta-file.h>
33 #define ANJUTA_REMEMBERED_PLUGINS "remembered-plugins"
34 #define ANJUTA_SESSION_SKIP_LAST "session-skip-last"
35 #define ANJUTA_SESSION_SKIP_LAST_FILES "session-skip-last-files"
36 #define USER_SESSION_PATH_NEW (anjuta_util_get_user_cache_file_path ("session/", NULL))
38 #define DEFAULT_PROFILE "file://"PACKAGE_DATA_DIR"/profiles/default.profile"
39 #define USER_PROFILE_NAME "user"
41 #define ANJUTA_PIXMAP_SPLASH_SCREEN "anjuta_splash.png"
43 static gchar
*system_restore_session
= NULL
;
46 on_anjuta_delete_event (AnjutaWindow
*win
, GdkEvent
*event
, gpointer data
)
48 AnjutaPluginManager
*plugin_manager
;
49 AnjutaProfileManager
*profile_manager
;
50 AnjutaProfile
*current_profile
;
51 AnjutaSavePrompt
*save_prompt
;
52 gchar
*remembered_plugins
;
54 DEBUG_PRINT ("%s", "AnjutaWindow delete event");
56 plugin_manager
= anjuta_shell_get_plugin_manager (ANJUTA_SHELL (win
), NULL
);
57 profile_manager
= anjuta_shell_get_profile_manager (ANJUTA_SHELL (win
), NULL
);
59 /* Save remembered plugins */
61 anjuta_plugin_manager_get_remembered_plugins (plugin_manager
);
62 g_settings_set_string (win
->settings
,
63 ANJUTA_REMEMBERED_PLUGINS
,
65 g_free (remembered_plugins
);
67 /* Check for unsaved data */
68 save_prompt
= anjuta_save_prompt_new (GTK_WINDOW (win
));
69 anjuta_shell_save_prompt (ANJUTA_SHELL (win
), save_prompt
, NULL
);
71 if (anjuta_save_prompt_get_items_count (save_prompt
) > 0)
73 switch (gtk_dialog_run (GTK_DIALOG (save_prompt
)))
75 case GTK_RESPONSE_DELETE_EVENT
:
76 case ANJUTA_SAVE_PROMPT_RESPONSE_CANCEL
:
77 gtk_widget_destroy (GTK_WIDGET (save_prompt
));
80 case ANJUTA_SAVE_PROMPT_RESPONSE_DISCARD
:
81 case ANJUTA_SAVE_PROMPT_RESPONSE_SAVE_CLOSE
:
86 /* Wait for files to be really saved (asyncronous operation) */
87 if (win
->save_count
> 0)
89 g_message ("Waiting for %d file(s) to be saved!", win
->save_count
);
90 while (win
->save_count
> 0)
92 g_main_context_iteration (NULL
, TRUE
);
96 /* If current active profile is "user", save current session as
99 current_profile
= anjuta_profile_manager_get_current (profile_manager
);
100 if (strcmp (anjuta_profile_get_name (current_profile
), "user") == 0)
103 session_dir
= USER_SESSION_PATH_NEW
;
104 anjuta_shell_session_save (ANJUTA_SHELL (win
), session_dir
, NULL
);
105 g_free (session_dir
);
108 anjuta_shell_notify_exit (ANJUTA_SHELL (win
), NULL
);
110 gtk_widget_destroy (GTK_WIDGET (save_prompt
));
113 if (g_object_get_data (G_OBJECT (win
), "__proper_shutdown"))
115 gtk_widget_hide (GTK_WIDGET (win
));
116 anjuta_plugin_manager_unload_all_plugins
117 (anjuta_shell_get_plugin_manager (ANJUTA_SHELL (win
), NULL
));
123 on_anjuta_destroy (GtkWidget
* w
, gpointer data
)
125 DEBUG_PRINT ("%s", "AnjutaWindow destroy event");
131 on_profile_scoped (AnjutaProfileManager
*profile_manager
,
132 AnjutaProfile
*profile
, AnjutaWindow
*win
)
135 static gboolean first_time
= TRUE
;
137 DEBUG_PRINT ("Profile scoped: %s", anjuta_profile_get_name (profile
));
138 if (strcmp (anjuta_profile_get_name (profile
), USER_PROFILE_NAME
) != 0)
141 DEBUG_PRINT ("%s", "User profile loaded; Restoring user session");
143 /* If profile scoped to "user", restore user session */
144 if (system_restore_session
)
146 session_dir
= system_restore_session
;
147 system_restore_session
= NULL
;
151 session_dir
= USER_SESSION_PATH_NEW
;
160 /* Clear the files list since we don't want to load them later */
161 AnjutaSession
*session
;
162 session
= anjuta_session_new (session_dir
);
163 anjuta_session_set_string_list (session
, "File Loader",
165 anjuta_session_sync (session
);
166 g_object_unref (session
);
169 /* Restore session */
170 anjuta_shell_session_load (ANJUTA_SHELL (win
), session_dir
, NULL
);
171 g_free (session_dir
);
175 on_profile_descoped (AnjutaProfileManager
*profile_manager
,
176 AnjutaProfile
*profile
, AnjutaWindow
*win
)
180 DEBUG_PRINT ("Profile descoped: %s", anjuta_profile_get_name (profile
));
181 if (strcmp (anjuta_profile_get_name (profile
), USER_PROFILE_NAME
) != 0)
184 DEBUG_PRINT ("%s", "User profile descoped; Saving user session");
186 /* If profile descoped from is "user", save user session */
187 session_dir
= USER_SESSION_PATH_NEW
;
189 /* Save current session */
190 anjuta_shell_session_save (ANJUTA_SHELL (win
), session_dir
, NULL
);
191 g_free (session_dir
);
194 /* This extracts the project URI saved in the session so that it could be
195 * loaded sequencially. Returned string must be freed.
198 extract_project_from_session (const gchar
* session_dir
)
200 AnjutaSession
*session
;
202 GFile
*project
= NULL
;
204 session
= anjuta_session_new (session_dir
);
206 files
= anjuta_session_get_string_list (session
, "File Loader", "Files");
208 /* Find project file */
210 for (node
= files
; node
!= NULL
; node
= g_list_next (node
))
212 gchar
*uri
= node
->data
;
215 if (anjuta_util_is_project_file (uri
))
217 if (project
!= NULL
) g_object_unref (project
);
218 project
= anjuta_session_get_file_from_relative_uri (session
, uri
, NULL
);
224 g_object_unref (session
);
230 create_window (GFile
**files
, int n_files
, gboolean no_splash
,
231 gboolean no_session
, gboolean no_files
,
232 gboolean proper_shutdown
, const gchar
*geometry
)
234 AnjutaPluginManager
*plugin_manager
;
235 AnjutaProfileManager
*profile_manager
;
237 AnjutaStatus
*status
;
238 AnjutaProfile
*profile
;
239 GFile
*session_profile
;
240 gchar
*remembered_plugins
;
241 GFile
*project
= NULL
;
242 GFile
*template = NULL
;
243 gchar
*profile_name
= NULL
;
244 gchar
*im_file
= NULL
;
245 GError
*error
= NULL
;
247 /* Initialize application */
248 win
= ANJUTA_WINDOW (anjuta_window_new ());
249 status
= anjuta_shell_get_status (ANJUTA_SHELL (win
), NULL
);
250 anjuta_status_progress_add_ticks (status
, 1);
252 im_file
= anjuta_res_get_pixmap_file (ANJUTA_PIXMAP_SPLASH_SCREEN
);
254 gtk_window_set_role (GTK_WINDOW (win
), "anjuta-app");
255 gtk_window_set_auto_startup_notification(TRUE
);
256 gtk_window_set_default_icon_name ("anjuta");
257 gtk_window_set_auto_startup_notification(FALSE
);
261 anjuta_status_set_splash (status
, im_file
, 100);
265 anjuta_status_disable_splash (status
, no_splash
);
269 g_object_set_data (G_OBJECT (win
), "__proper_shutdown", "1");
271 g_signal_connect (G_OBJECT (win
), "delete_event",
272 G_CALLBACK (on_anjuta_delete_event
), NULL
);
273 g_signal_connect (G_OBJECT (win
), "destroy",
274 G_CALLBACK (on_anjuta_destroy
), NULL
);
276 /* Setup application framework */
277 plugin_manager
= anjuta_shell_get_plugin_manager (ANJUTA_SHELL (win
),
279 profile_manager
= anjuta_shell_get_profile_manager (ANJUTA_SHELL (win
),
282 /* Restore remembered plugins */
284 g_settings_get_string (win
->settings
, ANJUTA_REMEMBERED_PLUGINS
);
285 if (remembered_plugins
)
286 anjuta_plugin_manager_set_remembered_plugins (plugin_manager
,
288 g_free (remembered_plugins
);
290 /* Prepare profile */
291 profile
= anjuta_profile_new (USER_PROFILE_NAME
, plugin_manager
);
292 session_profile
= g_file_new_for_uri (DEFAULT_PROFILE
);
293 anjuta_profile_add_plugins_from_xml (profile
, session_profile
,
297 anjuta_util_dialog_error (GTK_WINDOW (win
), "%s", error
->message
);
298 g_error_free (error
);
301 g_object_unref (session_profile
);
303 /* Load user session profile */
304 profile_name
= g_path_get_basename (DEFAULT_PROFILE
);
305 session_profile
= anjuta_util_get_user_cache_file (profile_name
, NULL
);
306 if (g_file_query_exists (session_profile
, NULL
))
308 anjuta_profile_add_plugins_from_xml (profile
, session_profile
,
312 anjuta_util_dialog_error (GTK_WINDOW (win
), "%s", error
->message
);
313 g_error_free (error
);
317 anjuta_profile_set_sync_file (profile
, session_profile
);
318 g_object_unref (session_profile
);
319 g_free (profile_name
);
322 anjuta_profile_manager_freeze (profile_manager
);
323 anjuta_profile_manager_push (profile_manager
, profile
, &error
);
326 anjuta_util_dialog_error (GTK_WINDOW (win
), "%s", error
->message
);
327 g_error_free (error
);
331 if (files
|| geometry
)
334 AnjutaSession
*session
;
336 GList
*files_load
= NULL
;
338 /* Reset default session */
339 session_dir
= USER_SESSION_PATH_NEW
;
341 project
= extract_project_from_session (session_dir
);
344 session
= anjuta_session_new (session_dir
);
345 anjuta_session_clear (session
);
347 anjuta_session_set_string (session
, "Anjuta", "Geometry",
350 /* Identify non-project files and set them for loading in session */
351 for (i
= 0; i
< n_files
; i
++)
353 gchar
* file
= g_file_get_path (files
[i
]);
356 if (anjuta_util_is_project_file (file
))
358 /* Pick up the first project file for loading later */
360 g_object_ref (project
);
362 else if (anjuta_util_is_template_file (file
))
365 g_object_ref (template);
369 files_load
= g_list_prepend (files_load
, g_file_get_uri (files
[i
]));
374 anjuta_session_set_string_list (session
, "File Loader", "Files",
376 g_list_foreach (files_load
, (GFunc
)g_free
, NULL
);
377 g_list_free (files_load
);
379 anjuta_session_sync (session
);
380 g_object_unref (session
);
381 g_free (session_dir
);
386 AnjutaSession
*session
;
388 /* Load user session */
389 session_dir
= USER_SESSION_PATH_NEW
;
391 /* If preferences is set to not load last session, clear it */
393 g_settings_get_boolean (win
->settings
,
394 ANJUTA_SESSION_SKIP_LAST
))
396 /* Reset default session */
397 session
= anjuta_session_new (session_dir
);
398 anjuta_session_clear (session
);
399 g_object_unref (session
);
401 /* If preferences is set to not load last project, clear it */
403 g_settings_get_boolean (win
->settings
,
404 ANJUTA_SESSION_SKIP_LAST_FILES
))
406 session
= anjuta_session_new (session_dir
);
407 anjuta_session_set_string_list (session
, "File Loader",
409 anjuta_session_sync (session
);
410 g_object_unref (session
);
412 /* Otherwise, load session normally */
415 project
= extract_project_from_session (session_dir
);
417 g_free (session_dir
);
420 /* Prepare for session save and load on profile change */
421 g_signal_connect (profile_manager
, "profile-scoped",
422 G_CALLBACK (on_profile_scoped
), win
);
423 /* Load project file */
424 if ((project
!= NULL
) && (template == NULL
))
426 IAnjutaFileLoader
*loader
;
427 loader
= anjuta_shell_get_interface (ANJUTA_SHELL (win
),
428 IAnjutaFileLoader
, NULL
);
429 ianjuta_file_loader_load (loader
, project
, FALSE
, NULL
);
430 g_object_unref (project
);
432 anjuta_profile_manager_thaw (profile_manager
, &error
);
436 anjuta_util_dialog_error (GTK_WINDOW (win
), "%s", error
->message
);
437 g_error_free (error
);
440 g_signal_connect (profile_manager
, "profile-descoped",
441 G_CALLBACK (on_profile_descoped
), win
);
443 anjuta_status_progress_tick (status
, NULL
, _("Loaded Session…"));
444 anjuta_status_disable_splash (status
, TRUE
);
446 /* Load template file */
447 if (template != NULL
)
449 IAnjutaFileLoader
*loader
;
450 loader
= anjuta_shell_get_interface (ANJUTA_SHELL (win
),
451 IAnjutaFileLoader
, NULL
);
452 ianjuta_file_loader_load (loader
, template, FALSE
, NULL
);
453 g_object_unref (template);
461 G_DEFINE_TYPE (Anjuta
, anjuta
, GTK_TYPE_APPLICATION
)
464 anjuta_finalize (GObject
*object
)
466 G_OBJECT_CLASS (anjuta_parent_class
)->finalize (object
);
470 anjuta_open (GApplication
*application
,
476 GList
* windows
= gtk_application_get_windows (GTK_APPLICATION (application
));
477 AnjutaWindow
*win
= ANJUTA_WINDOW (windows
->data
);
478 IAnjutaFileLoader
* loader
=
479 anjuta_shell_get_interface(ANJUTA_SHELL(win
), IAnjutaFileLoader
, NULL
);
484 /* Identify non-project files and set them for loading in session */
485 for (i
= 0; i
< n_files
; i
++)
487 gchar
* file
= g_file_get_path (files
[i
]);
490 if (anjuta_util_is_project_file (file
))
492 AnjutaWindow
* new_win
= create_window (files
, n_files
,
493 TRUE
, TRUE
, FALSE
, FALSE
, NULL
);
494 gtk_application_add_window (GTK_APPLICATION (application
),
495 GTK_WINDOW (new_win
));
496 gtk_widget_show (GTK_WIDGET (new_win
));
503 for (i
= 0; i
< n_files
; i
++)
505 ianjuta_file_loader_load(loader
, files
[i
], FALSE
, NULL
);
510 anjuta_activate (GApplication
*application
)
512 /* Show first window */
513 GList
* windows
= gtk_application_get_windows (GTK_APPLICATION (application
));
515 gtk_window_present (GTK_WINDOW (g_list_last (windows
)->data
));
519 anjuta_init (Anjuta
*anjuta
)
525 anjuta_class_init (AnjutaClass
*klass
)
527 GObjectClass
* object_class
= G_OBJECT_CLASS (klass
);
528 GApplicationClass
* app_class
= G_APPLICATION_CLASS (klass
);
530 object_class
->finalize
= anjuta_finalize
;
532 app_class
->open
= anjuta_open
;
533 app_class
->activate
= anjuta_activate
;
541 return g_object_new (anjuta_get_type (),
542 "application-id", "org.gnome.anjuta",
543 "flags", G_APPLICATION_HANDLES_OPEN
,