**
** \legal
** Copyright (c) 2002-2005 Robert B. Quattlebaum Jr., Adrian Bentley
-** Copyright (c) 2007 Chris Moore
+** Copyright (c) 2007, 2008 Chris Moore
**
** This package is free software; you can redistribute it and/or
** modify it under the terms of the GNU General Public License as
#include <gtk/gtk.h>
#include <synfig/loadcanvas.h>
+#include <synfig/savecanvas.h>
#include "app.h"
#include "about.h"
#include "devicetracker.h"
#include "dialog_tooloptions.h"
+#include "widget_enum.h"
#include "autorecover.h"
bool studio::App::use_colorspace_gamma=true;
bool studio::App::single_threaded=false;
+bool studio::App::restrict_radius_ducks=false;
+String studio::App::browser_command("firefox");
static int max_recent_files_=25;
int studio::App::get_max_recent_files() { return max_recent_files_; }
value=strprintf("%i",App::auto_recover->get_timeout());
return true;
}
+ if(key=="restrict_radius_ducks")
+ {
+ value=strprintf("%i",(int)App::restrict_radius_ducks);
+ return true;
+ }
+ if(key=="browser_command")
+ {
+ value=App::browser_command;
+ return true;
+ }
return synfigapp::Settings::get_value(key,value);
}
App::single_threaded=i;
return true;
}
+ if(key=="restrict_radius_ducks")
+ {
+ int i(atoi(value.c_str()));
+ App::restrict_radius_ducks=i;
+ return true;
+ }
+ if(key=="browser_command")
+ {
+ App::browser_command=value;
+ return true;
+ }
return synfigapp::Settings::set_value(key,value);
}
ret.push_back("use_colorspace_gamma");
ret.push_back("single_threaded");
ret.push_back("auto_recover_backup_interval");
+ ret.push_back("restrict_radius_ducks");
+ ret.push_back("browser_command");
return ret;
}
};
device_tracker=new studio::DeviceTracker();
studio_init_cb.task(_("Init Tools..."));
+
+ /* row 1 */
state_manager->add_state(&state_normal);
state_manager->add_state(&state_smooth_move);
state_manager->add_state(&state_scale);
state_manager->add_state(&state_rotate);
+ studio_init_cb.task(_("Init ModMirror...")); module_list_.push_back(new ModMirror()); module_list_.back()->start();
+ /* row 2 */
state_manager->add_state(&state_bline);
-
-
state_manager->add_state(&state_circle);
state_manager->add_state(&state_rectangle);
-
state_manager->add_state(&state_gradient);
- state_manager->add_state(&state_eyedrop);
- state_manager->add_state(&state_fill);
-
- state_manager->add_state(&state_zoom);
+ if(!getenv("SYNFIG_DISABLE_POLYGON")) state_manager->add_state(&state_polygon); // Enabled - for working without ducks
- // Enabled - it's useful to be able to work with polygons without tangent ducks getting in the way.
- // I know we can switch tangent ducks off, but why not allow this kind of layer as well?
- if(!getenv("SYNFIG_DISABLE_POLYGON")) state_manager->add_state(&state_polygon);
-
- // Enabled for now. Let's see whether they're good enough yet.
- if(!getenv("SYNFIG_DISABLE_DRAW" )) state_manager->add_state(&state_draw);
+ /* row 3 */
+ if(!getenv("SYNFIG_DISABLE_DRAW" )) state_manager->add_state(&state_draw); // Enabled for now. Let's see whether they're good enough yet.
if(!getenv("SYNFIG_DISABLE_SKETCH" )) state_manager->add_state(&state_sketch);
+ state_manager->add_state(&state_fill);
+ state_manager->add_state(&state_eyedrop);
+ state_manager->add_state(&state_zoom);
// Disabled by default - it doesn't work properly?
if(getenv("SYNFIG_ENABLE_WIDTH" )) state_manager->add_state(&state_width);
studio_init_cb.task(_("Init ModPalette..."));
module_list_.push_back(new ModPalette()); module_list_.back()->start();
- studio_init_cb.task(_("Init ModMirror..."));
- module_list_.push_back(new ModMirror()); module_list_.back()->start();
-
-
studio_init_cb.task(_("Init Setup Dialog..."));
dialog_setup=new studio::Dialog_Setup();
studio_init_cb.amount_complete(9900,10000);
+ bool opened_any = false;
if(auto_recover->recovery_needed())
{
splash_screen.hide();
- if(
- get_ui_interface()->yes_no(
- _("Auto Recovery"),
- _("Synfig Studio seems to have crashed\n"
- "before you could save all your files.\n"
- "Would you like to re-open those files\n"
- "and recover your unsaved changes?")
- )==synfigapp::UIInterface::RESPONSE_YES
- )
+ if (get_ui_interface()->yes_no(_("Auto Recovery"),
+ _("Synfig Studio seems to have crashed\n"
+ "before you could save all your files.\n"
+ "Would you like to re-open those files\n"
+ "and recover your unsaved changes?")) ==
+ synfigapp::UIInterface::RESPONSE_YES)
{
- if(!auto_recover->recover())
- {
- get_ui_interface()->error(_("Unable to fully recover from previous crash"));
- }
+ int number_recovered;
+ if(!auto_recover->recover(number_recovered))
+ if (number_recovered)
+ get_ui_interface()->error(_("Unable to fully recover from previous crash"));
+ else
+ get_ui_interface()->error(_("Unable to recover from previous crash"));
else
- get_ui_interface()->error(
- _("Synfig Studio has attempted to recover\n"
- "from a previous crash. The files that it has\n"
- "recovered are NOT YET SAVED. It would be a good\n"
- "idea to review them and save them now.")
- );
+ get_ui_interface()->error(
+ _("Synfig Studio has attempted to recover\n"
+ "from a previous crash. The files that it has\n"
+ "recovered are NOT YET SAVED. It would be a good\n"
+ "idea to review them and save them now."));
+
+ if (number_recovered)
+ opened_any = true;
}
splash_screen.show();
}
// Look for any files given on the command line,
// and load them if found.
- bool opened_any = false;
for(;*argc>=1;(*argc)--)
if((*argv)[*argc] && (*argv)[*argc][0]!='-')
{
synfigapp::Main::settings().set_value("pref.distance_system","pt");
synfigapp::Main::settings().set_value("pref.use_colorspace_gamma","1");
synfigapp::Main::settings().set_value("pref.single_threaded","0");
+ synfigapp::Main::settings().set_value("pref.restrict_radius_ducks","0");
synfigapp::Main::settings().set_value("window.toolbox.pos","4 4");
}
dialog->add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
dialog->add_button(Gtk::Stock::SAVE, Gtk::RESPONSE_ACCEPT);
+ Widget_Enum *file_type_enum = 0;
+ if (preference == ANIMATION_DIR_PREFERENCE)
+ {
+ file_type_enum = manage(new Widget_Enum());
+ file_type_enum->set_param_desc(ParamDesc().set_hint("enum")
+ .add_enum_value(synfig::RELEASE_VERSION_0_61_08, "0.61.08", strprintf("0.61.08 (%s)", _("current")))
+ .add_enum_value(synfig::RELEASE_VERSION_0_61_07, "0.61.07", "0.61.07")
+ .add_enum_value(synfig::RELEASE_VERSION_0_61_06, "0.61.06", strprintf("0.61.06 %s", _("and older"))));
+ file_type_enum->set_value(RELEASE_VERSION_END-1); // default to the most recent version
+
+ Gtk::HBox *hbox = manage(new Gtk::HBox);
+ hbox->pack_start(*manage(new Gtk::Label(_("File Format Version: "))),Gtk::PACK_SHRINK,0);
+ hbox->pack_start(*file_type_enum,Gtk::PACK_EXPAND_WIDGET,0);
+ hbox->show_all();
+
+ dialog->set_extra_widget(*hbox);
+ }
+
if (filename.empty())
dialog->set_filename(prev_path);
else
}
if(dialog->run() == GTK_RESPONSE_ACCEPT) {
+ if (preference == ANIMATION_DIR_PREFERENCE)
+ set_file_version(synfig::ReleaseVersion(file_type_enum->get_value()));
filename = dialog->get_filename();
info("Saving preference %s = '%s' in App::dialog_save_file()", preference.c_str(), dirname(filename).c_str());
_preferences.set_value(preference, dirname(filename));
dialog.run();
}
+static bool
+try_open_url(const std::string &url)
+{
+#ifdef WIN32
+ return ShellExecute(GetDesktopWindow(), "open", url.c_str(), NULL, NULL, SW_SHOW);
+#else // WIN32
+ gchar* argv[3] = {strdup(App::browser_command.c_str()), strdup(url.c_str()), NULL};
+
+ GError* gerror = NULL;
+ gboolean retval;
+ retval = g_spawn_async(NULL, argv, NULL, G_SPAWN_SEARCH_PATH, NULL, NULL, NULL, &gerror);
+ free(argv[0]);
+ free(argv[1]);
+
+ if (!retval)
+ {
+ error(_("Could not execute specified web browser: %s"), gerror->message);
+ g_error_free(gerror);
+ return false;
+ }
+
+ return true;
+#endif // WIN32
+}
+
+void
+App::dialog_help()
+{
+ if (!try_open_url("http://synfig.org/Documentation"))
+ {
+ Gtk::MessageDialog dialog(_("Documentation"), false, Gtk::MESSAGE_INFO, Gtk::BUTTONS_CLOSE, true);
+ dialog.set_secondary_text(_("Documentation for Synfig Studio is available on the website:\n\nhttp://www.synfig.org/Documentation"));
+ dialog.set_title(_("Help"));
+ dialog.run();
+ }
+}
+
+void
+App::open_url(const std::string &url)
+{
+ try_open_url(url);
+}
+
bool
App::dialog_entry(const std::string &title, const std::string &message,std::string &text)
{
if(canvas && get_instance(canvas))
{
get_instance(canvas)->find_canvas_view(canvas)->present();
- throw (String)strprintf(_("\"%s\" appears to already be open!"),filename.c_str());
+ info("%s is already open", filename.c_str());
+ // throw (String)strprintf(_("\"%s\" appears to already be open!"),filename.c_str());
}
- if(!canvas)
- throw (String)strprintf(_("Unable to open file \"%s\""),filename.c_str());
+ else
+ {
+ if(!canvas)
+ throw (String)strprintf(_("Unable to open file \"%s\""),filename.c_str());
- add_recent_file(as);
+ add_recent_file(as);
- handle<Instance> instance(Instance::create(canvas));
+ handle<Instance> instance(Instance::create(canvas));
- if(!instance)
- throw (String)strprintf(_("Unable to create instance for \"%s\""),filename.c_str());
+ if(!instance)
+ throw (String)strprintf(_("Unable to create instance for \"%s\""),filename.c_str());
- one_moment.hide();
+ one_moment.hide();
- if(instance->is_updated() && App::dialog_yes_no(_("CVS Update"), _("There appears to be a newer version of this file available on the CVS repository.\nWould you like to update now? (It would probably be a good idea)")))
- instance->dialog_cvs_update();
+ if(instance->is_updated() && App::dialog_yes_no(_("CVS Update"), _("There appears to be a newer version of this file available on the CVS repository.\nWould you like to update now? (It would probably be a good idea)")))
+ instance->dialog_cvs_update();
+ }
}
catch(String x)
{
}
void
-App::dialog_open()
+App::dialog_open(string filename)
{
- string filename="*.sif";
+ if (filename.empty())
+ filename="*.sif";
while(dialog_open_file("Open", filename, ANIMATION_DIR_PREFERENCE))
{