diff options
Diffstat (limited to 'src')
152 files changed, 1445 insertions, 1489 deletions
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index a1f5fc3dd..680d3bae5 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -336,7 +336,6 @@ set(inkscape_SRC icon-size.h id-clash.h # ige-mac-menu.h - inkscape-private.h inkscape-version.h inkscape.h interface.h @@ -518,10 +517,19 @@ set(inkscape_SRC # make executable for INKSCAPE add_executable(inkscape ${main_SRC} ${inkscape_SRC} ${sp_SRC}) +if(UNIX) +# message after building. +add_custom_command( + TARGET inkscape + POST_BUILD MAIN_DEPENDENCY inkscape + COMMAND ${CMAKE_COMMAND} -E echo 'now run: \"make install\" to copy runtime files & scripts to ${CMAKE_INSTALL_PREFIX}' +) +endif() + add_dependencies(inkscape inkscape_version) target_link_libraries(inkscape - # order from automake + # order from automake #sp_LIB nrtype_LIB diff --git a/src/Makefile_insert b/src/Makefile_insert index 107acdf31..488ab52c5 100644 --- a/src/Makefile_insert +++ b/src/Makefile_insert @@ -63,7 +63,7 @@ ink_common_sources += \ helper/pixbuf-ops.h \ icon-size.h \ id-clash.cpp id-clash.h \ - inkscape.cpp inkscape.h inkscape-private.h \ + inkscape.cpp inkscape.h \ isinf.h \ knot.cpp knot.h \ knot-enums.h \ diff --git a/src/attribute-rel-css.cpp b/src/attribute-rel-css.cpp index 89678edb5..b904cd5f4 100644 --- a/src/attribute-rel-css.cpp +++ b/src/attribute-rel-css.cpp @@ -60,6 +60,7 @@ bool SPAttributeRelCSS::findIfValid(Glib::ustring property, Glib::ustring elemen || property.substr(0,4) == "rdf:" || property.substr(0,3) == "cc:" || property.substr(0,4) == "ns1:" // JessyInk + || property.substr(0,4) == "osb:" // Open Swatch Book || (SPAttributeRelCSS::instance->propertiesOfElements[temp].find(property) != SPAttributeRelCSS::instance->propertiesOfElements[temp].end()) ) { return true; diff --git a/src/attribute-rel-svg.cpp b/src/attribute-rel-svg.cpp index 49c97ae64..0064f4c62 100644 --- a/src/attribute-rel-svg.cpp +++ b/src/attribute-rel-svg.cpp @@ -56,6 +56,7 @@ bool SPAttributeRelSVG::findIfValid(Glib::ustring attribute, Glib::ustring eleme || attribute.substr(0,4) == "rdf:" || attribute.substr(0,3) == "cc:" || attribute.substr(0,4) == "ns1:" // JessyInk + || attribute.substr(0,4) == "osb:" // Open Swatch Book || (SPAttributeRelSVG::instance->attributesOfElements[temp].find(attribute) != SPAttributeRelSVG::instance->attributesOfElements[temp].end()) ) { return true; diff --git a/src/attributes.cpp b/src/attributes.cpp index d142d1a06..2b04843a7 100644 --- a/src/attributes.cpp +++ b/src/attributes.cpp @@ -115,7 +115,7 @@ static SPStyleProp const props[] = { {SP_ATTR_INKSCAPE_SNAP_BBOX_CORNER, "inkscape:bbox-nodes"}, {SP_ATTR_INKSCAPE_SNAP_PAGE_BORDER, "inkscape:snap-page"}, {SP_ATTR_INKSCAPE_CURRENT_LAYER, "inkscape:current-layer"}, - {SP_ATTR_INKSCAPE_DOCUMENT_UNITS, "inkscape:document-units"}, + {SP_ATTR_INKSCAPE_DOCUMENT_UNITS, "inkscape:document-units"}, // This setting sets the Display units, *not* the units used in SVG {SP_ATTR_UNITS, "units"}, {SP_ATTR_INKSCAPE_CONNECTOR_SPACING, "inkscape:connector-spacing"}, /* SPColorProfile */ diff --git a/src/box3d.cpp b/src/box3d.cpp index 3c0cbb675..9ccc969bc 100644 --- a/src/box3d.cpp +++ b/src/box3d.cpp @@ -401,7 +401,7 @@ box3d_snap (SPBox3D *box, int id, Proj::Pt3 const &pt_proj, Proj::Pt3 const &sta snap_pts[3] = diag2.closest_to (pt); } - gdouble const zoom = inkscape_active_desktop()->current_zoom(); + gdouble const zoom = SP_ACTIVE_DESKTOP->current_zoom(); // determine the distances to all potential snapping points double snap_dists[MAX_POINT_COUNT]; diff --git a/src/conn-avoid-ref.cpp b/src/conn-avoid-ref.cpp index cb72f65dc..afd1bc407 100644 --- a/src/conn-avoid-ref.cpp +++ b/src/conn-avoid-ref.cpp @@ -87,7 +87,7 @@ void SPAvoidRef::setAvoid(char const *value) void SPAvoidRef::handleSettingChange(void) { - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; if (desktop == NULL) { return; } @@ -277,7 +277,7 @@ static std::vector<Geom::Point> approxItemWithPoints(SPItem const *item, const G } static Avoid::Polygon avoid_item_poly(SPItem const *item) { - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; g_assert(desktop != NULL); double spacing = desktop->namedview->connector_spacing; diff --git a/src/desktop-events.cpp b/src/desktop-events.cpp index 5d8ea8b9f..a45823380 100644 --- a/src/desktop-events.cpp +++ b/src/desktop-events.cpp @@ -40,6 +40,7 @@ #include "display/sp-canvas.h" #include "sp-guide.h" #include "sp-namedview.h" +#include "sp-root.h" #include "ui/tools-switch.h" #include "verbs.h" #include "widgets/desktop-widget.h" @@ -217,8 +218,18 @@ static gint sp_dt_ruler_event(GtkWidget *widget, GdkEvent *event, SPDesktopWidge if ((horiz ? wy : wx) >= 0) { Inkscape::XML::Document *xml_doc = desktop->doc()->getReprDoc(); Inkscape::XML::Node *repr = xml_doc->createElement("sodipodi:guide"); + + // If root viewBox set, interpret guides in terms of viewBox (90/96) + double newx = event_dt.x(); + double newy = event_dt.y(); + + SPRoot *root = desktop->doc()->getRoot(); + if( root->viewBox_set ) { + newx = newx * root->viewBox.width() / root->width.computed; + newy = newy * root->viewBox.height() / root->height.computed; + } + sp_repr_set_point(repr, "position", Geom::Point( newx, newy )); sp_repr_set_point(repr, "orientation", normal); - sp_repr_set_point(repr, "position", event_dt); desktop->namedview->appendChild(repr); Inkscape::GC::release(repr); DocumentUndo::done(sp_desktop_document(desktop), SP_VERB_NONE, diff --git a/src/desktop.cpp b/src/desktop.cpp index 74dea3ca1..288ca1fbf 100644 --- a/src/desktop.cpp +++ b/src/desktop.cpp @@ -56,7 +56,6 @@ #include "event-log.h" #include "helper/action-context.h" #include "ui/interface.h" -#include "inkscape-private.h" #include "layer-fns.h" #include "layer-manager.h" #include "layer-model.h" @@ -94,28 +93,28 @@ static void _reconstruction_finish(SPDesktop * desktop); static void _namedview_modified (SPObject *obj, guint flags, SPDesktop *desktop); SPDesktop::SPDesktop() : - _dlg_mgr( 0 ), - namedview( 0 ), - canvas( 0 ), - layers( 0 ), - selection( 0 ), - event_context( 0 ), - layer_manager( 0 ), - event_log( 0 ), - temporary_item_list( 0 ), - snapindicator( 0 ), - acetate( 0 ), - main( 0 ), - gridgroup( 0 ), - guides( 0 ), - drawing( 0 ), - sketch( 0 ), - controls( 0 ), - tempgroup ( 0 ), - table( 0 ), - page( 0 ), - page_border( 0 ), - current( 0 ), + _dlg_mgr( NULL ), + namedview( NULL ), + canvas( NULL ), + layers( NULL ), + selection( NULL ), + event_context( NULL ), + layer_manager( NULL ), + event_log( NULL ), + temporary_item_list( NULL ), + snapindicator( NULL ), + acetate( NULL ), + main( NULL ), + gridgroup( NULL ), + guides( NULL ), + drawing( NULL ), + sketch( NULL ), + controls( NULL ), + tempgroup ( NULL ), + table( NULL ), + page( NULL ), + page_border( NULL ), + current( NULL ), _focusMode(false), dkey( 0 ), number( 0 ), @@ -124,16 +123,15 @@ SPDesktop::SPDesktop() : waiting_cursor( false ), showing_dialogs ( false ), guides_active( false ), - gr_item( 0 ), + gr_item( NULL ), gr_point_type( POINT_LG_BEGIN ), gr_point_i( 0 ), gr_fill_or_stroke( Inkscape::FOR_FILL ), _reconstruction_old_layer_id(), // an id attribute is not allowed to be the empty string _display_mode(Inkscape::RENDERMODE_NORMAL), _display_color_mode(Inkscape::COLORMODE_NORMAL), - _widget( 0 ), - _inkscape( 0 ), - _guides_message_context( 0 ), + _widget( NULL ), + _guides_message_context( NULL ), _active( false ), _w2d(), _d2w(), @@ -299,7 +297,6 @@ SPDesktop::init (SPNamedView *nv, SPCanvas *aCanvas, Inkscape::UI::View::EditWid // ? // sp_active_desktop_set (desktop); - _inkscape = INKSCAPE; _activate_connection = _activate_signal.connect( sigc::bind( @@ -385,10 +382,6 @@ void SPDesktop::destroy() layer_manager = NULL; } - if (_inkscape) { - _inkscape = NULL; - } - if (drawing) { doc()->getRoot()->invoke_hide(dkey); g_object_unref(drawing); @@ -1431,7 +1424,7 @@ void SPDesktop::emitToolSubselectionChanged(gpointer data) { _tool_subselection_changed.emit(data); - inkscape_subselection_changed (this); + INKSCAPE.subselection_changed (this); } void SPDesktop::updateNow() diff --git a/src/desktop.h b/src/desktop.h index 509f8a396..496cc30eb 100644 --- a/src/desktop.h +++ b/src/desktop.h @@ -424,7 +424,6 @@ public: private: Inkscape::UI::View::EditWidgetInterface *_widget; - InkscapeApplication *_inkscape; Inkscape::MessageContext *_guides_message_context; bool _active; Geom::Affine _w2d; diff --git a/src/document-private.h b/src/document-private.h index 8e28b288b..a5033b3c2 100644 --- a/src/document-private.h +++ b/src/document-private.h @@ -75,6 +75,8 @@ struct SPDocumentPrivate { Inkscape::ConsoleOutputUndoObserver console_output_undo_observer; bool seeking; + sigc::connection selChangeConnection; + sigc::connection desktopActivatedConnection; }; #endif // SEEN_SP_DOCUMENT_PRIVATE_H diff --git a/src/document-undo.cpp b/src/document-undo.cpp index 15d5d2c70..d4015bafb 100644 --- a/src/document-undo.cpp +++ b/src/document-undo.cpp @@ -99,9 +99,8 @@ void Inkscape::DocumentUndo::done(SPDocument *doc, const unsigned int event_type maybeDone(doc, NULL, event_type, event_description); } -void Inkscape::DocumentUndo::resetKey( InkscapeApplication * /*inkscape*/, SPDesktop * /*desktop*/, GObject *base ) +void Inkscape::DocumentUndo::resetKey( SPDocument *doc ) { - SPDocument *doc = reinterpret_cast<SPDocument *>(base); doc->actionkey.clear(); } @@ -259,7 +258,7 @@ gboolean Inkscape::DocumentUndo::undo(SPDocument *doc) doc->priv->seeking = false; if (ret) - inkscape_external_change(); + INKSCAPE.external_change(); return ret; } @@ -304,7 +303,7 @@ gboolean Inkscape::DocumentUndo::redo(SPDocument *doc) doc->priv->seeking = false; if (ret) - inkscape_external_change(); + INKSCAPE.external_change(); return ret; } diff --git a/src/document-undo.h b/src/document-undo.h index 17b3de252..85b44d562 100644 --- a/src/document-undo.h +++ b/src/document-undo.h @@ -41,7 +41,7 @@ public: static void maybeDone(SPDocument *document, const gchar *keyconst, unsigned int event_type, Glib::ustring const &event_description); - static void resetKey(InkscapeApplication *inkscape, SPDesktop *desktop, GObject *base); + static void resetKey(SPDocument *doc); static void cancel(SPDocument *document); diff --git a/src/document.cpp b/src/document.cpp index e5b827937..c7d14727a 100644 --- a/src/document.cpp +++ b/src/document.cpp @@ -50,7 +50,7 @@ #include "document-private.h" #include "document-undo.h" #include "id-clash.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "inkscape-version.h" #include "libavoid/router.h" #include "persp3d.h" @@ -154,6 +154,14 @@ SPDocument::~SPDocument() { router = NULL; } + if (oldSignalsConnected) { + priv->selChangeConnection.disconnect(); + priv->desktopActivatedConnection.disconnect(); + } else { + _selection_changed_connection.disconnect(); + _desktop_activated_connection.disconnect(); + } + if (priv) { if (priv->partial) { sp_repr_free_log(priv->partial); @@ -208,17 +216,8 @@ SPDocument::~SPDocument() { rerouting_handler_id = 0; } - if (oldSignalsConnected) { - g_signal_handlers_disconnect_by_func(G_OBJECT(INKSCAPE), - reinterpret_cast<gpointer>(DocumentUndo::resetKey), - static_cast<gpointer>(this)); - } else { - _selection_changed_connection.disconnect(); - _desktop_activated_connection.disconnect(); - } - if (keepalive) { - inkscape_unref(); + inkscape_unref(INKSCAPE); keepalive = FALSE; } @@ -447,7 +446,7 @@ SPDocument *SPDocument::createDoc(Inkscape::XML::Document *rdoc, rdf_set_defaults( document ); if (keepalive) { - inkscape_ref(); + inkscape_ref(INKSCAPE); } // Check if the document already has a perspective (e.g., when opening an existing @@ -462,10 +461,14 @@ SPDocument *SPDocument::createDoc(Inkscape::XML::Document *rdoc, DocumentUndo::setUndoSensitive(document, true); // reset undo key when selection changes, so that same-key actions on different objects are not coalesced - g_signal_connect(G_OBJECT(INKSCAPE), "change_selection", - G_CALLBACK(DocumentUndo::resetKey), document); - g_signal_connect(G_OBJECT(INKSCAPE), "activate_desktop", - G_CALLBACK(DocumentUndo::resetKey), document); + document->priv->selChangeConnection = INKSCAPE.signal_selection_changed.connect( + sigc::hide(sigc::bind( + sigc::ptr_fun(&DocumentUndo::resetKey), document) + )); + document->priv->desktopActivatedConnection = INKSCAPE.signal_activate_desktop.connect( + sigc::hide(sigc::bind( + sigc::ptr_fun(&DocumentUndo::resetKey), document) + )); document->oldSignalsConnected = true; return document; @@ -593,10 +596,18 @@ SPDocument *SPDocument::doUnref() } /// guaranteed not to return nullptr -Inkscape::Util::Unit const* SPDocument::getDefaultUnit() const +Inkscape::Util::Unit const* SPDocument::getDisplayUnit() const { SPNamedView const* nv = sp_document_namedview(this, NULL); - return nv ? nv->getDefaultUnit() : unit_table.getUnit("pt"); + return nv ? nv->getDisplayUnit() : unit_table.getUnit("px"); +} + +/// guaranteed not to return nullptr +// returns 'px' units as default, like legacy Inkscape +Inkscape::Util::Unit const& SPDocument::getSVGUnit() const +{ + SPNamedView const* nv = sp_document_namedview(this, NULL); + return nv ? nv->getSVGUnit() : *unit_table.getUnit("px"); } Inkscape::Util::Quantity SPDocument::getWidth() const @@ -616,24 +627,18 @@ Inkscape::Util::Quantity SPDocument::getWidth() const return Inkscape::Util::Quantity(result, unit_table.getUnit(u)); } -void SPDocument::setWidth(const Inkscape::Util::Quantity &width) +void SPDocument::setWidth(const Inkscape::Util::Quantity &width, bool changeSize) { Inkscape::Util::Unit const *old_units = unit_table.getUnit("px"); if (root->width.unit) old_units = unit_table.getUnit(root->width.unit); gdouble old_converted = Inkscape::Util::Quantity::convert(root->width.value, old_units, width.unit); + root->width.computed = width.value("px"); - /* SVG does not support meters as a unit, so we must translate meters to - * cm when writing */ - if (*width.unit == *unit_table.getUnit("m")) { - root->width.value = width.value("cm"); - root->width.unit = SVGLength::CM; - } else { - root->width.value = width.quantity; - root->width.unit = (SVGLength::Unit) width.unit->svgUnit(); - } + root->width.value = width.quantity; + root->width.unit = (SVGLength::Unit) width.unit->svgUnit(); - if (root->viewBox_set) + if (root->viewBox_set && changeSize) root->viewBox.setMax(Geom::Point(root->viewBox.left() + (root->width.value / old_converted) * root->viewBox.width(), root->viewBox.bottom())); root->updateRepr(); @@ -657,24 +662,18 @@ Inkscape::Util::Quantity SPDocument::getHeight() const return Inkscape::Util::Quantity(result, unit_table.getUnit(u)); } -void SPDocument::setHeight(const Inkscape::Util::Quantity &height) +void SPDocument::setHeight(const Inkscape::Util::Quantity &height, bool changeSize) { Inkscape::Util::Unit const *old_units = unit_table.getUnit("px"); if (root->height.unit) old_units = unit_table.getUnit(root->height.unit); gdouble old_converted = Inkscape::Util::Quantity::convert(root->height.value, old_units, height.unit); + root->height.computed = height.value("px"); - /* SVG does not support meters as a unit, so we must translate meters to - * cm when writing */ - if (*height.unit == *unit_table.getUnit("m")) { - root->height.value = height.value("cm"); - root->height.unit = SVGLength::CM; - } else { - root->height.value = height.quantity; - root->height.unit = (SVGLength::Unit) height.unit->svgUnit(); - } + root->height.value = height.quantity; + root->height.unit = (SVGLength::Unit) height.unit->svgUnit(); - if (root->viewBox_set) + if (root->viewBox_set && changeSize) root->viewBox.setMax(Geom::Point(root->viewBox.right(), root->viewBox.top() + (root->height.value / old_converted) * root->viewBox.height())); root->updateRepr(); @@ -713,11 +712,9 @@ void SPDocument::fitToRect(Geom::Rect const &rect, bool with_margins) double const old_height = getHeight().value("px"); Inkscape::Util::Unit const *nv_units = unit_table.getUnit("px"); + if (root->height.unit) + nv_units = unit_table.getUnit(root->height.unit); SPNamedView *nv = sp_document_namedview(this, NULL); - if (nv != NULL) { - if (nv->getAttribute("units")) - nv_units = unit_table.getUnit(nv->getAttribute("units")); - } /* in px */ double margin_top = 0.0; diff --git a/src/document.h b/src/document.h index 4ace249ae..4a24ff502 100644 --- a/src/document.h +++ b/src/document.h @@ -38,7 +38,6 @@ class SPGroup; class SPRoot; namespace Inkscape { - struct Application; class Selection; class UndoStackObserver; class EventLog; @@ -241,13 +240,14 @@ public: SPDocument *doRef(); SPDocument *doUnref(); - Inkscape::Util::Unit const* getDefaultUnit() const; + Inkscape::Util::Unit const* getDisplayUnit() const; + Inkscape::Util::Unit const& getSVGUnit() const; Inkscape::Util::Quantity getWidth() const; Inkscape::Util::Quantity getHeight() const; Geom::Point getDimensions() const; Geom::OptRect preferredBounds() const; - void setWidth(const Inkscape::Util::Quantity &width); - void setHeight(const Inkscape::Util::Quantity &height); + void setWidth(const Inkscape::Util::Quantity &width, bool changeSize=true); + void setHeight(const Inkscape::Util::Quantity &height, bool changeSize=true); void setViewBox(const Geom::Rect &viewBox); void requestModified(); int ensureUpToDate(); diff --git a/src/extension/dbus/application-interface.cpp b/src/extension/dbus/application-interface.cpp index c0bc19d90..292832a4b 100644 --- a/src/extension/dbus/application-interface.cpp +++ b/src/extension/dbus/application-interface.cpp @@ -49,7 +49,7 @@ application_interface_init (ApplicationInterface *app_interface) static bool ensure_desktop_valid(GError **error) { - if (!inkscape_use_gui()) { + if (!INKSCAPE.use_gui()) { g_set_error(error, INKSCAPE_ERROR, INKSCAPE_ERROR_OTHER, "Application interface action requires a GUI"); return false; } @@ -59,7 +59,7 @@ ensure_desktop_valid(GError **error) static bool ensure_desktop_not_present(GError **error) { - if (inkscape_use_gui()) { + if (INKSCAPE.use_gui()) { g_set_error(error, INKSCAPE_ERROR, INKSCAPE_ERROR_OTHER, "Application interface action requires non-GUI (command line) mode"); return false; } diff --git a/src/extension/dbus/dbus-init.cpp b/src/extension/dbus/dbus-init.cpp index 19b48e10d..43830762c 100644 --- a/src/extension/dbus/dbus-init.cpp +++ b/src/extension/dbus/dbus-init.cpp @@ -153,23 +153,23 @@ gchar * init_document (void) { // This is for command-line use only - g_assert(!inkscape_use_gui()); + g_assert(!INKSCAPE.use_gui()); // Create a blank document and get its selection model etc in an ActionContext SPDocument *doc = SPDocument::createNewDoc(NULL, 1, TRUE); - inkscape_add_document(doc); - return dbus_register_document(inkscape_action_context_for_document(doc)); + INKSCAPE.add_document(doc); + return dbus_register_document(INKSCAPE.action_context_for_document(doc)); } gchar * init_active_document() { - SPDocument *doc = inkscape_active_document(); + SPDocument *doc = INKSCAPE.active_document(); if (!doc) { return NULL; } - return dbus_register_document(inkscape_active_action_context()); + return dbus_register_document(INKSCAPE.active_action_context()); } gchar * diff --git a/src/extension/dbus/document-interface.cpp b/src/extension/dbus/document-interface.cpp index e3452f4ce..bd5f826d3 100644 --- a/src/extension/dbus/document-interface.cpp +++ b/src/extension/dbus/document-interface.cpp @@ -156,7 +156,7 @@ get_name_from_object (SPObject * obj) void desktop_ensure_active (SPDesktop* desk) { if (desk != SP_ACTIVE_DESKTOP) - inkscape_activate_desktop (desk); + INKSCAPE.activate_desktop (desk); return; } diff --git a/src/extension/effect.cpp b/src/extension/effect.cpp index 3c8ee5844..c8f3b2ff9 100644 --- a/src/extension/effect.cpp +++ b/src/extension/effect.cpp @@ -9,7 +9,7 @@ */ #include "prefdialog.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "helper/action.h" #include "ui/view/view.h" #include "desktop-handles.h" @@ -89,11 +89,13 @@ Effect::Effect (Inkscape::XML::Node * in_repr, Implementation::Implementation * } // children of "inkscape-extension" } // if we have an XML file - if (INKSCAPE != NULL && inkscape_use_gui()) { + // \TODO this gets called from the Inkscape::Application constructor, where it initializes the menus. + // But in the constructor, our object isn't quite there yet! + if (Inkscape::Application::exists() && INKSCAPE.use_gui()) { if (_effects_list == NULL) - _effects_list = find_menu(inkscape_get_menus(INKSCAPE), EFFECTS_LIST); + _effects_list = find_menu(INKSCAPE.get_menus(), EFFECTS_LIST); if (_filters_list == NULL) - _filters_list = find_menu(inkscape_get_menus(INKSCAPE), FILTERS_LIST); + _filters_list = find_menu(INKSCAPE.get_menus(), FILTERS_LIST); } if ((_effects_list != NULL || _filters_list != NULL)) { diff --git a/src/extension/error-file.cpp b/src/extension/error-file.cpp index f60af870f..db354c0ce 100644 --- a/src/extension/error-file.cpp +++ b/src/extension/error-file.cpp @@ -48,9 +48,10 @@ ErrorFileNotice::ErrorFileNotice (void) : ) { + // \FIXME change this /* This is some filler text, needs to change before relase */ Glib::ustring dialog_text(_("<span weight=\"bold\" size=\"larger\">One or more extensions failed to load</span>\n\nThe failed extensions have been skipped. Inkscape will continue to run normally but those extensions will be unavailable. For details to troubleshoot this problem, please refer to the error log located at: ")); - gchar * ext_error_file = profile_path(EXTENSION_ERROR_LOG_FILENAME); + gchar * ext_error_file = Inkscape::Application::profile_path(EXTENSION_ERROR_LOG_FILENAME); dialog_text += ext_error_file; g_free(ext_error_file); set_message(dialog_text, true); diff --git a/src/extension/extension.cpp b/src/extension/extension.cpp index 6a22eb585..3d0f49a20 100644 --- a/src/extension/extension.cpp +++ b/src/extension/extension.cpp @@ -667,7 +667,7 @@ Extension::set_param_color (const gchar * name, guint32 color, SPDocument * doc, void Extension::error_file_open (void) { - gchar * ext_error_file = profile_path(EXTENSION_ERROR_LOG_FILENAME); + gchar * ext_error_file = Inkscape::Application::profile_path(EXTENSION_ERROR_LOG_FILENAME); gchar * filename = g_filename_from_utf8( ext_error_file, -1, NULL, NULL, NULL ); error_file.open(filename); if (!error_file.is_open()) { diff --git a/src/extension/implementation/script.cpp b/src/extension/implementation/script.cpp index 99c882a01..e6ac13cdc 100644 --- a/src/extension/implementation/script.cpp +++ b/src/extension/implementation/script.cpp @@ -1051,7 +1051,7 @@ int Script::execute (const std::list<std::string> &in_command, Glib::ustring stderr_data = fileerr.string(); if (stderr_data.length() != 0 && - inkscape_use_gui() + INKSCAPE.use_gui() ) { checkStderr(stderr_data, Gtk::MESSAGE_INFO, _("Inkscape has received additional data from the script executed. " diff --git a/src/extension/init.cpp b/src/extension/init.cpp index 912d58a13..c16a5a899 100644 --- a/src/extension/init.cpp +++ b/src/extension/init.cpp @@ -243,7 +243,7 @@ init() /* Load search path for extensions */ if (Inkscape::Extension::Extension::search_path.size() == 0) { - Inkscape::Extension::Extension::search_path.push_back(profile_path("extensions")); + Inkscape::Extension::Extension::search_path.push_back(Inkscape::Application::profile_path("extensions")); Inkscape::Extension::Extension::search_path.push_back(g_strdup(INKSCAPE_EXTENSIONDIR)); diff --git a/src/extension/internal/cairo-renderer.cpp b/src/extension/internal/cairo-renderer.cpp index 5a9a28ef9..1f48d2097 100644 --- a/src/extension/internal/cairo-renderer.cpp +++ b/src/extension/internal/cairo-renderer.cpp @@ -206,7 +206,7 @@ static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx) } else if (marker->orient_mode == MARKER_ORIENT_AUTO_START_REVERSE) { tr = Geom::Rotate::from_degrees( 180.0 ) * sp_shape_marker_get_transform_at_start(pathv.begin()->front()); } else { - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(pathv.begin()->front().pointAt(0)); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(pathv.begin()->front().pointAt(0)); } sp_shape_render_invoke_marker_rendering(marker, tr, style, ctx); } @@ -224,7 +224,7 @@ static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx) if (marker->orient_mode != MARKER_ORIENT_ANGLE) { tr = sp_shape_marker_get_transform_at_start(path_it->front()); } else { - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(path_it->front().pointAt(0)); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(path_it->front().pointAt(0)); } sp_shape_render_invoke_marker_rendering(marker, tr, style, ctx); } @@ -241,7 +241,7 @@ static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx) if (marker->orient_mode != MARKER_ORIENT_ANGLE) { tr = sp_shape_marker_get_transform(*curve_it1, *curve_it2); } else { - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(curve_it1->pointAt(1)); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(curve_it1->pointAt(1)); } sp_shape_render_invoke_marker_rendering(marker, tr, style, ctx); @@ -257,7 +257,7 @@ static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx) if (marker->orient_mode != MARKER_ORIENT_ANGLE) { tr = sp_shape_marker_get_transform_at_end(lastcurve); } else { - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(lastcurve.pointAt(1)); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(lastcurve.pointAt(1)); } sp_shape_render_invoke_marker_rendering(marker, tr, style, ctx); } @@ -281,7 +281,7 @@ static void sp_shape_render(SPShape *shape, CairoRenderContext *ctx) if (marker->orient_mode != MARKER_ORIENT_ANGLE) { tr = sp_shape_marker_get_transform_at_end(lastcurve); } else { - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(lastcurve.pointAt(1)); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(lastcurve.pointAt(1)); } sp_shape_render_invoke_marker_rendering(marker, tr, style, ctx); diff --git a/src/extension/internal/cdr-input.cpp b/src/extension/internal/cdr-input.cpp index 3a3e2b58e..f4789a08f 100644 --- a/src/extension/internal/cdr-input.cpp +++ b/src/extension/internal/cdr-input.cpp @@ -263,7 +263,7 @@ SPDocument *CdrInput::open(Inkscape::Extension::Input * /*mod*/, const gchar * u // If only one page is present, import that one without bothering user if (tmpSVGOutput.size() > 1) { CdrImportDialog *dlg = 0; - if (inkscape_use_gui()) { + if (INKSCAPE.use_gui()) { dlg = new CdrImportDialog(tmpSVGOutput); if (!dlg->showDialog()) { delete dlg; @@ -285,7 +285,7 @@ SPDocument *CdrInput::open(Inkscape::Extension::Input * /*mod*/, const gchar * u // Set viewBox if it doesn't exist if (doc && !doc->getRoot()->viewBox_set) { - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); } return doc; } diff --git a/src/extension/internal/emf-print.cpp b/src/extension/internal/emf-print.cpp index 0f43fbca1..f7b6626c4 100644 --- a/src/extension/internal/emf-print.cpp +++ b/src/extension/internal/emf-print.cpp @@ -144,7 +144,7 @@ unsigned int PrintEmf::begin(Inkscape::Extension::Print *mod, SPDocument *doc) // width and height in px _width = doc->getWidth().value("px"); _height = doc->getHeight().value("px"); - _doc_unit_scale = Inkscape::Util::Quantity::convert(1, (doc->getDefaultUnit()), "px"); + _doc_unit_scale = Inkscape::Util::Quantity::convert(1, &doc->getSVGUnit(), "px"); // initialize a few global variables hbrush = hbrushOld = hpen = 0; diff --git a/src/extension/internal/filter/filter-file.cpp b/src/extension/internal/filter/filter-file.cpp index 48e64f089..b1993057d 100644 --- a/src/extension/internal/filter/filter-file.cpp +++ b/src/extension/internal/filter/filter-file.cpp @@ -29,7 +29,7 @@ namespace Filter { void Filter::filters_all_files(void) { - gchar *filtersProfilePath = profile_path("filters"); + gchar *filtersProfilePath = Inkscape::Application::profile_path("filters"); filters_load_dir(INKSCAPE_FILTERDIR, _("Bundled")); filters_load_dir(filtersProfilePath, _("Personal")); diff --git a/src/extension/internal/gdkpixbuf-input.cpp b/src/extension/internal/gdkpixbuf-input.cpp index 28e44c461..04a446d1c 100644 --- a/src/extension/internal/gdkpixbuf-input.cpp +++ b/src/extension/internal/gdkpixbuf-input.cpp @@ -136,7 +136,7 @@ GdkpixbufInput::open(Inkscape::Extension::Input *mod, char const *uri) // Set viewBox if it doesn't exist if (!doc->getRoot()->viewBox_set) { std::cout << "Viewbox not set, setting" << std::endl; - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); } // restore undo, as now this document may be shown to the user if a bitmap was opened diff --git a/src/extension/internal/grid.cpp b/src/extension/internal/grid.cpp index 0059bbec2..f4e0e5843 100644 --- a/src/extension/internal/grid.cpp +++ b/src/extension/internal/grid.cpp @@ -113,7 +113,7 @@ Grid::effect (Inkscape::Extension::Effect *module, Inkscape::UI::View::View *doc bounding_area = temprec; } - gdouble scale = Inkscape::Util::Quantity::convert(1, "px", (document->doc())->getDefaultUnit()); + gdouble scale = Inkscape::Util::Quantity::convert(1, "px", &document->doc()->getSVGUnit()); bounding_area *= Geom::Scale(scale); Geom::Point spacings( scale * module->get_param_float("xspacing"), scale * module->get_param_float("yspacing") ); diff --git a/src/extension/internal/pdfinput/pdf-input.cpp b/src/extension/internal/pdfinput/pdf-input.cpp index c8a7feabf..148d2dcba 100644 --- a/src/extension/internal/pdfinput/pdf-input.cpp +++ b/src/extension/internal/pdfinput/pdf-input.cpp @@ -720,7 +720,7 @@ PdfInput::open(::Inkscape::Extension::Input * /*mod*/, const gchar * uri) { } PdfImportDialog *dlg = NULL; - if (inkscape_use_gui()) { + if (INKSCAPE.use_gui()) { dlg = new PdfImportDialog(pdf_doc, uri); if (!dlg->showDialog()) { _cancelled = true; @@ -883,7 +883,7 @@ PdfInput::open(::Inkscape::Extension::Input * /*mod*/, const gchar * uri) { // Set viewBox if it doesn't exist if (!doc->getRoot()->viewBox_set) { - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); } // Restore undo diff --git a/src/extension/internal/vsd-input.cpp b/src/extension/internal/vsd-input.cpp index 9f9bf2651..7fd0d363b 100644 --- a/src/extension/internal/vsd-input.cpp +++ b/src/extension/internal/vsd-input.cpp @@ -263,7 +263,7 @@ SPDocument *VsdInput::open(Inkscape::Extension::Input * /*mod*/, const gchar * u // If only one page is present, import that one without bothering user if (tmpSVGOutput.size() > 1) { VsdImportDialog *dlg = 0; - if (inkscape_use_gui()) { + if (INKSCAPE.use_gui()) { dlg = new VsdImportDialog(tmpSVGOutput); if (!dlg->showDialog()) { delete dlg; @@ -285,7 +285,7 @@ SPDocument *VsdInput::open(Inkscape::Extension::Input * /*mod*/, const gchar * u // Set viewBox if it doesn't exist if (!doc->getRoot()->viewBox_set) { - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); } return doc; diff --git a/src/extension/internal/wpg-input.cpp b/src/extension/internal/wpg-input.cpp index 12d86a99a..54a14fc72 100644 --- a/src/extension/internal/wpg-input.cpp +++ b/src/extension/internal/wpg-input.cpp @@ -129,7 +129,7 @@ SPDocument *WpgInput::open(Inkscape::Extension::Input * /*mod*/, const gchar * u // Set viewBox if it doesn't exist if (doc && !doc->getRoot()->viewBox_set) { - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); } delete input; diff --git a/src/extension/system.cpp b/src/extension/system.cpp index 5225f11ee..6a95717f2 100644 --- a/src/extension/system.cpp +++ b/src/extension/system.cpp @@ -121,7 +121,7 @@ SPDocument *open(Extension *key, gchar const *filename) } if (last_chance_svg) { - if ( inkscape_use_gui() ) { + if ( INKSCAPE.use_gui() ) { sp_ui_error_dialog(_("Format autodetect failed. The file is being opened as SVG.")); } else { g_warning("%s", _("Format autodetect failed. The file is being opened as SVG.")); diff --git a/src/file.cpp b/src/file.cpp index 307944001..a933a9611 100644 --- a/src/file.cpp +++ b/src/file.cpp @@ -144,7 +144,7 @@ SPDesktop *sp_file_new(const std::string &templ) // Set viewBox if it doesn't exist if (!doc->getRoot()->viewBox_set) { DocumentUndo::setUndoSensitive(doc, false); - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); DocumentUndo::setUndoSensitive(doc, true); } @@ -177,7 +177,7 @@ SPDesktop *sp_file_new(const std::string &templ) Glib::ustring sp_file_default_template_uri() { std::list<gchar *> sources; - sources.push_back( profile_path("templates") ); // first try user's local dir + sources.push_back( Inkscape::Application::profile_path("templates") ); // first try user's local dir sources.push_back( g_strdup(INKSCAPE_TEMPLATESDIR) ); // then the system templates dir std::list<gchar const*> baseNames; gchar const* localized = _("default.svg"); @@ -316,7 +316,7 @@ bool sp_file_open(const Glib::ustring &uri, sp_file_add_recent( doc->getURI() ); } - if ( inkscape_use_gui() ) { + if ( INKSCAPE.use_gui() ) { // Perform a fixup pass for hrefs. if ( Inkscape::ResourceManager::getManager().fixupBrokenLinks(doc) ) { Glib::ustring msg = _("Broken links have been changed to point to existing files."); diff --git a/src/graphlayout.cpp b/src/graphlayout.cpp index 18159cb41..e5d61ab64 100644 --- a/src/graphlayout.cpp +++ b/src/graphlayout.cpp @@ -117,7 +117,7 @@ void graphlayout(GSList const *const items) { // add the connector spacing to the size of node bounding boxes // so that connectors can always be routed between shapes - SPDesktop* desktop = inkscape_active_desktop(); + SPDesktop* desktop = SP_ACTIVE_DESKTOP; double spacing = 0; if(desktop) spacing = desktop->namedview->connector_spacing+0.1; diff --git a/src/helper/stock-items.cpp b/src/helper/stock-items.cpp index 582dcd2a8..99dc21e58 100644 --- a/src/helper/stock-items.cpp +++ b/src/helper/stock-items.cpp @@ -195,7 +195,7 @@ SPObject *get_stock_item(gchar const *urn, gboolean stock) gchar * base = g_strndup(e, a); - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; SPDocument *doc = sp_desktop_document(desktop); SPDefs *defs = doc->getDefs(); if (!defs) { @@ -265,7 +265,7 @@ SPObject *get_stock_item(gchar const *urn, gboolean stock) else { - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; SPDocument *doc = sp_desktop_document(desktop); SPObject *object = doc->getObjectById(urn); diff --git a/src/inkscape-manifest-x64.xml b/src/inkscape-manifest-x64.xml index 38526cfe6..b5a6f11f2 100644 --- a/src/inkscape-manifest-x64.xml +++ b/src/inkscape-manifest-x64.xml @@ -1,5 +1,10 @@ <?xml version="1.0" encoding="UTF-8" standalone="yes"?> <assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0"> + <application xmlns="urn:schemas-microsoft-com:asm.v3"> + <windowsSettings> + <dpiAware xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">true</dpiAware> + </windowsSettings> + </application> <dependency> <dependentAssembly> <assemblyIdentity type="win32" name="Microsoft.Windows.Common-Controls" diff --git a/src/inkscape-private.h b/src/inkscape-private.h deleted file mode 100644 index d28ed223e..000000000 --- a/src/inkscape-private.h +++ /dev/null @@ -1,67 +0,0 @@ -#ifndef SEEN_INKSCAPE_PRIVATE_H -#define SEEN_INKSCAPE_PRIVATE_H - -/* - * Some forward declarations - * - * Authors: - * Lauris Kaplinski <lauris@kaplinski.com> - * - * Copyright (C) 1999-2002 Lauris Kaplinski - * Copyright (C) 2001-2002 Ximian, Inc. - * - * Released under GNU GPL, read the file 'COPYING' for more information - */ -#include <glib-object.h> - -#define SP_TYPE_INKSCAPE (inkscape_get_type ()) -#define SP_INKSCAPE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), SP_TYPE_INKSCAPE, Inkscape)) -#define SP_INKSCAPE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), SP_TYPE_INKSCAPE, InkscapeClass)) -#define SP_IS_INKSCAPE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), SP_TYPE_INKSCAPE)) -#define SP_IS_INKSCAPE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), SP_TYPE_INKSCAPE)) - -#include "inkscape.h" - -struct SPColor; -namespace Inkscape { class Selection; } - -GType inkscape_get_type (void); - -void inkscape_ref (void); -void inkscape_unref (void); - -guint inkscape_mapalt(); -void inkscape_mapalt(guint); - -guint inkscape_trackalt(); -void inkscape_trackalt(guint); - -/* - * These are meant solely for desktop, document etc. implementations - */ - -void inkscape_selection_modified (Inkscape::Selection *selection, guint flags); -void inkscape_selection_changed (Inkscape::Selection * selection); -void inkscape_selection_set (Inkscape::Selection * selection); -void inkscape_eventcontext_set (Inkscape::UI::Tools::ToolBase * eventcontext); -void inkscape_add_desktop (SPDesktop * desktop); -void inkscape_remove_desktop (SPDesktop * desktop); -void inkscape_activate_desktop (SPDesktop * desktop); -void inkscape_reactivate_desktop (SPDesktop * desktop); - -void inkscape_set_color (SPColor *color, float opacity); - -#endif // SEEN_INKSCAPE_PRIVATE_H - - - -/* - Local Variables: - mode:c++ - c-file-style:"stroustrup" - c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +)) - indent-tabs-mode:nil - fill-column:99 - End: -*/ -// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:fileencoding=utf-8:textwidth=99 : diff --git a/src/inkscape.cpp b/src/inkscape.cpp index 36a802e5f..94c3722cb 100644 --- a/src/inkscape.cpp +++ b/src/inkscape.cpp @@ -1,13 +1,15 @@ /** * @file - * Legacy interface to main application. + * Interface to main application. */ /* Authors: * Lauris Kaplinski <lauris@kaplinski.com> * bulia byak <buliabyak@users.sf.net> + * Liam P. White <inkscapebrony@gmail.com> * - * Copyright (C) 1999-2005 authors - * g++ port Copyright (C) 2003 Nathan Hurst + * Copyright (C) 1999-2014 authors + * c++ port Copyright (C) 2003 Nathan Hurst + * c++ification Copyright (C) 2014 Liam P. White * * Released under GNU GPL, read the file 'COPYING' for more information */ @@ -50,240 +52,174 @@ #include <gtk/gtk.h> #include <signal.h> #include <string> + #include "desktop.h" #include "desktop-handles.h" #include "device-manager.h" #include "document.h" -#include "ui/tools/tool-base.h" #include "extension/db.h" #include "extension/init.h" #include "extension/output.h" #include "extension/system.h" -#include "inkscape-private.h" +#include "helper/action-context.h" +#include "helper/sp-marshal.h" +#include "inkscape.h" #include "io/sys.h" #include "layer-model.h" #include "message-stack.h" #include "preferences.h" #include "resource-manager.h" #include "selection.h" +#include "ui/tools/tool-base.h" #include "ui/dialog/debug.h" #include "xml/repr.h" -#include "helper/action-context.h" -#include "helper/sp-marshal.h" - -static InkscapeApplication *inkscape = NULL; /* Backbones of configuration xml data */ #include "menus-skeleton.h" -enum { - MODIFY_SELECTION, // global: one of selections modified - CHANGE_SELECTION, // global: one of selections changed - CHANGE_SUBSELECTION, // global: one of subselections (text selection, gradient handle, etc) changed - SET_SELECTION, // global: one of selections set - SET_EVENTCONTEXT, // tool switched - ACTIVATE_DESKTOP, // some desktop got focus - DEACTIVATE_DESKTOP, // some desktop lost focus - SHUTDOWN_SIGNAL, // inkscape is quitting - DIALOGS_HIDE, // user pressed F12 - DIALOGS_UNHIDE, // user pressed F12 - EXTERNAL_CHANGE, // a document was changed by some external means (undo or XML editor); this - // may not be reflected by a selection change and thus needs a separate signal - LAST_SIGNAL -}; +// Inkscape::Application static members +Inkscape::Application * Inkscape::Application::_S_inst = NULL; +bool Inkscape::Application::_crashIsHappening = false; -#define DESKTOP_IS_ACTIVE(d) (inkscape->desktops && ((d) == inkscape->desktops->data)) +#define DESKTOP_IS_ACTIVE(d) (!INKSCAPE._desktops->empty() && ((d) == INKSCAPE._desktops->front())) +static void (* segv_handler) (int) = SIG_DFL; +static void (* abrt_handler) (int) = SIG_DFL; +static void (* fpe_handler) (int) = SIG_DFL; +static void (* ill_handler) (int) = SIG_DFL; +#ifndef WIN32 +static void (* bus_handler) (int) = SIG_DFL; +#endif -/*################################ -# FORWARD DECLARATIONS -################################*/ +#define INKSCAPE_PROFILE_DIR "inkscape" +#define INKSCAPE_PROFILE_DIR_047DEV "Inkscape" +#define INKSCAPE_LEGACY_PROFILE_DIR ".inkscape" +#define MENUS_FILE "menus.xml" -static void inkscape_dispose (GObject *object); +#define SP_INDENT 8 -static void inkscape_activate_desktop_private (InkscapeApplication *inkscape, SPDesktop *desktop); -static void inkscape_deactivate_desktop_private (InkscapeApplication *inkscape, SPDesktop *desktop); +#ifdef WIN32 +typedef int uid_t; +#define getuid() 0 +#endif + +/** C++ification TODO list + * - _S_inst should NOT need to be assigned inside the constructor, but if it isn't the Filters+Extensions menus break. + * - Application::_deskops has to be a pointer because of a signal bug somewhere else. Basically, it will attempt to access a deleted object in sp_ui_close_all(), + * but if it's a pointer we can stop and return NULL in Application::active_desktop() + * - These functions are calling Application::create for no good reason I can determine: + * + * Inkscape::UI::Dialog::SVGPreview::SVGPreview() + * src/ui/dialog/filedialogimpl-gtkmm.cpp:542:9 + * void Inkscape::UI::Widget::ImageIcon::init() + * src/ui/widget/imageicon.cpp:93:9 + */ -class AppSelectionModel { - Inkscape::LayerModel _layer_model; - Inkscape::Selection *_selection; +class InkErrorHandler : public Inkscape::ErrorReporter { public: - AppSelectionModel(SPDocument *doc) { - _layer_model.setDocument(doc); - // TODO: is this really how we should manage the lifetime of the selection? - // I just copied this from the initialization of the Selection in SPDesktop. - // When and how is it actually released? - _selection = Inkscape::GC::release(new Inkscape::Selection(&_layer_model, NULL)); + InkErrorHandler(bool useGui) : Inkscape::ErrorReporter(), + _useGui(useGui) + {} + virtual ~InkErrorHandler() {} + + virtual void handleError( Glib::ustring const& primary, Glib::ustring const& secondary ) const + { + if (_useGui) { + Gtk::MessageDialog err(primary, false, Gtk::MESSAGE_WARNING, Gtk::BUTTONS_OK, true); + err.set_secondary_text(secondary); + err.run(); + } else { + g_message("%s", primary.data()); + g_message("%s", secondary.data()); + } } - Inkscape::Selection *getSelection() const { return _selection; } +private: + bool _useGui; }; -struct InkscapeApplication { - GObject object; - Inkscape::XML::Document *menus; - std::map<SPDocument *, int> document_set; - std::map<SPDocument *, AppSelectionModel *> selection_models; - GSList *desktops; - gchar *argv0; - gboolean dialogs_toggle; - gboolean use_gui; // may want to consider a virtual function - // for overriding things like the warning dlg's - guint mapalt; - guint trackalt; -}; +void inkscape_ref(Inkscape::Application & in) +{ + in.refCount++; +} -struct InkscapeApplicationClass { - GObjectClass object_class; - - /* Signals */ - void (* change_selection) (InkscapeApplication * inkscape, Inkscape::Selection * selection); - void (* change_subselection) (InkscapeApplication * inkscape, SPDesktop *desktop); - void (* modify_selection) (InkscapeApplication * inkscape, Inkscape::Selection * selection, guint flags); - void (* set_selection) (InkscapeApplication * inkscape, Inkscape::Selection * selection); - void (* set_eventcontext) (InkscapeApplication * inkscape, Inkscape::UI::Tools::ToolBase * eventcontext); - void (* activate_desktop) (InkscapeApplication * inkscape, SPDesktop * desktop); - void (* deactivate_desktop) (InkscapeApplication * inkscape, SPDesktop * desktop); - void (* destroy_document) (InkscapeApplication *inkscape, SPDocument *doc); - void (* color_set) (InkscapeApplication *inkscape, SPColor *color, double opacity); - void (* shut_down) (InkscapeApplication *inkscape); - void (* dialogs_hide) (InkscapeApplication *inkscape); - void (* dialogs_unhide) (InkscapeApplication *inkscape); - void (* external_change) (InkscapeApplication *inkscape); -}; +void inkscape_unref(Inkscape::Application & in) +{ + in.refCount--; -static guint inkscape_signals[LAST_SIGNAL] = {0}; + if (&in == Inkscape::Application::_S_inst) { + if (in.refCount <= 0) { + delete Inkscape::Application::_S_inst; + } + } else { + g_error("Attempt to unref an Application (=%p) not the current instance (=%p) (maybe it's already been destroyed?)", + &in, Inkscape::Application::_S_inst); + } +} -static void (* segv_handler) (int) = SIG_DFL; -static void (* abrt_handler) (int) = SIG_DFL; -static void (* fpe_handler) (int) = SIG_DFL; -static void (* ill_handler) (int) = SIG_DFL; -#ifndef WIN32 -static void (* bus_handler) (int) = SIG_DFL; -#endif +// Callback passed to g_timeout_add_seconds() +// gets the current instance and calls autosave() +int inkscape_autosave(gpointer) { + g_assert(Inkscape::Application::exists()); + return INKSCAPE.autosave(); +} -#define INKSCAPE_PROFILE_DIR "inkscape" -#define INKSCAPE_PROFILE_DIR_047DEV "Inkscape" -#define INKSCAPE_LEGACY_PROFILE_DIR ".inkscape" -#define MENUS_FILE "menus.xml" +namespace Inkscape { + +/** + * Defined only for debugging purposes. If we are certain the bugs are gone we can remove this + * and the references in inkscape_ref and inkscape_unref. + */ +Application* +Application::operator &() const +{ + return const_cast<Application*>(this); +} +/** + * Creates a new Inkscape::Application global object. + */ +void +Application::create(const char *argv0, bool use_gui) +{ + if (!Application::exists()) { + new Application(argv0, use_gui); + } else { + g_assert_not_reached(); + } +} -G_DEFINE_TYPE(InkscapeApplication, inkscape, G_TYPE_OBJECT); /** - * Initializes the inkscape class, registering all of its signal handlers - * and virtual functions + * Checks whether the current Inkscape::Application global object exists. */ -static void -inkscape_class_init (InkscapeApplicationClass * klass) +bool +Application::exists() { - GObjectClass * object_class = G_OBJECT_CLASS(klass); - - inkscape_signals[MODIFY_SELECTION] = g_signal_new ("modify_selection", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, modify_selection), - NULL, NULL, - sp_marshal_VOID__POINTER_UINT, - G_TYPE_NONE, 2, - G_TYPE_POINTER, G_TYPE_UINT); - inkscape_signals[CHANGE_SELECTION] = g_signal_new ("change_selection", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, change_selection), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - inkscape_signals[CHANGE_SUBSELECTION] = g_signal_new ("change_subselection", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, change_subselection), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - inkscape_signals[SET_SELECTION] = g_signal_new ("set_selection", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, set_selection), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - inkscape_signals[SET_EVENTCONTEXT] = g_signal_new ("set_eventcontext", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, set_eventcontext), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - inkscape_signals[ACTIVATE_DESKTOP] = g_signal_new ("activate_desktop", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, activate_desktop), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - inkscape_signals[DEACTIVATE_DESKTOP] = g_signal_new ("deactivate_desktop", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, deactivate_desktop), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - inkscape_signals[SHUTDOWN_SIGNAL] = g_signal_new ("shut_down", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, shut_down), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - inkscape_signals[DIALOGS_HIDE] = g_signal_new ("dialogs_hide", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, dialogs_hide), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - inkscape_signals[DIALOGS_UNHIDE] = g_signal_new ("dialogs_unhide", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, dialogs_unhide), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - inkscape_signals[EXTERNAL_CHANGE] = g_signal_new ("external_change", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (InkscapeApplicationClass, external_change), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - - object_class->dispose = inkscape_dispose; - - klass->activate_desktop = inkscape_activate_desktop_private; - klass->deactivate_desktop = inkscape_deactivate_desktop_private; + return Application::_S_inst != NULL; } -#ifdef WIN32 -typedef int uid_t; -#define getuid() 0 -#endif +/** + * Returns the current Inkscape::Application global object. + * \pre Application::_S_inst != NULL + */ +Application& +Application::instance() +{ + if (!exists()) { + g_error("Inkscape::Application does not yet exist."); + } + return *Application::_S_inst; +} /** * static gint inkscape_autosave(gpointer); * - * Callback passed to g_timeout_add_seconds() * Responsible for autosaving all open documents */ -static gint inkscape_autosave(gpointer) +int Application::autosave() { - if (inkscape->document_set.empty()) { // nothing to autosave + if (_document_set.empty()) { // nothing to autosave return TRUE; } Inkscape::Preferences *prefs = Inkscape::Preferences::get(); @@ -302,7 +238,7 @@ static gint inkscape_autosave(gpointer) } GDir *autosave_dir_ptr = g_dir_open(autosave_dir.c_str(), 0, NULL); - if( !autosave_dir_ptr ){ + if (!autosave_dir_ptr) { // Try to create the autosave directory if it doesn't exist if (g_mkdir(autosave_dir.c_str(), 0755)) { // the creation failed @@ -333,8 +269,8 @@ static gint inkscape_autosave(gpointer) gint docnum = 0; SP_ACTIVE_DESKTOP->messageStack()->flash(Inkscape::NORMAL_MESSAGE, _("Autosaving documents...")); - for (std::map<SPDocument*,int>::iterator iter = inkscape->document_set.begin(); - iter != inkscape->document_set.end(); + for (std::map<SPDocument*,int>::iterator iter = _document_set.begin(); + iter != _document_set.end(); ++iter) { SPDocument *doc = iter->first; @@ -342,7 +278,6 @@ static gint inkscape_autosave(gpointer) ++docnum; Inkscape::XML::Node *repr = doc->getReprRoot(); - // g_debug("Document %d: \"%s\" %s", docnum, doc ? doc->getName() : "(null)", doc ? (doc->isModifiedSinceSave() ? "(dirty)" : "(clean)") : "(null)"); if (doc->isModifiedSinceSave()) { gchar *oldest_autosave = 0; @@ -373,8 +308,6 @@ static gint inkscape_autosave(gpointer) } } - // g_debug("%d previous autosaves exists. Max = %d", count, autosave_max); - // Have we reached the limit for number of autosaves? if ( count >= autosave_max ){ // Remove the oldest file @@ -396,8 +329,6 @@ static gint inkscape_autosave(gpointer) g_free(baseName); baseName = 0; - // g_debug("Filename: %s", full_path); - // Try to save the file FILE *file = Inkscape::IO::fopen_utf8name(full_path, "w"); gchar *errortext = 0; @@ -435,7 +366,7 @@ static gint inkscape_autosave(gpointer) return TRUE; } -void inkscape_autosave_init() +void Application::autosave_init() { static guint32 autosave_timeout_id = 0; Inkscape::Preferences *prefs = Inkscape::Preferences::get(); @@ -446,139 +377,149 @@ void inkscape_autosave_init() autosave_timeout_id = 0; } - // g_debug("options.autosave.enable = %d", prefs->getBool("/options/autosave/enable", true)); // Is autosave enabled? if (!prefs->getBool("/options/autosave/enable", true)){ autosave_timeout_id = 0; } else { // Turn on autosave guint32 timeout = prefs->getInt("/options/autosave/interval", 10) * 60; - // g_debug("options.autosave.interval = %d", prefs->getInt("/options/autosave/interval", 10)); autosave_timeout_id = g_timeout_add_seconds(timeout, inkscape_autosave, NULL); } } - -static void -inkscape_init (InkscapeApplication * object) +void Application::argv0(char const* argv) { - if (!inkscape) { - inkscape = (InkscapeApplication *) object; - } else { - g_assert_not_reached (); - } - - new (&inkscape->document_set) std::map<SPDocument *, int>(); - new (&inkscape->selection_models) std::map<SPDocument *, AppSelectionModel *>(); - - inkscape->menus = NULL; - inkscape->desktops = NULL; - inkscape->dialogs_toggle = TRUE; - inkscape->mapalt = GDK_MOD1_MASK; - inkscape->trackalt = FALSE; + _argv0 = g_strdup(argv); } -static void -inkscape_dispose (GObject *object) +/* \brief Constructor for the application. + * Creates a new Inkscape::Application. + * + * \pre Application::_S_inst == NULL + */ + +Application::Application(const char* argv, bool use_gui) : + _menus(NULL), + _desktops(NULL), + refCount(1), + _dialogs_toggle(TRUE), + _mapalt(GDK_MOD1_MASK), + _trackalt(FALSE), + _use_gui(use_gui) { - InkscapeApplication *inkscape = (InkscapeApplication *) object; + /* fixme: load application defaults */ - g_assert (!inkscape->desktops); + segv_handler = signal (SIGSEGV, Application::crash_handler); + abrt_handler = signal (SIGABRT, Application::crash_handler); + fpe_handler = signal (SIGFPE, Application::crash_handler); + ill_handler = signal (SIGILL, Application::crash_handler); +#ifndef WIN32 + bus_handler = signal (SIGBUS, Application::crash_handler); +#endif - Inkscape::Preferences::unload(); + _argv0 = g_strdup(argv); - if (inkscape->menus) { - /* fixme: This is not the best place */ - Inkscape::GC::release(inkscape->menus); - inkscape->menus = NULL; - } + // \TODO: this belongs to Application::init but if it isn't here + // then the Filters and Extensions menus don't work. + _S_inst = this; - inkscape->selection_models.~map(); - inkscape->document_set.~map(); + /* Load the preferences and menus */ + Inkscape::Preferences *prefs = Inkscape::Preferences::get(); + InkErrorHandler* handler = new InkErrorHandler(use_gui); + prefs->setErrorHandler(handler); + { + Glib::ustring msg; + Glib::ustring secondary; + if (prefs->getLastError( msg, secondary )) { + handler->handleError(msg, secondary); + } + } - G_OBJECT_CLASS (inkscape_parent_class)->dispose (object); + if (use_gui) { + load_menus(); + Inkscape::DeviceManager::getManager().loadConfig(); + } + Inkscape::ResourceManager::getManager(); - gtk_main_quit (); -} + /* set language for user interface according setting in preferences */ + Glib::ustring ui_language = prefs->getString("/ui/language"); + if(!ui_language.empty()) + { + setenv("LANGUAGE", ui_language, 1); + } + /* DebugDialog redirection. On Linux, default to OFF, on Win32, default to ON. + * Use only if use_gui is enabled + */ +#ifdef WIN32 +#define DEFAULT_LOG_REDIRECT true +#else +#define DEFAULT_LOG_REDIRECT false +#endif -void -inkscape_ref (void) -{ - if (inkscape) - g_object_ref (G_OBJECT (inkscape)); -} + if (use_gui == TRUE && prefs->getBool("/dialogs/debug/redirect", DEFAULT_LOG_REDIRECT)) + { + Inkscape::UI::Dialog::DebugDialog::getInstance()->captureLogMessages(); + } + /* Check for global remapping of Alt key */ + if (use_gui) + { + mapalt(guint(prefs->getInt("/options/mapalt/value", 0))); + trackalt(guint(prefs->getInt("/options/trackalt/value", 0))); + } -void -inkscape_unref (void) -{ - if (inkscape) - g_object_unref (G_OBJECT (inkscape)); -} + /* Initialize the extensions */ + Inkscape::Extension::init(); -/* returns the mask of the keyboard modifier to map to Alt, zero if no mapping */ -/* Needs to be a guint because gdktypes.h does not define a 'no-modifier' value */ -guint -inkscape_mapalt() { - return inkscape->mapalt; + autosave_init(); } -/* Sets the keyboard modifer to map to Alt. Zero switches off mapping, as does '1', which is the default */ -void inkscape_mapalt(guint maskvalue) +Application::~Application() { - if(maskvalue<2 || maskvalue> 5 ){ /* MOD5 is the highest defined in gdktypes.h */ - inkscape->mapalt=0; - }else{ - inkscape->mapalt=(GDK_MOD1_MASK << (maskvalue-1)); + if (_desktops) { + g_error("FATAL: desktops still in list on application destruction!"); } -} -guint -inkscape_trackalt() { - return inkscape->trackalt; -} - -void inkscape_trackalt(guint trackvalue) -{ - inkscape->trackalt = trackvalue; -} + Inkscape::Preferences::unload(); + if (_menus) { + Inkscape::GC::release(_menus); + _menus = NULL; + } -static void -inkscape_activate_desktop_private (InkscapeApplication */*inkscape*/, SPDesktop *desktop) -{ - desktop->set_active (true); -} + if (_argv0) { + g_free(_argv0); + _argv0 = NULL; + } + _S_inst = NULL; // this will probably break things -static void -inkscape_deactivate_desktop_private (InkscapeApplication */*inkscape*/, SPDesktop *desktop) -{ - desktop->set_active (false); + refCount = 0; + gtk_main_quit (); } - -/* fixme: This is EVIL, and belongs to main after all */ - -#define SP_INDENT 8 - - -static bool crashIsHappening = false; - -bool inkscapeIsCrashing() +/** Sets the keyboard modifer to map to Alt. + * + * Zero switches off mapping, as does '1', which is the default. + */ +void Application::mapalt(guint maskvalue) { - return crashIsHappening; + if ( maskvalue < 2 || maskvalue > 5 ) { // MOD5 is the highest defined in gdktypes.h + _mapalt = 0; + } else { + _mapalt = (GDK_MOD1_MASK << (maskvalue-1)); + } } -static void -inkscape_crash_handler (int /*signum*/) +void +Application::crash_handler (int /*signum*/) { using Inkscape::Debug::SimpleEvent; using Inkscape::Debug::EventTracker; using Inkscape::Debug::Logger; - static gint recursion = FALSE; + static bool recursion = false; /* * reset all signal handlers: any further crashes should just be allowed @@ -596,9 +537,9 @@ inkscape_crash_handler (int /*signum*/) if (recursion) { abort (); } - recursion = TRUE; + recursion = true; - crashIsHappening = true; + _crashIsHappening = true; EventTracker<SimpleEvent<Inkscape::Debug::Event::CORE> > tracker("crash"); tracker.set<SimpleEvent<> >("emergency-save"); @@ -612,11 +553,11 @@ inkscape_crash_handler (int /*signum*/) gint count = 0; gchar *curdir = g_get_current_dir(); // This one needs to be freed explicitly - gchar *inkscapedir = g_path_get_dirname(INKSCAPE->argv0); // Needs to be freed + gchar *inkscapedir = g_path_get_dirname(INKSCAPE._argv0); // Needs to be freed GSList *savednames = NULL; GSList *failednames = NULL; - for (std::map<SPDocument*,int>::iterator iter = inkscape->document_set.begin(); - iter != inkscape->document_set.end(); + for (std::map<SPDocument*,int>::iterator iter = INKSCAPE._document_set.begin(), e = INKSCAPE._document_set.end(); + iter != e; ++iter) { SPDocument *doc = iter->first; Inkscape::XML::Node *repr; @@ -757,7 +698,7 @@ inkscape_crash_handler (int /*signum*/) } *(b + pos) = '\0'; - if ( inkscape_get_instance() && inkscape_use_gui() ) { + if ( exists() && instance().use_gui() ) { GtkWidget *msgbox = gtk_message_dialog_new (NULL, GTK_DIALOG_MODAL, GTK_MESSAGE_ERROR, GTK_BUTTONS_CLOSE, "%s", b); gtk_dialog_run (GTK_DIALOG (msgbox)); gtk_widget_destroy (msgbox); @@ -774,132 +715,19 @@ inkscape_crash_handler (int /*signum*/) /* on exit, allow restored signal handler to take over and crash us */ } - -class InkErrorHandler : public Inkscape::ErrorReporter { -public: - InkErrorHandler(bool useGui) : Inkscape::ErrorReporter(), - _useGui(useGui) - {} - virtual ~InkErrorHandler() {} - - virtual void handleError( Glib::ustring const& primary, Glib::ustring const& secondary ) const - { - if (_useGui) { - Gtk::MessageDialog err(primary, false, Gtk::MESSAGE_WARNING, Gtk::BUTTONS_OK, true); - err.set_secondary_text(secondary); - err.run(); - } else { - g_message("%s", primary.data()); - g_message("%s", secondary.data()); - } - } - -private: - bool _useGui; -}; - -void -inkscape_application_init (const gchar *argv0, gboolean use_gui) -{ - inkscape = (InkscapeApplication *)g_object_new (SP_TYPE_INKSCAPE, NULL); - /* fixme: load application defaults */ - - segv_handler = signal (SIGSEGV, inkscape_crash_handler); - abrt_handler = signal (SIGABRT, inkscape_crash_handler); - fpe_handler = signal (SIGFPE, inkscape_crash_handler); - ill_handler = signal (SIGILL, inkscape_crash_handler); -#ifndef WIN32 - bus_handler = signal (SIGBUS, inkscape_crash_handler); -#endif - - inkscape->use_gui = use_gui; - inkscape->argv0 = g_strdup(argv0); - - /* Load the preferences and menus */ - Inkscape::Preferences *prefs = Inkscape::Preferences::get(); - InkErrorHandler* handler = new InkErrorHandler(use_gui); - prefs->setErrorHandler(handler); - { - Glib::ustring msg; - Glib::ustring secondary; - if (prefs->getLastError( msg, secondary )) { - handler->handleError(msg, secondary); - } - } - - if (use_gui) { - inkscape_load_menus(inkscape); - Inkscape::DeviceManager::getManager().loadConfig(); - } - Inkscape::ResourceManager::getManager(); - - /* set language for user interface according setting in preferences */ - Glib::ustring ui_language = prefs->getString("/ui/language"); - if(!ui_language.empty()) - { - setenv("LANGUAGE", ui_language, 1); - } - - /* DebugDialog redirection. On Linux, default to OFF, on Win32, default to ON. - * Use only if use_gui is enabled - */ -#ifdef WIN32 -#define DEFAULT_LOG_REDIRECT true -#else -#define DEFAULT_LOG_REDIRECT false -#endif - - if (use_gui == TRUE && prefs->getBool("/dialogs/debug/redirect", DEFAULT_LOG_REDIRECT)) - { - Inkscape::UI::Dialog::DebugDialog::getInstance()->captureLogMessages(); - } - - /* Check for global remapping of Alt key */ - if (use_gui) - { - inkscape_mapalt(guint(prefs->getInt("/options/mapalt/value", 0))); - inkscape_trackalt(guint(prefs->getInt("/options/trackalt/value", 0))); - } - - /* Initialize the extensions */ - Inkscape::Extension::init(); - - inkscape_autosave_init(); - - return; -} - -/** - * Returns the current InkscapeApplication global object - */ -InkscapeApplication * -inkscape_get_instance() -{ - return inkscape; -} - -gboolean inkscape_use_gui() -{ - return inkscape_get_instance()->use_gui; -} - /** * Menus management * */ -bool inkscape_load_menus( InkscapeApplication * inkscape ) +bool Application::load_menus() { gchar *fn = profile_path(MENUS_FILE); gchar *menus_xml = 0; gsize len = 0; - if ( inkscape != inkscape_get_instance() ) { - g_warning("BAD BAD BAD THINGS"); - } - if ( g_file_get_contents(fn, &menus_xml, &len, NULL) ) { // load the menus_xml file - inkscape->menus = sp_repr_read_mem(menus_xml, len, NULL); + _menus = sp_repr_read_mem(menus_xml, len, NULL); g_free(menus_xml); menus_xml = 0; @@ -907,146 +735,157 @@ bool inkscape_load_menus( InkscapeApplication * inkscape ) g_free(fn); fn = 0; - if ( !inkscape->menus ) { - inkscape->menus = sp_repr_read_mem(menus_skeleton, MENUS_SKELETON_SIZE, NULL); + if ( !_menus ) { + _menus = sp_repr_read_mem(menus_skeleton, MENUS_SKELETON_SIZE, NULL); } - return (inkscape->menus != NULL); + return (_menus != 0); } void -inkscape_selection_modified (Inkscape::Selection *selection, guint flags) +Application::selection_modified (Inkscape::Selection *selection, guint flags) { g_return_if_fail (selection != NULL); if (DESKTOP_IS_ACTIVE (selection->desktop())) { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[MODIFY_SELECTION], 0, selection, flags); + signal_selection_modified.emit(selection, flags); } } void -inkscape_selection_changed (Inkscape::Selection * selection) +Application::selection_changed (Inkscape::Selection * selection) { g_return_if_fail (selection != NULL); - + if (DESKTOP_IS_ACTIVE (selection->desktop())) { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[CHANGE_SELECTION], 0, selection); + signal_selection_changed.emit(selection); } } void -inkscape_subselection_changed (SPDesktop *desktop) +Application::subselection_changed (SPDesktop *desktop) { g_return_if_fail (desktop != NULL); if (DESKTOP_IS_ACTIVE (desktop)) { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[CHANGE_SUBSELECTION], 0, desktop); + signal_subselection_changed.emit(desktop); } } void -inkscape_selection_set (Inkscape::Selection * selection) +Application::selection_set (Inkscape::Selection * selection) { g_return_if_fail (selection != NULL); if (DESKTOP_IS_ACTIVE (selection->desktop())) { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_SELECTION], 0, selection); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[CHANGE_SELECTION], 0, selection); + signal_selection_set.emit(selection); + signal_selection_changed.emit(selection); } } void -inkscape_eventcontext_set (Inkscape::UI::Tools::ToolBase * eventcontext) +Application::eventcontext_set (Inkscape::UI::Tools::ToolBase * eventcontext) { g_return_if_fail (eventcontext != NULL); g_return_if_fail (SP_IS_EVENT_CONTEXT (eventcontext)); if (DESKTOP_IS_ACTIVE (eventcontext->desktop)) { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_EVENTCONTEXT], 0, eventcontext); + signal_eventcontext_set.emit(eventcontext); } } void -inkscape_add_desktop (SPDesktop * desktop) +Application::add_desktop (SPDesktop * desktop) { g_return_if_fail (desktop != NULL); - g_return_if_fail (inkscape != NULL); + if (_desktops == NULL) { + _desktops = new std::vector<SPDesktop*>; + } - g_assert (!g_slist_find (inkscape->desktops, desktop)); + if (std::find(_desktops->begin(), _desktops->end(), desktop) != _desktops->end()) { + g_error("Attempted to add desktop already in list."); + } - inkscape->desktops = g_slist_prepend (inkscape->desktops, desktop); + _desktops->insert(_desktops->begin(), desktop); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[ACTIVATE_DESKTOP], 0, desktop); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_EVENTCONTEXT], 0, desktop->getEventContext()); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_SELECTION], 0, sp_desktop_selection (desktop)); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[CHANGE_SELECTION], 0, sp_desktop_selection (desktop)); + signal_activate_desktop.emit(desktop); + signal_eventcontext_set.emit(desktop->getEventContext()); + signal_selection_set.emit(sp_desktop_selection(desktop)); + signal_selection_changed.emit(sp_desktop_selection(desktop)); } void -inkscape_remove_desktop (SPDesktop * desktop) +Application::remove_desktop (SPDesktop * desktop) { g_return_if_fail (desktop != NULL); - g_return_if_fail (inkscape != NULL); - g_assert (g_slist_find (inkscape->desktops, desktop)); + if (std::find (_desktops->begin(), _desktops->end(), desktop) == _desktops->end() ) { + g_error("Attempted to remove desktop not in list."); + } if (DESKTOP_IS_ACTIVE (desktop)) { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[DEACTIVATE_DESKTOP], 0, desktop); - if (inkscape->desktops->next != NULL) { - SPDesktop * new_desktop = static_cast<SPDesktop *>(inkscape->desktops->next->data); - inkscape->desktops = g_slist_remove (inkscape->desktops, new_desktop); - inkscape->desktops = g_slist_prepend (inkscape->desktops, new_desktop); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[ACTIVATE_DESKTOP], 0, new_desktop); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_EVENTCONTEXT], 0, new_desktop->getEventContext()); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_SELECTION], 0, sp_desktop_selection (new_desktop)); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[CHANGE_SELECTION], 0, sp_desktop_selection (new_desktop)); + signal_deactivate_desktop.emit(desktop); + if (_desktops->size() > 1) { + SPDesktop * new_desktop = *(++_desktops->begin()); + _desktops->erase(std::find(_desktops->begin(), _desktops->end(), new_desktop)); + _desktops->insert(_desktops->begin(), new_desktop); + + signal_activate_desktop.emit(new_desktop); + signal_eventcontext_set.emit(new_desktop->getEventContext()); + signal_selection_set.emit(sp_desktop_selection(new_desktop)); + signal_selection_changed.emit(sp_desktop_selection(new_desktop)); } else { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_EVENTCONTEXT], 0, NULL); + signal_eventcontext_set.emit(NULL); if (sp_desktop_selection(desktop)) sp_desktop_selection(desktop)->clear(); } } - inkscape->desktops = g_slist_remove (inkscape->desktops, desktop); + _desktops->erase(std::find(_desktops->begin(), _desktops->end(), desktop)); // if this was the last desktop, shut down the program - if (inkscape->desktops == NULL) { - inkscape_exit (inkscape); + if (_desktops->empty()) { + this->exit(); + delete _desktops; + _desktops = NULL; } } void -inkscape_activate_desktop (SPDesktop * desktop) +Application::activate_desktop (SPDesktop * desktop) { g_return_if_fail (desktop != NULL); - g_return_if_fail (inkscape != NULL); if (DESKTOP_IS_ACTIVE (desktop)) { return; } - g_assert (g_slist_find (inkscape->desktops, desktop)); + std::vector<SPDesktop*>::iterator i; + + if ((i = std::find (_desktops->begin(), _desktops->end(), desktop)) == _desktops->end()) { + g_error("Tried to activate desktop not added to list."); + } - SPDesktop *current = static_cast<SPDesktop *>(inkscape->desktops->data); + SPDesktop *current = _desktops->front(); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[DEACTIVATE_DESKTOP], 0, current); + signal_deactivate_desktop.emit(current); - inkscape->desktops = g_slist_remove (inkscape->desktops, desktop); - inkscape->desktops = g_slist_prepend (inkscape->desktops, desktop); + _desktops->erase (i); + _desktops->insert (_desktops->begin(), desktop); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[ACTIVATE_DESKTOP], 0, desktop); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_EVENTCONTEXT], 0, desktop->getEventContext()); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[SET_SELECTION], 0, sp_desktop_selection (desktop)); - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[CHANGE_SELECTION], 0, sp_desktop_selection (desktop)); + signal_activate_desktop.emit(desktop); + signal_eventcontext_set.emit(desktop->getEventContext()); + signal_selection_set(sp_desktop_selection(desktop)); + signal_selection_changed(sp_desktop_selection(desktop)); } @@ -1054,65 +893,62 @@ inkscape_activate_desktop (SPDesktop * desktop) * Resends ACTIVATE_DESKTOP for current desktop; needed when a new desktop has got its window that dialogs will transientize to */ void -inkscape_reactivate_desktop (SPDesktop * desktop) +Application::reactivate_desktop (SPDesktop * desktop) { g_return_if_fail (desktop != NULL); - g_return_if_fail (inkscape != NULL); - if (DESKTOP_IS_ACTIVE (desktop)) - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[ACTIVATE_DESKTOP], 0, desktop); + if (DESKTOP_IS_ACTIVE (desktop)) { + signal_activate_desktop.emit(desktop); + } } SPDesktop * -inkscape_find_desktop_by_dkey (unsigned int dkey) +Application::find_desktop_by_dkey (unsigned int dkey) { - for (GSList *r = inkscape->desktops; r; r = r->next) { - if ((static_cast<SPDesktop *>(r->data))->dkey == dkey){ - return (static_cast<SPDesktop *>(r->data)); + for (std::vector<SPDesktop*>::iterator r = _desktops->begin(), e = _desktops->end(); r != e; ++r) { + if ((*r)->dkey == dkey){ + return *r; } } return NULL; } - - -static unsigned int -inkscape_maximum_dkey() +unsigned int +Application::maximum_dkey() { unsigned int dkey = 0; - for (GSList *r = inkscape->desktops; r; r = r->next) { - if ((static_cast<SPDesktop *>(r->data))->dkey > dkey){ - dkey = (static_cast<SPDesktop *>(r->data))->dkey; + for (std::vector<SPDesktop*>::iterator r = _desktops->begin(), e = _desktops->end(); r != e; ++r) { + if ((*r)->dkey > dkey){ + dkey = (*r)->dkey; } } - return dkey; } -static SPDesktop * -inkscape_next_desktop () +SPDesktop * +Application::next_desktop () { SPDesktop *d = NULL; - unsigned int dkey_current = (static_cast<SPDesktop *>(inkscape->desktops->data))->dkey; + unsigned int dkey_current = (_desktops->front())->dkey; - if (dkey_current < inkscape_maximum_dkey()) { + if (dkey_current < maximum_dkey()) { // find next existing - for (unsigned int i = dkey_current + 1; i <= inkscape_maximum_dkey(); i++) { - d = inkscape_find_desktop_by_dkey (i); + for (unsigned int i = dkey_current + 1; i <= maximum_dkey(); ++i) { + d = find_desktop_by_dkey (i); if (d) { break; } } } else { // find first existing - for (unsigned int i = 0; i <= inkscape_maximum_dkey(); i++) { - d = inkscape_find_desktop_by_dkey (i); + for (unsigned int i = 0; i <= maximum_dkey(); ++i) { + d = find_desktop_by_dkey (i); if (d) { break; } @@ -1120,22 +956,21 @@ inkscape_next_desktop () } g_assert (d); - return d; } -static SPDesktop * -inkscape_prev_desktop () +SPDesktop * +Application::prev_desktop () { SPDesktop *d = NULL; - unsigned int dkey_current = (static_cast<SPDesktop *>(inkscape->desktops->data))->dkey; + unsigned int dkey_current = (_desktops->front())->dkey; if (dkey_current > 0) { // find prev existing - for (signed int i = dkey_current - 1; i >= 0; i--) { - d = inkscape_find_desktop_by_dkey (i); + for (signed int i = dkey_current - 1; i >= 0; --i) { + d = find_desktop_by_dkey (i); if (d) { break; } @@ -1143,81 +978,74 @@ inkscape_prev_desktop () } if (!d) { // find last existing - d = inkscape_find_desktop_by_dkey (inkscape_maximum_dkey()); + d = find_desktop_by_dkey (maximum_dkey()); } g_assert (d); - return d; } void -inkscape_switch_desktops_next () +Application::switch_desktops_next () { - inkscape_next_desktop()->presentWindow(); + next_desktop()->presentWindow(); } - - void -inkscape_switch_desktops_prev () +Application::switch_desktops_prev() { - inkscape_prev_desktop()->presentWindow(); + prev_desktop()->presentWindow(); } - - void -inkscape_dialogs_hide () +Application::dialogs_hide() { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[DIALOGS_HIDE], 0); - inkscape->dialogs_toggle = FALSE; + signal_dialogs_hide.emit(); + _dialogs_toggle = false; } void -inkscape_dialogs_unhide () +Application::dialogs_unhide() { - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[DIALOGS_UNHIDE], 0); - inkscape->dialogs_toggle = TRUE; + signal_dialogs_unhide.emit(); + _dialogs_toggle = true; } void -inkscape_dialogs_toggle () +Application::dialogs_toggle() { - if (inkscape->dialogs_toggle) { - inkscape_dialogs_hide (); + if (_dialogs_toggle) { + dialogs_hide(); } else { - inkscape_dialogs_unhide (); + dialogs_unhide(); } } void -inkscape_external_change () +Application::external_change() { - g_return_if_fail (inkscape != NULL); - - g_signal_emit (G_OBJECT (inkscape), inkscape_signals[EXTERNAL_CHANGE], 0); + signal_external_change.emit(); } /** * fixme: These need probably signals too */ void -inkscape_add_document (SPDocument *document) +Application::add_document (SPDocument *document) { g_return_if_fail (document != NULL); // try to insert the pair into the list - if (!(inkscape->document_set.insert(std::make_pair(document, 1)).second)) { + if (!(_document_set.insert(std::make_pair(document, 1)).second)) { //insert failed, this key (document) is already in the list - for (std::map<SPDocument*,int>::iterator iter = inkscape->document_set.begin(); - iter != inkscape->document_set.end(); + for (std::map<SPDocument*,int>::iterator iter = _document_set.begin(); + iter != _document_set.end(); ++iter) { if (iter->first == document) { // found this document in list, increase its count @@ -1227,10 +1055,10 @@ inkscape_add_document (SPDocument *document) } else { // insert succeeded, this document is new. Do we need to create a // selection model for it, i.e. are we running without a desktop? - if (!inkscape->use_gui) { + if (!_use_gui) { // Create layer model and selection model so we can run some verbs without a GUI - g_assert(inkscape->selection_models.find(document) == inkscape->selection_models.end()); - inkscape->selection_models[document] = new AppSelectionModel(document); + g_assert(_selection_models.find(document) == _selection_models.end()); + _selection_models[document] = new AppSelectionModel(document); } } } @@ -1238,24 +1066,24 @@ inkscape_add_document (SPDocument *document) // returns true if this was last reference to this document, so you can delete it bool -inkscape_remove_document (SPDocument *document) +Application::remove_document (SPDocument *document) { g_return_val_if_fail (document != NULL, false); - for (std::map<SPDocument*,int>::iterator iter = inkscape->document_set.begin(); - iter != inkscape->document_set.end(); + for (std::map<SPDocument *,int>::iterator iter = _document_set.begin(); + iter != _document_set.end(); ++iter) { if (iter->first == document) { // found this document in list, decrease its count iter->second --; if (iter->second < 1) { // this was the last one, remove the pair from list - inkscape->document_set.erase (iter); + _document_set.erase (iter); // also remove the selection model - std::map<SPDocument *, AppSelectionModel *>::iterator sel_iter = inkscape->selection_models.find(document); - if (sel_iter != inkscape->selection_models.end()) { - inkscape->selection_models.erase(sel_iter); + std::map<SPDocument *, AppSelectionModel *>::iterator sel_iter = _selection_models.find(document); + if (sel_iter != _selection_models.end()) { + _selection_models.erase(sel_iter); } return true; @@ -1269,37 +1097,38 @@ inkscape_remove_document (SPDocument *document) } SPDesktop * -inkscape_active_desktop (void) +Application::active_desktop() { - if (inkscape->desktops == NULL) { + if (!_desktops || _desktops->empty()) { return NULL; } - return static_cast<SPDesktop *>(inkscape->desktops->data); + return _desktops->front(); } SPDocument * -inkscape_active_document (void) +Application::active_document() { if (SP_ACTIVE_DESKTOP) { return sp_desktop_document (SP_ACTIVE_DESKTOP); - } else if (!inkscape->document_set.empty()) { + } else if (!_document_set.empty()) { // If called from the command line there will be no desktop // So 'fall back' to take the first listed document in the Inkscape instance - return inkscape->document_set.begin()->first; + return _document_set.begin()->first; } return NULL; } -bool inkscape_is_sole_desktop_for_document(SPDesktop const &desktop) { +bool +Application::sole_desktop_for_document(SPDesktop const &desktop) { SPDocument const* document = desktop.doc(); if (!document) { return false; } - for ( GSList *iter = inkscape->desktops ; iter ; iter = iter->next ) { - SPDesktop *other_desktop=static_cast<SPDesktop *>(iter->data); - SPDocument *other_document=other_desktop->doc(); + for ( std::vector<SPDesktop*>::iterator iter = _desktops->begin(), e = _desktops->end() ; iter != e; ++iter ) { + SPDesktop *other_desktop = *iter; + SPDocument *other_document = other_desktop->doc(); if ( other_document == document && other_desktop != &desktop ) { return false; } @@ -1308,7 +1137,7 @@ bool inkscape_is_sole_desktop_for_document(SPDesktop const &desktop) { } Inkscape::UI::Tools::ToolBase * -inkscape_active_event_context (void) +Application::active_event_context (void) { if (SP_ACTIVE_DESKTOP) { return SP_ACTIVE_DESKTOP->getEventContext(); @@ -1318,34 +1147,36 @@ inkscape_active_event_context (void) } Inkscape::ActionContext -inkscape_active_action_context() +Application::active_action_context() { if (SP_ACTIVE_DESKTOP) { return Inkscape::ActionContext(SP_ACTIVE_DESKTOP); } - SPDocument *doc = inkscape_active_document(); + SPDocument *doc = active_document(); if (!doc) { return Inkscape::ActionContext(); } - return inkscape_action_context_for_document(doc); + return action_context_for_document(doc); } Inkscape::ActionContext -inkscape_action_context_for_document(SPDocument *doc) +Application::action_context_for_document(SPDocument *doc) { // If there are desktops, check them first to see if the document is bound to one of them - for (GSList *iter = inkscape->desktops ; iter ; iter = iter->next) { - SPDesktop *desktop=static_cast<SPDesktop *>(iter->data); - if (desktop->doc() == doc) { - return Inkscape::ActionContext(desktop); + if (_desktops != NULL) { + for (std::vector<SPDesktop*>::iterator iter = _desktops->begin(), e = _desktops->end() ; iter != e ; ++iter) { + SPDesktop *desktop = *iter; + if (desktop->doc() == doc) { + return Inkscape::ActionContext(desktop); + } } } // Document is not associated with any desktops - maybe we're in command-line mode - std::map<SPDocument *, AppSelectionModel *>::iterator sel_iter = inkscape->selection_models.find(doc); - if (sel_iter == inkscape->selection_models.end()) { + std::map<SPDocument *, AppSelectionModel *>::iterator sel_iter = _selection_models.find(doc); + if (sel_iter == _selection_models.end()) { return Inkscape::ActionContext(); } return Inkscape::ActionContext(sel_iter->second->getSelection()); @@ -1357,10 +1188,10 @@ inkscape_action_context_for_document(SPDocument *doc) #####################*/ void -inkscape_refresh_display (InkscapeApplication *inkscape) +Application::refresh_display () { - for (GSList *l = inkscape->desktops; l != NULL; l = l->next) { - (static_cast<Inkscape::UI::View::View*>(l->data))->requestRedraw(); + for (std::vector<SPDesktop*>::iterator l = _desktops->begin(), e = _desktops->end(); l != e; ++l) { + (*l)->requestRedraw(); } } @@ -1370,26 +1201,26 @@ inkscape_refresh_display (InkscapeApplication *inkscape) * saves the preferences if appropriate, and quits. */ void -inkscape_exit (InkscapeApplication */*inkscape*/) +Application::exit () { - g_assert (INKSCAPE); - //emit shutdown signal so that dialogs could remember layout - g_signal_emit (G_OBJECT (INKSCAPE), inkscape_signals[SHUTDOWN_SIGNAL], 0); + signal_shut_down.emit(); Inkscape::Preferences::unload(); gtk_main_quit (); } char * -homedir_path(const char *filename) +Application::homedir_path(const char *filename) { static const gchar *homedir = NULL; if (!homedir) { homedir = g_get_home_dir(); } if (!homedir) { - homedir = g_path_get_dirname(INKSCAPE->argv0); + if (Application::exists()) { + homedir = g_path_get_dirname(Application::instance()._argv0); + } } return g_build_filename(homedir, filename, NULL); } @@ -1400,7 +1231,7 @@ homedir_path(const char *filename) * file should be located. */ gchar * -profile_path(const char *filename) +Application::profile_path(const char *filename) { static const gchar *prefdir = NULL; @@ -1512,21 +1343,21 @@ profile_path(const char *filename) } Inkscape::XML::Node * -inkscape_get_menus (InkscapeApplication * inkscape) +Application::get_menus() { - Inkscape::XML::Node *repr = inkscape->menus->root(); + Inkscape::XML::Node *repr = _menus->root(); g_assert (!(strcmp (repr->name(), "inkscape"))); return repr->firstChild(); } void -inkscape_get_all_desktops(std::list< SPDesktop* >& listbuf) +Application::get_all_desktops(std::list< SPDesktop* >& listbuf) { - for(GSList* l = inkscape->desktops; l != NULL; l = l->next) { - listbuf.push_back(static_cast< SPDesktop* >(l->data)); - } + listbuf.insert(listbuf.end(), _desktops->begin(), _desktops->end()); } +} // namespace Inkscape + /* Local Variables: mode:c++ diff --git a/src/inkscape.h b/src/inkscape.h index 3a9b85fc9..fe424377c 100644 --- a/src/inkscape.h +++ b/src/inkscape.h @@ -6,116 +6,220 @@ * * Authors: * Lauris Kaplinski <lauris@kaplinski.com> + * Liam P. White <inkscapebrony@gmail.com> * - * Copyright (C) 1999-2003 Authors + * Copyright (C) 1999-2014 Authors * * Released under GNU GPL, read the file 'COPYING' for more information */ -#include <list> +#include <map> +#include <vector> #include <glib.h> +#include <glib-object.h> +#include <sigc++/signal.h> +#include "layer-model.h" +#include "selection.h" class SPDesktop; class SPDocument; +struct SPColor; namespace Inkscape { + +class Application; namespace UI { namespace Tools { class ToolBase; -} -} -} - -struct InkscapeApplication; - -namespace Inkscape { - class ActionContext; - namespace XML { - class Node; - struct Document; - } -} - -#define INKSCAPE inkscape_get_instance() - -void inkscape_autosave_init(); - -void inkscape_application_init (const gchar *argv0, gboolean use_gui); - -bool inkscape_load_config (const gchar *filename, Inkscape::XML::Document *config, const gchar *skeleton, unsigned int skel_size, const gchar *e_notreg, const gchar *e_notxml, const gchar *e_notsp, const gchar *warn); - -/* Menus */ -bool inkscape_load_menus (InkscapeApplication * inkscape); -bool inkscape_save_menus (InkscapeApplication * inkscape); -Inkscape::XML::Node *inkscape_get_menus (InkscapeApplication * inkscape); - -InkscapeApplication *inkscape_get_instance(); -gboolean inkscape_use_gui(); - -bool inkscapeIsCrashing(); +} // namespace Tools +} // namespace UI -SPDesktop * inkscape_find_desktop_by_dkey (unsigned int dkey); +class ActionContext; -#define SP_ACTIVE_EVENTCONTEXT inkscape_active_event_context () -Inkscape::UI::Tools::ToolBase * inkscape_active_event_context (void); +namespace XML { +class Node; +struct Document; +} // namespace XML -#define SP_ACTIVE_DOCUMENT inkscape_active_document () -SPDocument * inkscape_active_document (void); +} // namespace Inkscape -#define SP_ACTIVE_DESKTOP inkscape_active_desktop () -SPDesktop * inkscape_active_desktop (void); +void inkscape_ref (Inkscape::Application & in); +void inkscape_unref(Inkscape::Application & in); -// Use this function to get selection model etc for a document, if possible! -// The "active" alternative below has all the horrible static cling of a singleton. -Inkscape::ActionContext -inkscape_action_context_for_document(SPDocument *doc); +#define INKSCAPE (Inkscape::Application::instance()) +#define SP_ACTIVE_EVENTCONTEXT (INKSCAPE.active_event_context()) +#define SP_ACTIVE_DOCUMENT (INKSCAPE.active_document()) +#define SP_ACTIVE_DESKTOP (INKSCAPE.active_desktop()) -// More horrible static cling... sorry about this. Should really replace all of -// the static stuff with a single instance of some kind of engine class holding -// all the document / non-GUI stuff, and an optional GUI class that behaves a -// bit like SPDesktop does currently. Then it will be easier to write good code -// that doesn't just expect a GUI all the time (like lots of the app currently -// does). -// Also, while the "active" document / desktop concepts are convenient, they -// appear to have been abused somewhat, further increasing static cling. -Inkscape::ActionContext inkscape_active_action_context(); +class AppSelectionModel { + Inkscape::LayerModel _layer_model; + Inkscape::Selection *_selection; -bool inkscape_is_sole_desktop_for_document(SPDesktop const &desktop); +public: + AppSelectionModel(SPDocument *doc) { + _layer_model.setDocument(doc); + // TODO: is this really how we should manage the lifetime of the selection? + // I just copied this from the initialization of the Selection in SPDesktop. + // When and how is it actually released? + _selection = Inkscape::GC::release(new Inkscape::Selection(&_layer_model, NULL)); + } -gchar *homedir_path(const char *filename); -gchar *profile_path(const char *filename); + Inkscape::Selection *getSelection() const { return _selection; } +}; -/* Inkscape desktop stuff */ -void inkscape_activate_desktop (SPDesktop * desktop); -void inkscape_switch_desktops_next (); -void inkscape_switch_desktops_prev (); -void inkscape_get_all_desktops (std::list< SPDesktop* >& listbuf); - -void inkscape_dialogs_hide (); -void inkscape_dialogs_unhide (); -void inkscape_dialogs_toggle (); - -void inkscape_external_change (); -void inkscape_subselection_changed (SPDesktop *desktop); - -/* Moved document add/remove functions into public inkscape.h as they are used - (rightly or wrongly) by console-mode functions */ -void inkscape_add_document (SPDocument *document); -bool inkscape_remove_document (SPDocument *document); - -/* - * fixme: This has to be rethought - */ - -void inkscape_refresh_display (InkscapeApplication *inkscape); - -/* - * fixme: This also - */ +namespace Inkscape { -void inkscape_exit (InkscapeApplication *inkscape); +class Application { +public: + static Application& instance(); + static bool exists(); + static void create(const char* argv0, bool use_gui); + + // returns the mask of the keyboard modifier to map to Alt, zero if no mapping + // Needs to be a guint because gdktypes.h does not define a 'no-modifier' value + guint mapalt() const { return _mapalt; } + + // Sets the keyboard modifer to map to Alt. Zero switches off mapping, as does '1', which is the default + void mapalt(guint maskvalue); + + guint trackalt() const { return _trackalt; } + void trackalt(guint trackvalue) { _trackalt = trackvalue; } + + bool use_gui() const { return _use_gui; } + void use_gui(gboolean guival) { _use_gui = guival; } + + char const* argv0() const { return _argv0; } + void argv0(char const *); + + // no setter for this -- only we can control this variable + static bool isCrashing() { return _crashIsHappening; } + + // useful functions + void autosave_init(); + void application_init (const gchar *argv0, gboolean use_gui); + void load_config (const gchar *filename, Inkscape::XML::Document *config, const gchar *skeleton, + unsigned int skel_size, const gchar *e_notreg, const gchar *e_notxml, + const gchar *e_notsp, const gchar *warn); + + bool load_menus(); + bool save_menus(); + Inkscape::XML::Node * get_menus(); + + Inkscape::UI::Tools::ToolBase * active_event_context(); + SPDocument * active_document(); + SPDesktop * active_desktop(); + + // Use this function to get selection model etc for a document + Inkscape::ActionContext action_context_for_document(SPDocument *doc); + Inkscape::ActionContext active_action_context(); + + bool sole_desktop_for_document(SPDesktop const &desktop); + + // Inkscape desktop stuff + void add_desktop(SPDesktop * desktop); + void remove_desktop(SPDesktop* desktop); + void activate_desktop (SPDesktop * desktop); + void switch_desktops_next (); + void switch_desktops_prev (); + void get_all_desktops (std::list< SPDesktop* >& listbuf); + void reactivate_desktop (SPDesktop * desktop); + SPDesktop * find_desktop_by_dkey (unsigned int dkey); + unsigned int maximum_dkey(); + SPDesktop * next_desktop (); + SPDesktop * prev_desktop (); + + void dialogs_hide (); + void dialogs_unhide (); + void dialogs_toggle (); + + void external_change (); + void selection_modified (Inkscape::Selection *selection, guint flags); + void selection_changed (Inkscape::Selection * selection); + void subselection_changed (SPDesktop *desktop); + void selection_set (Inkscape::Selection * selection); + + void eventcontext_set (Inkscape::UI::Tools::ToolBase * eventcontext); + + // Moved document add/remove functions into public inkscape.h as they are used + // (rightly or wrongly) by console-mode functions + void add_document (SPDocument *document); + bool remove_document (SPDocument *document); + + static char *homedir_path(const char *filename); + static char *profile_path(const char *filename); + + // fixme: This has to be rethought + void refresh_display (); + + // fixme: This also + void exit (); + + static void crash_handler(int signum); + + int autosave(); + + // nobody should be accessing our reference count, so it's made private. + friend void ::inkscape_ref (Application & in); + friend void ::inkscape_unref(Application & in); + + // signals + + // one of selections changed + sigc::signal<void, Inkscape::Selection *> signal_selection_changed; + // one of subselections (text selection, gradient handle, etc) changed + sigc::signal<void, SPDesktop *> signal_subselection_changed; + // one of selections modified + sigc::signal<void, Inkscape::Selection *, guint /*flags*/> signal_selection_modified; + // one of selections set + sigc::signal<void, Inkscape::Selection *> signal_selection_set; + // tool switched + sigc::signal<void, Inkscape::UI::Tools::ToolBase * /*eventcontext*/> signal_eventcontext_set; + // some desktop got focus + sigc::signal<void, SPDesktop *> signal_activate_desktop; + // some desktop lost focus + sigc::signal<void, SPDesktop *> signal_deactivate_desktop; + + // these are orphaned signals (nothing emits them and nothing connects to them) + sigc::signal<void, SPDocument *> signal_destroy_document; + sigc::signal<void, SPColor *, double /*opacity*/> signal_color_set; + + // inkscape is quitting + sigc::signal<void> signal_shut_down; + // user pressed F12 + sigc::signal<void> signal_dialogs_hide; + // user pressed F12 + sigc::signal<void> signal_dialogs_unhide; + // a document was changed by some external means (undo or XML editor); this + // may not be reflected by a selection change and thus needs a separate signal + sigc::signal<void> signal_external_change; + +private: + static Inkscape::Application * _S_inst; + + Application(const char* argv0, bool use_gui); + ~Application(); + + Application(Application const&); // no copy + Application& operator=(Application const&); // no assign + Application* operator&() const; // no pointer access + + Inkscape::XML::Document * _menus; + std::map<SPDocument *, int> _document_set; + std::map<SPDocument *, AppSelectionModel *> _selection_models; + std::vector<SPDesktop *> * _desktops; + + unsigned refCount; + bool _dialogs_toggle; + guint _mapalt; + guint _trackalt; + char * _argv0; + static bool _crashIsHappening; + bool _use_gui; +}; + +} // namespace Inkscape #endif diff --git a/src/inkview.cpp b/src/inkview.cpp index 2969bb140..0b7b4d35c 100644 --- a/src/inkview.cpp +++ b/src/inkview.cpp @@ -60,9 +60,7 @@ #include "io/inkjar.h" #endif -#include "inkscape-private.h" - -InkscapeApplication *inkscape; +#include "inkscape.h" #include <iostream> @@ -232,7 +230,8 @@ main (int argc, const char **argv) ss.view = NULL; ss.fullscreen = false; - inkscape = (InkscapeApplication *)g_object_new (SP_TYPE_INKSCAPE, NULL); + Inkscape::Application::create(argv[0], true); + //Inkscape::Application &inkscape = Inkscape::Application::instance(); // starting at where the commandline options stopped parsing because // we want all the files to be in the list diff --git a/src/io/resource.cpp b/src/io/resource.cpp index ac1c5f06b..501eab03b 100644 --- a/src/io/resource.cpp +++ b/src/io/resource.cpp @@ -73,7 +73,7 @@ Util::ptr_shared<char> get_path(Domain domain, Type type, char const *filename) case TEMPLATES: name = "templates"; break; default: return get_path(SYSTEM, type, filename); } - path = profile_path(name); + path = Inkscape::Application::profile_path(name); } break; } diff --git a/src/libnrtype/Layout-TNG-Compute.cpp b/src/libnrtype/Layout-TNG-Compute.cpp index 7eb53446f..bd1acbe46 100644 --- a/src/libnrtype/Layout-TNG-Compute.cpp +++ b/src/libnrtype/Layout-TNG-Compute.cpp @@ -704,6 +704,7 @@ static void dumpUnbrokenSpans(ParagraphInfo *para){ // create the Layout::Character(s) double advance_width = new_glyph.width; if (newcluster){ + newcluster = 0; // find where the text ends for this log_cluster end_byte = it_span->start.iter_span->text_bytes; // Upper limit for(int next_glyph_index = glyph_index+1; next_glyph_index < unbroken_span.glyph_string->num_glyphs; next_glyph_index++){ @@ -751,18 +752,15 @@ static void dumpUnbrokenSpans(ParagraphInfo *para){ log_cluster_size_chars--; } - if (newcluster){ - advance_width *= direction_sign; - if (new_span.direction != para.direction) { - counter_directional_width_remaining -= advance_width; - x -= advance_width; - x_in_span_last -= advance_width; - } else { - x += advance_width; - x_in_span_last += advance_width; - } + advance_width *= direction_sign; + if (new_span.direction != para.direction) { + counter_directional_width_remaining -= advance_width; + x -= advance_width; + x_in_span_last -= advance_width; + } else { + x += advance_width; + x_in_span_last += advance_width; } - newcluster = 0; } } else if (_flow._input_stream[unbroken_span.input_index]->Type() == CONTROL_CODE) { x += static_cast<InputStreamControlCode const *>(_flow._input_stream[unbroken_span.input_index])->width; @@ -1080,7 +1078,9 @@ void Layout::Calculator::_computeFontLineHeight(font_instance *font, double font bool compareGlyphWidth(const PangoGlyphInfo &a, const PangoGlyphInfo &b) { - return (a.geometry.width > b.geometry.width); + bool retval = false; + if ( b.geometry.width == 0 && (a.geometry.width > 0))retval = true; + return (retval); } @@ -1227,13 +1227,27 @@ unsigned Layout::Calculator::_buildSpansForPara(ParagraphInfo *para) const /* CAREFUL, within a log_cluster the order of glyphs may not map 1:1, or even in the same order, to the original unicode characters!!! Among - other things, diacritical mark glyphs can end up in front of the base - character. That makes determining kerning, even approximately, difficult - later on. To resolve this somewhat sort the glyphs with the same - log_cluster into descending order by width. In theory there should be 1 - that is nonzero, and N that are zero. The order of the zero width ones - does not matter. Sort the glyphs before copying. If ligatures other than with - Mark, nonspacing are ever implemented in Pango this will screw up, for instance + other things, diacritical mark glyphs can end up sequentially in front of the base + character glyph. That makes determining kerning, even approximately, difficult + later on. + + To resolve this to the extent possible sort the glyphs within the same + log_cluster into descending order by width in a special manner before copying. Diacritical marks + and similar have zero width and the glyph they modify has nonzero width. The order + of the zero width ones does not matter. A logical cluster is sorted into sequential order + [base] [zw_modifier1] [zw_modifier2] + where all the modifiers have zero width and the base does not. This works for languages like Hebrew. + + Pango also creates log clusters for languages like Telugu having many glyphs with nonzero widths. + Since these are nonzero, their order is not modified. + + If some language mixes these modes, having a log cluster having something like + [base1] [zw_modifier1] [base2] [zw_modifier2] + the result will be incorrect: + base1] [base2] [zw_modifier1] [zw_modifier2] + + + If ligatures other than with Mark, nonspacing are ever implemented in Pango this will screw up, for instance changing "fi" to "if". */ if(j - i){ @@ -1258,6 +1272,7 @@ unsigned Layout::Calculator::_buildSpansForPara(ParagraphInfo *para) const while( (j < nglyphs-1) && (new_span.glyph_string->log_clusters[j+1] == new_span.glyph_string->log_clusters[i]) )j++; + /* see note in preceding section */ if(j - i){ std::sort(&(new_span.glyph_string->glyphs[i]), &(new_span.glyph_string->glyphs[j+1]), compareGlyphWidth); } diff --git a/src/line-geometry.cpp b/src/line-geometry.cpp index 566af8840..1f6329be0 100644 --- a/src/line-geometry.cpp +++ b/src/line-geometry.cpp @@ -201,7 +201,7 @@ boost::optional<Geom::Point> Line::intersection_with_viewbox (SPDesktop *desktop void create_canvas_point(Geom::Point const &pos, double size, guint32 rgba) { - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; SPCanvasItem * canvas_pt = sp_canvas_item_new(sp_desktop_controls(desktop), SP_TYPE_CTRL, "size", size, "filled", 1, @@ -214,7 +214,7 @@ void create_canvas_point(Geom::Point const &pos, double size, guint32 rgba) void create_canvas_line(Geom::Point const &p1, Geom::Point const &p2, guint32 rgba) { - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; SPCtrlLine *line = ControlManager::getManager().createControlLine(sp_desktop_controls(desktop), p1, p2); line->setRgba32(rgba); sp_canvas_item_show(line); diff --git a/src/live_effects/effect.cpp b/src/live_effects/effect.cpp index 0f4bdfaaa..4a323cc7e 100644 --- a/src/live_effects/effect.cpp +++ b/src/live_effects/effect.cpp @@ -451,7 +451,7 @@ void Effect::doOnRemove (SPLPEItem const* /*lpeitem*/) void Effect::doOnApply_impl(SPLPEItem const* lpeitem) { sp_lpe_item = const_cast<SPLPEItem *>(lpeitem); - defaultUnit = &sp_lpe_item->document->getDefaultUnit()->abbr; + defaultUnit = &sp_lpe_item->document->getDisplayUnit()->abbr; /*sp_curve = SP_SHAPE(sp_lpe_item)->getCurve(); pathvector_before_effect = sp_curve->get_pathvector();*/ doOnApply(lpeitem); @@ -460,7 +460,7 @@ void Effect::doOnApply_impl(SPLPEItem const* lpeitem) void Effect::doBeforeEffect_impl(SPLPEItem const* lpeitem) { sp_lpe_item = const_cast<SPLPEItem *>(lpeitem); - defaultUnit = &sp_lpe_item->document->getDefaultUnit()->abbr; + defaultUnit = &sp_lpe_item->document->getDisplayUnit()->abbr; //printf("(SPLPEITEM*) %p\n", sp_lpe_item); sp_curve = SP_SHAPE(sp_lpe_item)->getCurve(); pathvector_before_effect = sp_curve->get_pathvector(); @@ -477,7 +477,7 @@ void Effect::doAcceptPathPreparations(SPLPEItem *lpeitem) { // switch to pen context - SPDesktop *desktop = inkscape_active_desktop(); // TODO: Is there a better method to find the item's desktop? + SPDesktop *desktop = SP_ACTIVE_DESKTOP; // TODO: Is there a better method to find the item's desktop? if (!tools_isactive(desktop, TOOLS_FREEHAND_PEN)) { tools_switch(desktop, TOOLS_FREEHAND_PEN); } diff --git a/src/live_effects/lpe-bspline.cpp b/src/live_effects/lpe-bspline.cpp index 97a4c6205..2bed90139 100644 --- a/src/live_effects/lpe-bspline.cpp +++ b/src/live_effects/lpe-bspline.cpp @@ -88,25 +88,12 @@ void LPEBSpline::doBeforeEffect (SPLPEItem const* /*lpeitem*/) } -void LPEBSpline::createAndApply(const char *name, SPDocument *doc, - SPItem *item) +void LPEBSpline::doOnApply(SPLPEItem const* lpeitem) { - if (!SP_IS_SHAPE(item)) { + if (!SP_IS_SHAPE(lpeitem)) { g_warning("LPE BSpline can only be applied to shapes (not groups)."); - } else { - // Path effect definition - Inkscape::XML::Document *xml_doc = doc->getReprDoc(); - Inkscape::XML::Node *repr = xml_doc->createElement("inkscape:path-effect"); - repr->setAttribute("effect", name); - - doc->getDefs()->getRepr() - ->addChild(repr, NULL); // adds to <defs> and assigns the 'id' attribute - const gchar *repr_id = repr->attribute("id"); - Inkscape::GC::release(repr); - - gchar *href = g_strdup_printf("#%s", repr_id); - SP_LPE_ITEM(item)->addPathEffect(href, true); - g_free(href); + SPLPEItem * item = const_cast<SPLPEItem*>(lpeitem); + item->removeCurrentPathEffect(false); } } @@ -380,6 +367,7 @@ void LPEBSpline::doBSplineFromWidget(SPCurve *curve, double weightValue) { using Geom::X; using Geom::Y; + if (curve->get_segment_count() < 1) return; // Make copy of old path as it is changed during processing diff --git a/src/live_effects/lpe-bspline.h b/src/live_effects/lpe-bspline.h index 8751a5720..a17c0c4ac 100644 --- a/src/live_effects/lpe-bspline.h +++ b/src/live_effects/lpe-bspline.h @@ -19,10 +19,10 @@ public: LPEBSpline(LivePathEffectObject *lpeobject); virtual ~LPEBSpline(); - virtual void createAndApply(const char *name, SPDocument *doc, SPItem *item); virtual LPEPathFlashType pathFlashType() const { return SUPPRESS_FLASH; } + virtual void doOnApply(SPLPEItem const* lpeitem); virtual void doEffect(SPCurve *curve); virtual void doBeforeEffect (SPLPEItem const* lpeitem); void drawHandle(Geom::Point p, double radiusHelperNodes); diff --git a/src/live_effects/lpe-copy_rotate.cpp b/src/live_effects/lpe-copy_rotate.cpp index e0855d452..553f273fe 100644 --- a/src/live_effects/lpe-copy_rotate.cpp +++ b/src/live_effects/lpe-copy_rotate.cpp @@ -48,6 +48,7 @@ LPECopyRotate::LPECopyRotate(LivePathEffectObject *lpeobject) : num_copies(_("Number of copies:"), _("Number of copies of the original path"), "num_copies", &wr, this, 5), copiesTo360(_("360º Copies"), _("No rotation angle, fixed to 360º"), "copiesTo360", &wr, this, true), fusionPaths(_("Fusioned paths"), _("Fusion paths"), "fusionPaths", &wr, this, true), + origin(_("Origin"), _("Origin of the rotation"), "origin", &wr, this, "Adjust the origin of the rotation"), dist_angle_handle(100) { diff --git a/src/live_effects/lpe-fillet-chamfer.cpp b/src/live_effects/lpe-fillet-chamfer.cpp index 78e24f0b8..119759b87 100644 --- a/src/live_effects/lpe-fillet-chamfer.cpp +++ b/src/live_effects/lpe-fillet-chamfer.cpp @@ -79,7 +79,7 @@ LPEFilletChamfer::LPEFilletChamfer(LivePathEffectObject *lpeobject) : radius.param_set_range(0., infinity()); radius.param_set_increments(1, 1); radius.param_set_digits(4); - chamfer_steps.param_set_range(0, 999); + chamfer_steps.param_set_range(1, 999); chamfer_steps.param_set_increments(1, 1); chamfer_steps.param_set_digits(0); helper_size.param_set_range(0, infinity()); @@ -431,6 +431,8 @@ void LPEFilletChamfer::doOnApply(SPLPEItem const *lpeItem) fillet_chamfer_values.param_set_and_write_new_value(point); } else { g_warning("LPE Fillet can only be applied to shapes (not groups)."); + SPLPEItem * item = const_cast<SPLPEItem*>(lpeItem); + item->removeCurrentPathEffect(false); } } @@ -578,8 +580,10 @@ LPEFilletChamfer::doEffect_path(std::vector<Geom::Path> const &path_in) } else { type = std::abs(filletChamferData[counter + 1][Y]); } - if (type >= 3000 && type < 4000) { - unsigned int chamferSubs = type-2999; + if(are_near(middle_point(startArcPoint,endArcPoint),curve_it1->finalPoint(), 0.0001)){ + path_out.appendNew<Geom::LineSegment>(endArcPoint); + } else if (type >= 3000 && type < 4000) { + unsigned int chamferSubs = type-3000; Geom::Path path_chamfer; path_chamfer.start(path_out.finalPoint()); if((is_straight_curve(*curve_it1) && is_straight_curve(*curve_it2Fixed) && method != FM_BEZIER )|| method == FM_ARC){ @@ -594,7 +598,7 @@ LPEFilletChamfer::doEffect_path(std::vector<Geom::Path> const &path_in) } path_out.appendNew<Geom::LineSegment>(endArcPoint); } else if (type >= 4000 && type < 5000) { - unsigned int chamferSubs = type-3999; + unsigned int chamferSubs = type-4000; Geom::Path path_chamfer; path_chamfer.start(path_out.finalPoint()); if((is_straight_curve(*curve_it1) && is_straight_curve(*curve_it2Fixed) && method != FM_BEZIER )|| method == FM_ARC){ diff --git a/src/live_effects/lpe-perspective_path.cpp b/src/live_effects/lpe-perspective_path.cpp index d43772cf7..901519b4f 100644 --- a/src/live_effects/lpe-perspective_path.cpp +++ b/src/live_effects/lpe-perspective_path.cpp @@ -23,7 +23,7 @@ #include "knot-holder-entity.h" #include "knotholder.h" #include "desktop.h" - +#include <util/units.h> #include "inkscape.h" #include <2geom/path.h> @@ -44,6 +44,8 @@ public: } // namespace PP static Glib::ustring perspectiveID = _("First perspective"); + + LPEPerspectivePath::LPEPerspectivePath(LivePathEffectObject *lpeobject) : Effect(lpeobject), // initialise your parameters here: @@ -62,35 +64,42 @@ LPEPerspectivePath::LPEPerspectivePath(LivePathEffectObject *lpeobject) : concatenate_before_pwd2 = true; // don't split the path into its subpaths _provides_knotholder_entities = true; - unapply = false; - Persp3D *persp = persp3d_document_first_persp(lpeobject->document); +} + +LPEPerspectivePath::~LPEPerspectivePath() +{ + +} +void +LPEPerspectivePath::doOnApply(SPLPEItem const* lpeitem) +{ + Persp3D *persp = persp3d_document_first_persp(lpeitem->document); if(persp == 0 ){ char *msg = _("You need a BOX 3D object"); Gtk::MessageDialog dialog(msg, false, Gtk::MESSAGE_INFO, Gtk::BUTTONS_OK, true); dialog.run(); - unapply = true; - return; + SPLPEItem * item = const_cast<SPLPEItem*>(lpeitem); + item->removeCurrentPathEffect(false); } - Proj::TransfMat3x4 pmat = persp->perspective_impl->tmat; - pmat = pmat * SP_ACTIVE_DESKTOP->doc2dt(); - pmat.copy_tmat(tmat); } - -LPEPerspectivePath::~LPEPerspectivePath() -{ - -} - void LPEPerspectivePath::doBeforeEffect (SPLPEItem const* lpeitem) { original_bbox(lpeitem, true); - if(unapply){ - SP_LPE_ITEM(lpeitem)->removeCurrentPathEffect(false); + SPLPEItem * item = const_cast<SPLPEItem*>(lpeitem); + Persp3D *persp = persp3d_document_first_persp(lpeitem->document); + if(persp == 0 ){ + char *msg = _("You need a BOX 3D object"); + Gtk::MessageDialog dialog(msg, false, Gtk::MESSAGE_INFO, + Gtk::BUTTONS_OK, true); + dialog.run(); return; } - SPLPEItem * item = const_cast<SPLPEItem*>(lpeitem); + Proj::TransfMat3x4 pmat = persp->perspective_impl->tmat; + Geom::Affine doc2d = Geom::Scale(1, -1) * Geom::Translate(0, item->document->getHeight().value("px")); + pmat = pmat * doc2d; + pmat.copy_tmat(tmat); item->apply_to_clippath(item); item->apply_to_mask(item); } diff --git a/src/live_effects/lpe-perspective_path.h b/src/live_effects/lpe-perspective_path.h index 6ccac4a51..c4ddf1853 100644 --- a/src/live_effects/lpe-perspective_path.h +++ b/src/live_effects/lpe-perspective_path.h @@ -33,9 +33,8 @@ class LPEPerspectivePath : public Effect, GroupBBoxEffect { public: LPEPerspectivePath(LivePathEffectObject *lpeobject); virtual ~LPEPerspectivePath(); - virtual void doBeforeEffect (SPLPEItem const* lpeitem); - + virtual void doOnApply(SPLPEItem const* lpeitem); virtual Geom::Piecewise<Geom::D2<Geom::SBasis> > doEffect_pwd2 (Geom::Piecewise<Geom::D2<Geom::SBasis> > const & pwd2_in); virtual void refresh(Gtk::Entry* perspective); @@ -53,8 +52,6 @@ private: ScalarParam offsety; BoolParam uses_plane_xy; // there are all kinds of parameters. Check the /live_effects/parameter directory which types exist! - - bool unapply; Geom::Point orig; LPEPerspectivePath(const LPEPerspectivePath&); diff --git a/src/live_effects/lpe-roughen.cpp b/src/live_effects/lpe-roughen.cpp index 07d9e63e8..8cef9a3a3 100644 --- a/src/live_effects/lpe-roughen.cpp +++ b/src/live_effects/lpe-roughen.cpp @@ -160,11 +160,11 @@ double LPERoughen::sign(double randNumber) Geom::Point LPERoughen::randomize() { - Inkscape::Util::Unit const *doc_units = SP_ACTIVE_DESKTOP->namedview->doc_units; + Inkscape::Util::Unit const *svg_units = SP_ACTIVE_DESKTOP->namedview->svg_units; double displaceXParsed = Inkscape::Util::Quantity::convert( - displaceX * globalRandomize, unit.get_abbreviation(), doc_units->abbr); + displaceX * globalRandomize, unit.get_abbreviation(), svg_units->abbr); double displaceYParsed = Inkscape::Util::Quantity::convert( - displaceY * globalRandomize, unit.get_abbreviation(), doc_units->abbr); + displaceY * globalRandomize, unit.get_abbreviation(), svg_units->abbr); Geom::Point output = Geom::Point(sign(displaceXParsed), sign(displaceYParsed)); return output; @@ -175,7 +175,7 @@ void LPERoughen::doEffect(SPCurve *curve) Geom::PathVector const original_pathv = pathv_to_linear_and_cubic_beziers(curve->get_pathvector()); curve->reset(); - Inkscape::Util::Unit const *doc_units = SP_ACTIVE_DESKTOP->namedview->doc_units; + Inkscape::Util::Unit const *svg_units = SP_ACTIVE_DESKTOP->namedview->svg_units; for (Geom::PathVector::const_iterator path_it = original_pathv.begin(); path_it != original_pathv.end(); ++path_it) { if (path_it->empty()) @@ -221,7 +221,7 @@ void LPERoughen::doEffect(SPCurve *curve) nCurve->lineto(A3); } double length = Inkscape::Util::Quantity::convert( - curve_it1->length(0.001), doc_units->abbr, unit.get_abbreviation()); + curve_it1->length(0.001), svg_units->abbr, unit.get_abbreviation()); std::size_t splits = 0; if (method == DM_SEGMENTS) { splits = segments; diff --git a/src/live_effects/parameter/filletchamferpointarray.cpp b/src/live_effects/parameter/filletchamferpointarray.cpp index 4e2be6e88..7d8c8e9b0 100644 --- a/src/live_effects/parameter/filletchamferpointarray.cpp +++ b/src/live_effects/parameter/filletchamferpointarray.cpp @@ -693,28 +693,6 @@ void FilletChamferPointArrayParam::set_oncanvas_looks(SPKnotShapeType shape, knot_mode = mode; knot_color = color; } -/* -class FilletChamferPointArrayParamKnotHolderEntity : public KnotHolderEntity { -public: - FilletChamferPointArrayParamKnotHolderEntity(FilletChamferPointArrayParam -*p, unsigned int index); - virtual ~FilletChamferPointArrayParamKnotHolderEntity() {} - - virtual void knot_set(Point const &p, Point const &origin, guint state); - virtual Point knot_get() const; - virtual void knot_click(guint state); - virtual void knot_doubleclicked(guint state); - - /Checks whether the index falls within the size of the parameter's vector/ - bool valid_index(unsigned int index) const { - return (_pparam->_vector.size() > index); - }; - -private: - FilletChamferPointArrayParam *_pparam; - unsigned int _index; -}; -/*/ FilletChamferPointArrayParamKnotHolderEntity:: FilletChamferPointArrayParamKnotHolderEntity( @@ -730,11 +708,10 @@ void FilletChamferPointArrayParamKnotHolderEntity::knot_set(Point const &p, if (!valid_index(_index)) { return; } - /// @todo how about item transforms??? Piecewise<D2<SBasis> > const &pwd2 = _pparam->get_pwd2(); - //todo: add snapping - Geom::Point const s = snap_knot_position(p, state); double t = nearest_point(p, pwd2[_index]); + Geom::Point const s = snap_knot_position(pwd2[_index].valueAt(t), state); + t = nearest_point(s, pwd2[_index]); if (t == 1) { t = 0.9999; } diff --git a/src/live_effects/parameter/text.cpp b/src/live_effects/parameter/text.cpp index 956a001ad..a88ac7d75 100644 --- a/src/live_effects/parameter/text.cpp +++ b/src/live_effects/parameter/text.cpp @@ -32,7 +32,7 @@ TextParam::TextParam( const Glib::ustring& label, const Glib::ustring& tip, value(default_value), defvalue(default_value) { - SPDesktop *desktop = inkscape_active_desktop(); // FIXME: we shouldn't use this! + SPDesktop *desktop = SP_ACTIVE_DESKTOP; // FIXME: we shouldn't use this! canvas_text = (SPCanvasText *) sp_canvastext_new(sp_desktop_tempgroup(desktop), desktop, Geom::Point(0,0), ""); sp_canvastext_set_text (canvas_text, default_value.c_str()); sp_canvastext_set_coords (canvas_text, 0, 0); diff --git a/src/main-cmdlineact.cpp b/src/main-cmdlineact.cpp index 6af616e34..216953f4f 100644 --- a/src/main-cmdlineact.cpp +++ b/src/main-cmdlineact.cpp @@ -82,7 +82,7 @@ CmdLineAction::doList (ActionContext const & context) { bool CmdLineAction::idle (void) { std::list<SPDesktop *> desktops; - inkscape_get_all_desktops(desktops); + INKSCAPE.get_all_desktops(desktops); // We're going to assume one desktop per document, because no one // should have had time to make more at this point. diff --git a/src/main.cpp b/src/main.cpp index 12ddb76e6..06c0d4873 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -74,7 +74,7 @@ #include "svg/svg-color.h" #include "svg/stringstream.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "inkscape-version.h" #include "sp-namedview.h" @@ -933,9 +933,9 @@ guint get_group0_keyval(GdkEventKey const* event); static void snooper(GdkEvent *event, gpointer /*data*/) { - if (inkscape_mapalt()) /* returns the map of the keyboard modifier to map to Alt, zero if no mapping */ + if (INKSCAPE.mapalt()) /* returns the map of the keyboard modifier to map to Alt, zero if no mapping */ { - GdkModifierType mapping=(GdkModifierType)inkscape_mapalt(); + GdkModifierType mapping=(GdkModifierType)INKSCAPE.mapalt(); switch (event->type) { case GDK_MOTION_NOTIFY: if(event->motion.state & mapping) { @@ -957,7 +957,7 @@ snooper(GdkEvent *event, gpointer /*data*/) { } } - if (inkscape_trackalt()) { + if (INKSCAPE.trackalt()) { // MacOS X with X11 has some problem with the default // xmodmapping. A ~/.xmodmap solution does not work reliably due // to the way we package our executable in a .app that can launch @@ -1042,7 +1042,7 @@ sp_main_gui(int argc, char const **argv) } // Add our icon directory to the search path for icon theme lookups. - gchar *usericondir = profile_path("icons"); + gchar *usericondir = Inkscape::Application::profile_path("icons"); gtk_icon_theme_append_search_path(gtk_icon_theme_get_default(), usericondir); gtk_icon_theme_append_search_path(gtk_icon_theme_get_default(), INKSCAPE_PIXMAPDIR); g_free(usericondir); @@ -1059,7 +1059,7 @@ sp_main_gui(int argc, char const **argv) gboolean create_new = TRUE; /// \todo FIXME BROKEN - non-UTF-8 sneaks in here. - inkscape_application_init(argv[0], true); + Inkscape::Application::create(argv[0], true); while (fl) { if (sp_file_open((gchar *)fl->data,NULL)) { @@ -1125,14 +1125,14 @@ static int sp_process_file_list(GSList *fl) retVal++; } else { - inkscape_add_document(doc); + INKSCAPE.add_document(doc); if (sp_vacuum_defs) { doc->vacuumDocument(); } // Execute command-line actions (selections and verbs) using our local models - bool has_performed_actions = Inkscape::CmdLineAction::doList(inkscape_active_action_context()); + bool has_performed_actions = Inkscape::CmdLineAction::doList(INKSCAPE.active_action_context()); #ifdef WITH_DBUS // If we've been asked to listen for D-Bus messages, enter a main loop here @@ -1221,7 +1221,7 @@ static int sp_process_file_list(GSList *fl) do_query_dimension (doc, false, sp_query_x? Geom::X : Geom::Y, sp_query_id); } - inkscape_remove_document(doc); + INKSCAPE.remove_document(doc); delete doc; } @@ -1335,7 +1335,7 @@ int sp_main_console(int argc, char const **argv) exit(0); } - inkscape_application_init(argv[0], false); + Inkscape::Application::create(argv[0], false); if (sp_shell) { int retVal = sp_main_shell(argv[0]); // Run as interactive shell diff --git a/src/persp3d.cpp b/src/persp3d.cpp index b10e5f23b..d2c6978bb 100644 --- a/src/persp3d.cpp +++ b/src/persp3d.cpp @@ -140,7 +140,7 @@ void Persp3D::set(unsigned key, gchar const *value) { } // FIXME: Is this the right place for resetting the draggers? - Inkscape::UI::Tools::ToolBase *ec = inkscape_active_event_context(); + Inkscape::UI::Tools::ToolBase *ec = INKSCAPE.active_event_context(); if (SP_IS_BOX3D_CONTEXT(ec)) { Inkscape::UI::Tools::Box3dTool *bc = SP_BOX3D_CONTEXT(ec); bc->_vpdrag->updateDraggers(); @@ -289,7 +289,7 @@ persp3d_toggle_VP (Persp3D *persp, Proj::Axis axis, bool set_undo) { persp3d_update_box_reprs (persp); persp->updateRepr(SP_OBJECT_WRITE_EXT); if (set_undo) { - DocumentUndo::done(sp_desktop_document(inkscape_active_desktop()), SP_VERB_CONTEXT_3DBOX, + DocumentUndo::done(sp_desktop_document(SP_ACTIVE_DESKTOP), SP_VERB_CONTEXT_3DBOX, _("Toggle vanishing point")); } } @@ -300,7 +300,7 @@ persp3d_toggle_VPs (std::list<Persp3D *> p, Proj::Axis axis) { for (std::list<Persp3D *>::iterator i = p.begin(); i != p.end(); ++i) { persp3d_toggle_VP((*i), axis, false); } - DocumentUndo::done(sp_desktop_document(inkscape_active_desktop()), SP_VERB_CONTEXT_3DBOX, + DocumentUndo::done(sp_desktop_document(SP_ACTIVE_DESKTOP), SP_VERB_CONTEXT_3DBOX, _("Toggle multiple vanishing points")); } @@ -527,7 +527,7 @@ persp3d_print_all_selected() { g_print ("\n======================================\n"); g_print ("Selected perspectives and their boxes:\n"); - std::list<Persp3D *> sel_persps = sp_desktop_selection(inkscape_active_desktop())->perspList(); + std::list<Persp3D *> sel_persps = sp_desktop_selection(SP_ACTIVE_DESKTOP)->perspList(); for (std::list<Persp3D *>::iterator j = sel_persps.begin(); j != sel_persps.end(); ++j) { Persp3D *persp = SP_PERSP3D(*j); diff --git a/src/preferences.cpp b/src/preferences.cpp index d0c3783b5..e5a5fe7f0 100644 --- a/src/preferences.cpp +++ b/src/preferences.cpp @@ -91,11 +91,13 @@ Preferences::Preferences() : _hasError(false) { // profile_path essentailly returns the argument prefixed by the profile directory. - gchar *path = profile_path(NULL); + // \TODO this is kinda hackish, but the alternative (strrchr) is worse + + gchar *path = Inkscape::Application::profile_path(NULL); _prefs_dir = path; g_free(path); - path = profile_path(_prefs_basename.c_str()); + path = Inkscape::Application::profile_path(_prefs_basename.c_str()); _prefs_filename = path; g_free(path); @@ -155,7 +157,7 @@ void Preferences::_load() // create some subdirectories for user stuff char const *user_dirs[] = {"keys", "templates", "icons", "extensions", "palettes", NULL}; for (int i=0; user_dirs[i]; ++i) { - char *dir = profile_path(user_dirs[i]); + char *dir = Inkscape::Application::profile_path(user_dirs[i]); g_mkdir(dir, 0755); g_free(dir); } diff --git a/src/selection-chemistry.cpp b/src/selection-chemistry.cpp index d00e8d702..83a943f53 100644 --- a/src/selection-chemistry.cpp +++ b/src/selection-chemistry.cpp @@ -99,7 +99,7 @@ SPCycleType SP_CYCLING = SP_CYCLE_FOCUS; #include "display/curve.h" #include "display/canvas-bpath.h" #include "display/cairo-utils.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "path-chemistry.h" #include "ui/tool/control-point-selection.h" #include "ui/tool/multi-path-manipulator.h" @@ -521,11 +521,9 @@ void sp_selection_duplicate(SPDesktop *desktop, bool suppressDone) if (!strcmp(orig->getId(), old_ids[j])) { // we have both orig and clone in selection, relink // std::cout << id << " old, its ori: " << orig->getId() << "; will relink:" << new_ids[i] << " to " << new_ids[j] << "\n"; - gchar *newref = g_strdup_printf("#%s", new_ids[j]); SPObject *new_clone = doc->getObjectById(new_ids[i]); - new_clone->getRepr()->setAttribute("xlink:href", newref); + new_clone->getRepr()->setAttribute("xlink:href", Glib::ustring("#") + new_ids[j]); new_clone->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); - g_free(newref); } } } else { @@ -534,9 +532,7 @@ void sp_selection_duplicate(SPDesktop *desktop, bool suppressDone) for (guint j = 0; j < old_ids.size(); j++) { gchar *source_href = offset->sourceHref; if (source_href && source_href[0]=='#' && !strcmp(source_href+1, old_ids[j])) { - gchar *newref = g_strdup_printf("#%s", new_ids[j]); - doc->getObjectById(new_ids[i])->getRepr()->setAttribute("xlink:href", newref); - g_free(newref); + doc->getObjectById(new_ids[i])->getRepr()->setAttribute("xlink:href", Glib::ustring("#") + new_ids[j]); } } } @@ -1643,7 +1639,7 @@ void sp_selection_apply_affine(Inkscape::Selection *selection, Geom::Affine cons item->doWriteTransform(item->getRepr(), move, &move, compensate); } else if (prefs_unmoved) { - //if (SP_IS_USE(sp_use_get_original(SP_USE(item)))) + //if (dynamic_cast<SPUse *>(sp_use_get_original(dynamic_cast<SPUse *>(item)))) // clone_move = Geom::identity(); Geom::Affine move = result * clone_move; item->doWriteTransform(item->getRepr(), move, &t, compensate); @@ -2884,17 +2880,19 @@ void sp_selection_clone_original_path_lpe(SPDesktop *desktop) if (desktop == NULL) { return; } - + + Inkscape::Selection *selection = sp_desktop_selection(desktop); + Inkscape::SVGOStringStream os; SPObject * firstItem = NULL; - for (const GSList * item = desktop->selection->itemList(); item != NULL; item = item->next) { + for (const GSList * item = selection->itemList(); item != NULL; item = item->next) { if (SP_IS_SHAPE(item->data) || SP_IS_TEXT(item->data)) { if (firstItem) { os << "|"; } else { firstItem = SP_ITEM(item->data); } - os << "#" << SP_ITEM(item->data)->getId() << ",0"; + os << '#' << SP_ITEM(item->data)->getId() << ",0"; } } if (firstItem) { @@ -2905,10 +2903,10 @@ void sp_selection_clone_original_path_lpe(SPDesktop *desktop) Inkscape::XML::Node *lpe_repr = xml_doc->createElement("inkscape:path-effect"); { lpe_repr->setAttribute("effect", "fill_between_many"); - lpe_repr->setAttribute("linkedpaths", os.str().c_str()); + lpe_repr->setAttribute("linkedpaths", os.str()); desktop->doc()->getDefs()->getRepr()->addChild(lpe_repr, NULL); // adds to <defs> and assigns the 'id' attribute } - const gchar * lpe_id = lpe_repr->attribute("id"); + std::string lpe_id_href = std::string("#") + lpe_repr->attribute("id"); Inkscape::GC::release(lpe_repr); // create the new path @@ -2920,13 +2918,15 @@ void sp_selection_clone_original_path_lpe(SPDesktop *desktop) SPObject *clone_obj = desktop->doc()->getObjectById(clone->attribute("id")); SPLPEItem *clone_lpeitem = dynamic_cast<SPLPEItem *>(clone_obj); if (clone_lpeitem) { - gchar *href = g_strdup_printf("#%s", lpe_id); - clone_lpeitem->addPathEffect(href, false); - g_free(href); + clone_lpeitem->addPathEffect(lpe_id_href, false); } } DocumentUndo::done(sp_desktop_document(desktop), SP_VERB_EDIT_CLONE_ORIGINAL_PATH_LPE, _("Fill between many")); + // select the new object: + selection->set(clone); + + Inkscape::GC::release(clone); } else { desktop->messageStack()->flash(Inkscape::WARNING_MESSAGE, _("Select path(s) to fill.")); } @@ -3172,9 +3172,9 @@ void sp_selection_symbol(SPDesktop *desktop, bool /*apply*/ ) the_group->getAttribute("inkscape:transform-center-y")); the_group->setAttribute("style", NULL); - std::string id = symbol_repr->attribute("id"); + Glib::ustring id = symbol_repr->attribute("id"); id += "_transform"; - the_group->setAttribute("id", id.c_str()); + the_group->setAttribute("id", id); } @@ -3192,10 +3192,7 @@ void sp_selection_symbol(SPDesktop *desktop, bool /*apply*/ ) // Create <use> pointing to new symbol (to replace the moved objects). Inkscape::XML::Node *clone = xml_doc->createElement("svg:use"); - const gchar *symbol_id = symbol_repr->attribute("id"); - gchar *href_str = g_strdup_printf("#%s", symbol_id); - clone->setAttribute("xlink:href", href_str, false); - g_free(href_str); + clone->setAttribute("xlink:href", Glib::ustring("#")+symbol_repr->attribute("id"), false); the_parent_repr->appendChild(clone); @@ -3286,7 +3283,7 @@ void sp_selection_unsymbol(SPDesktop *desktop) // Need to delete <symbol>; all <use> elements that referenced <symbol> should // auto-magically reference <g> (if <symbol> deleted after setting <g> 'id'). Glib::ustring id = symbol->getAttribute("id"); - group->setAttribute("id",id.c_str()); + group->setAttribute("id", id); symbol->deleteObject(true); // Change selection to new <g> element. @@ -3628,7 +3625,7 @@ void sp_selection_create_bitmap_copy(SPDesktop *desktop) directory = g_path_get_dirname( document->getURI() ); } if (directory == NULL) { - directory = homedir_path(NULL); + directory = INKSCAPE.homedir_path(NULL); } gchar *filepath = g_build_filename(directory, basename, NULL); g_free(directory); @@ -4084,9 +4081,7 @@ void sp_selection_set_mask(SPDesktop *desktop, bool apply_clip_path, bool apply_ Inkscape::GC::release(group); } - gchar *value_str = g_strdup_printf("url(#%s)", mask_id); - apply_mask_to->setAttribute(attributeName, value_str); - g_free(value_str); + apply_mask_to->setAttribute(attributeName, Glib::ustring("url(#") + mask_id + ')'); } diff --git a/src/selection.cpp b/src/selection.cpp index 17b7253f2..81139d044 100644 --- a/src/selection.cpp +++ b/src/selection.cpp @@ -20,7 +20,7 @@ # include <config.h> #endif #include "macros.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "document.h" #include "layer-model.h" #include "selection.h" @@ -89,7 +89,7 @@ Selection::_emit_modified(Selection *selection) } void Selection::_emitModified(guint flags) { - inkscape_selection_modified(this, flags); + INKSCAPE.selection_modified(this, flags); _modified_signal.emit(this, flags); } @@ -104,7 +104,7 @@ void Selection::_emitChanged(bool persist_selection_context/* = false */) { _releaseContext(_selection_context); } - inkscape_selection_changed(this); + INKSCAPE.selection_changed(this); _changed_signal.emit(this); } diff --git a/src/seltrans.cpp b/src/seltrans.cpp index 96c7fb49b..a9ae9e465 100644 --- a/src/seltrans.cpp +++ b/src/seltrans.cpp @@ -1306,8 +1306,8 @@ gboolean Inkscape::SelTrans::centerRequest(Geom::Point &pt, guint state) // status text Inkscape::Util::Quantity x_q = Inkscape::Util::Quantity(pt[Geom::X], "px"); Inkscape::Util::Quantity y_q = Inkscape::Util::Quantity(pt[Geom::Y], "px"); - GString *xs = g_string_new(x_q.string(_desktop->namedview->doc_units).c_str()); - GString *ys = g_string_new(y_q.string(_desktop->namedview->doc_units).c_str()); + GString *xs = g_string_new(x_q.string(_desktop->namedview->display_units).c_str()); + GString *ys = g_string_new(y_q.string(_desktop->namedview->display_units).c_str()); _message_context.setF(Inkscape::NORMAL_MESSAGE, _("Move <b>center</b> to %s, %s"), xs->str, ys->str); g_string_free(xs, FALSE); g_string_free(ys, FALSE); @@ -1460,8 +1460,8 @@ void Inkscape::SelTrans::moveTo(Geom::Point const &xy, guint state) // status text Inkscape::Util::Quantity x_q = Inkscape::Util::Quantity(dxy[Geom::X], "px"); Inkscape::Util::Quantity y_q = Inkscape::Util::Quantity(dxy[Geom::Y], "px"); - GString *xs = g_string_new(x_q.string(_desktop->namedview->doc_units).c_str()); - GString *ys = g_string_new(y_q.string(_desktop->namedview->doc_units).c_str()); + GString *xs = g_string_new(x_q.string(_desktop->namedview->display_units).c_str()); + GString *ys = g_string_new(y_q.string(_desktop->namedview->display_units).c_str()); _message_context.setF(Inkscape::NORMAL_MESSAGE, _("<b>Move</b> by %s, %s; with <b>Ctrl</b> to restrict to horizontal/vertical; with <b>Shift</b> to disable snapping"), xs->str, ys->str); g_string_free(xs, TRUE); g_string_free(ys, TRUE); diff --git a/src/shortcuts.cpp b/src/shortcuts.cpp index 1e43c98c6..e72c16de0 100644 --- a/src/shortcuts.cpp +++ b/src/shortcuts.cpp @@ -211,7 +211,7 @@ Inkscape::XML::Document *sp_shortcut_create_template_file(char const *filename) void sp_shortcut_get_file_names(std::vector<Glib::ustring> *names, std::vector<Glib::ustring> *paths) { std::list<gchar *> sources; - sources.push_back( profile_path("keys") ); + sources.push_back( Inkscape::Application::profile_path("keys") ); sources.push_back( g_strdup(INKSCAPE_KEYSDIR) ); // loop through possible keyboard shortcut file locations. @@ -229,7 +229,7 @@ void sp_shortcut_get_file_names(std::vector<Glib::ustring> *names, std::vector<G gchar *filename = 0; while ((filename = (gchar *) g_dir_read_name(directory)) != NULL) { gchar* lower = g_ascii_strdown(filename, -1); - if (!strcmp(dirname, profile_path("keys")) && + if (!strcmp(dirname, Inkscape::Application::profile_path("keys")) && !strcmp(lower, "default.xml")) { // Dont add the users custom keys file continue; diff --git a/src/sp-ellipse.cpp b/src/sp-ellipse.cpp index b5c6e4af8..a74d4687d 100644 --- a/src/sp-ellipse.cpp +++ b/src/sp-ellipse.cpp @@ -604,7 +604,7 @@ void SPGenericEllipse::update_patheffect(bool write) if (write) { Inkscape::XML::Node *repr = this->getRepr(); - if (this->_curve != NULL) { + if (this->_curve != NULL && type == SP_GENERIC_ELLIPSE_ARC) { gchar *str = sp_svg_write_path(this->_curve->get_pathvector()); repr->setAttribute("d", str); g_free(str); @@ -642,8 +642,8 @@ bool SPGenericEllipse::set_elliptical_path_attribute(Inkscape::XML::Node *repr) // Make sure our pathvector is up to date. this->set_shape(); - if (this->getCurve() != NULL) { - gchar* d = sp_svg_write_path(this->getCurve()->get_pathvector()); + if (_curve != NULL) { + gchar* d = sp_svg_write_path(_curve->get_pathvector()); repr->setAttribute("d", d); diff --git a/src/sp-guide.cpp b/src/sp-guide.cpp index 581c8a440..d7d15bac7 100644 --- a/src/sp-guide.cpp +++ b/src/sp-guide.cpp @@ -37,6 +37,7 @@ #include <remove-last.h> #include "inkscape.h" #include "desktop.h" +#include "sp-root.h" #include "sp-namedview.h" #include <2geom/angle.h> #include "document.h" @@ -152,6 +153,12 @@ void SPGuide::set(unsigned int key, const gchar *value) { success += sp_svg_number_read_d(strarray[1], &newy); g_strfreev (strarray); if (success == 2) { + // If root viewBox set, interpret guides in terms of viewBox (90/96) + SPRoot *root = document->getRoot(); + if( root->viewBox_set ) { + newx = newx * root->width.computed / root->viewBox.width(); + newy = newy * root->height.computed / root->viewBox.height(); + } this->point_on_line = Geom::Point(newx, newy); } else if (success == 1) { // before 0.46 style guideline definition. @@ -185,7 +192,17 @@ SPGuide *SPGuide::createSPGuide(SPDocument *doc, Geom::Point const &pt1, Geom::P Geom::Point n = Geom::rot90(pt2 - pt1); - sp_repr_set_point(repr, "position", pt1); + // If root viewBox set, interpret guides in terms of viewBox (90/96) + double newx = pt1.x(); + double newy = pt1.y(); + + SPRoot *root = doc->getRoot(); + if( root->viewBox_set ) { + newx = newx * root->viewBox.width() / root->width.computed; + newy = newy * root->viewBox.height() / root->height.computed; + } + + sp_repr_set_point(repr, "position", Geom::Point( newx, newy )); sp_repr_set_point(repr, "orientation", n); SPNamedView *namedview = sp_document_namedview(doc, NULL); @@ -318,8 +335,18 @@ void SPGuide::moveto(Geom::Point const point_on_line, bool const commit) /* Calling sp_repr_set_point must precede calling sp_item_notify_moveto in the commit case, so that the guide's new position is available for sp_item_rm_unsatisfied_cns. */ if (commit) { + // If root viewBox set, interpret guides in terms of viewBox (90/96) + double newx = point_on_line.x(); + double newy = point_on_line.y(); + + SPRoot *root = document->getRoot(); + if( root->viewBox_set ) { + newx = newx * root->viewBox.width() / root->width.computed; + newy = newy * root->viewBox.height() / root->height.computed; + } + //XML Tree being used here directly while it shouldn't be. - sp_repr_set_point(getRepr(), "position", point_on_line); + sp_repr_set_point(getRepr(), "position", Geom::Point(newx, newy) ); } /* DISABLED CODE BECAUSE SPGuideAttachment IS NOT USE AT THE MOMENT (johan) @@ -410,8 +437,8 @@ char* SPGuide::description(bool const verbose) const Inkscape::Util::Quantity x_q = Inkscape::Util::Quantity(this->point_on_line[X], "px"); Inkscape::Util::Quantity y_q = Inkscape::Util::Quantity(this->point_on_line[Y], "px"); - GString *position_string_x = g_string_new(x_q.string(namedview->doc_units).c_str()); - GString *position_string_y = g_string_new(y_q.string(namedview->doc_units).c_str()); + GString *position_string_x = g_string_new(x_q.string(namedview->display_units).c_str()); + GString *position_string_y = g_string_new(y_q.string(namedview->display_units).c_str()); gchar *shortcuts = g_strdup_printf("; %s", _("<b>Shift+drag</b> to rotate, <b>Ctrl+drag</b> to move origin, <b>Del</b> to delete")); diff --git a/src/sp-item-group.cpp b/src/sp-item-group.cpp index 613ace5c1..992bca631 100644 --- a/src/sp-item-group.cpp +++ b/src/sp-item-group.cpp @@ -662,8 +662,13 @@ void SPGroup::scaleChildItemsRec(Geom::Scale const &sc, Geom::Point const &p, bo { if ( hasChildren() ) { for (SPObject *o = firstChild() ; o ; o = o->getNext() ) { - SPItem *item = dynamic_cast<SPItem *>(o); - if ( item ) { + if ( SPDefs *defs = dynamic_cast<SPDefs *>(o) ) { // select symbols from defs, ignore clips, masks, patterns + for (SPObject *defschild = defs->firstChild() ; defschild ; defschild = defschild->getNext() ) { + SPGroup *defsgroup = dynamic_cast<SPGroup *>(defschild); + if (defsgroup) + defsgroup->scaleChildItemsRec(sc, p, false); + } + } else if ( SPItem *item = dynamic_cast<SPItem *>(o) ) { SPGroup *group = dynamic_cast<SPGroup *>(item); if (group && !dynamic_cast<SPBox3D *>(item)) { /* Using recursion breaks clipping because transforms are applied diff --git a/src/sp-item.cpp b/src/sp-item.cpp index 73347fc4e..b6dee67e4 100644 --- a/src/sp-item.cpp +++ b/src/sp-item.cpp @@ -1006,7 +1006,7 @@ void SPItem::getSnappoints(std::vector<Inkscape::SnapCandidatePoint> &p, Inkscap clips_and_masks.push_back(clip_ref->getObject()); clips_and_masks.push_back(mask_ref->getObject()); - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; for (std::list<SPObject const *>::const_iterator o = clips_and_masks.begin(); o != clips_and_masks.end(); ++o) { if (*o) { // obj is a group object, the children are the actual clippers @@ -1607,7 +1607,7 @@ Geom::Affine SPItem::i2doc_affine() const Geom::Affine SPItem::i2dt_affine() const { Geom::Affine ret; - SPDesktop const *desktop = inkscape_active_desktop(); + SPDesktop const *desktop = SP_ACTIVE_DESKTOP; if ( desktop ) { ret = i2doc_affine() * desktop->doc2dt(); } else { @@ -1625,7 +1625,7 @@ void SPItem::set_i2d_affine(Geom::Affine const &i2dt) if (parent) { dt2p = static_cast<SPItem *>(parent)->i2dt_affine().inverse(); } else { - SPDesktop *dt = inkscape_active_desktop(); + SPDesktop *dt = SP_ACTIVE_DESKTOP; dt2p = dt->dt2doc(); } diff --git a/src/sp-lpe-item.cpp b/src/sp-lpe-item.cpp index 019d15162..f059ab531 100644 --- a/src/sp-lpe-item.cpp +++ b/src/sp-lpe-item.cpp @@ -58,8 +58,8 @@ static void sp_lpe_item_create_original_path_recursive(SPLPEItem *lpeitem); static void sp_lpe_item_cleanup_original_path_recursive(SPLPEItem *lpeitem); typedef std::list<std::string> HRefList; -static std::string patheffectlist_write_svg(PathEffectList const & list); -static std::string hreflist_write_svg(HRefList const & list); +static std::string patheffectlist_svg_string(PathEffectList const & list); +static std::string hreflist_svg_string(HRefList const & list); SPLPEItem::SPLPEItem() : SPItem() @@ -195,8 +195,7 @@ void SPLPEItem::modified(unsigned int flags) { Inkscape::XML::Node* SPLPEItem::write(Inkscape::XML::Document *xml_doc, Inkscape::XML::Node *repr, guint flags) { if (flags & SP_OBJECT_WRITE_EXT) { if ( hasPathEffect() ) { - std::string href = patheffectlist_write_svg(*this->path_effect_list); - repr->setAttribute("inkscape:path-effect", href.c_str()); + repr->setAttribute("inkscape:path-effect", patheffectlist_svg_string(*this->path_effect_list)); } else { repr->setAttribute("inkscape:path-effect", NULL); } @@ -418,9 +417,9 @@ sp_lpe_item_cleanup_original_path_recursive(SPLPEItem *lpeitem) } } -void SPLPEItem::addPathEffect(gchar *value, bool reset) +void SPLPEItem::addPathEffect(std::string value, bool reset) { - if (value) { + if (!value.empty()) { // Apply the path effects here because in the casse of a group, lpe->resetDefaults // needs that all the subitems have their effects applied sp_lpe_item_update_patheffect(this, false, true); @@ -434,10 +433,9 @@ void SPLPEItem::addPathEffect(gchar *value, bool reset) { hreflist.push_back( std::string((*it)->lpeobject_href) ); } - hreflist.push_back( std::string(value) ); - std::string hrefs = hreflist_write_svg(hreflist); + hreflist.push_back(value); // C++11: should be emplace_back std::move'd (also the reason why passed by value to addPathEffect) - this->getRepr()->setAttribute("inkscape:path-effect", hrefs.c_str()); + this->getRepr()->setAttribute("inkscape:path-effect", hreflist_svg_string(hreflist)); // Make sure that ellipse is stored as <svg:path> if( SP_IS_GENERICELLIPSE(this)) { @@ -501,13 +499,7 @@ void SPLPEItem::removeCurrentPathEffect(bool keep_paths) } PathEffectList new_list = *this->path_effect_list; new_list.remove(lperef); //current lpe ref is always our 'own' pointer from the path_effect_list - std::string r = patheffectlist_write_svg(new_list); - - if (!r.empty()) { - this->getRepr()->setAttribute("inkscape:path-effect", r.c_str()); - } else { - this->getRepr()->setAttribute("inkscape:path-effect", NULL); - } + this->getRepr()->setAttribute("inkscape:path-effect", patheffectlist_svg_string(new_list)); if (!keep_paths) { // Make sure that ellipse is stored as <svg:circle> or <svg:ellipse> if possible. @@ -551,8 +543,8 @@ void SPLPEItem::downCurrentPathEffect() std::iter_swap(cur_it, down_it); } } - std::string r = patheffectlist_write_svg(new_list); - this->getRepr()->setAttribute("inkscape:path-effect", r.c_str()); + + this->getRepr()->setAttribute("inkscape:path-effect", patheffectlist_svg_string(new_list)); sp_lpe_item_cleanup_original_path_recursive(this); } @@ -570,9 +562,8 @@ void SPLPEItem::upCurrentPathEffect() --up_it; std::iter_swap(cur_it, up_it); } - std::string r = patheffectlist_write_svg(new_list); - this->getRepr()->setAttribute("inkscape:path-effect", r.c_str()); + this->getRepr()->setAttribute("inkscape:path-effect", patheffectlist_svg_string(new_list)); sp_lpe_item_cleanup_original_path_recursive(this); } @@ -862,16 +853,16 @@ void SPLPEItem::remove_child(Inkscape::XML::Node * child) { SPItem::remove_child(child); } -static std::string patheffectlist_write_svg(PathEffectList const & list) +static std::string patheffectlist_svg_string(PathEffectList const & list) { HRefList hreflist; for (PathEffectList::const_iterator it = list.begin(); it != list.end(); ++it) { - hreflist.push_back( std::string((*it)->lpeobject_href) ); + hreflist.push_back( std::string((*it)->lpeobject_href) ); // C++11: use emplace_back } - return hreflist_write_svg(hreflist); + return hreflist_svg_string(hreflist); } /** @@ -881,7 +872,7 @@ static std::string patheffectlist_write_svg(PathEffectList const & list) * - populate the templist with the effects from the old list that you want to have and their order * - call this function with temp list as param */ -static std::string hreflist_write_svg(HRefList const & list) +static std::string hreflist_svg_string(HRefList const & list) { std::string r; bool semicolon_first = false; @@ -968,8 +959,7 @@ void SPLPEItem::replacePathEffects( std::vector<LivePathEffectObject const *> co } } - std::string r = hreflist_write_svg(hreflist); - this->getRepr()->setAttribute("inkscape:path-effect", r.c_str()); + this->getRepr()->setAttribute("inkscape:path-effect", hreflist_svg_string(hreflist)); } /** diff --git a/src/sp-lpe-item.h b/src/sp-lpe-item.h index 9c052b7b1..902271430 100644 --- a/src/sp-lpe-item.h +++ b/src/sp-lpe-item.h @@ -15,6 +15,7 @@ */ #include <list> +#include <string> #include "sp-item.h" #define SP_LPE_ITEM(obj) (dynamic_cast<SPLPEItem*>((SPObject*)obj)) @@ -88,7 +89,7 @@ public: bool setCurrentPathEffect(Inkscape::LivePathEffect::LPEObjectReference* lperef); void removeCurrentPathEffect(bool keep_paths); void removeAllPathEffects(bool keep_paths); - void addPathEffect(char *value, bool reset); + void addPathEffect(std::string value, bool reset); void addPathEffect(LivePathEffectObject * new_lpeobj); void apply_to_mask(SPItem * item); void apply_to_clippath(SPItem * item); diff --git a/src/sp-marker.cpp b/src/sp-marker.cpp index e955594ab..1c13a54e6 100644 --- a/src/sp-marker.cpp +++ b/src/sp-marker.cpp @@ -168,9 +168,12 @@ void SPMarker::set(unsigned int key, const gchar* value) { } else if (!strcmp (value, "auto-start-reverse")) { this->orient_mode = MARKER_ORIENT_AUTO_START_REVERSE; this->orient_set = TRUE; - } else if (sp_svg_number_read_f (value, &this->orient)) { - this->orient_mode = MARKER_ORIENT_ANGLE; - this->orient_set = TRUE; + } else { + orient.readOrUnset(value); + if (orient._set) { + this->orient_mode = MARKER_ORIENT_ANGLE; + this->orient_set = orient._set; + } } } @@ -273,7 +276,7 @@ Inkscape::XML::Node* SPMarker::write(Inkscape::XML::Document *xml_doc, Inkscape: } else if (this->orient_mode == MARKER_ORIENT_AUTO_START_REVERSE) { repr->setAttribute("orient", "auto-start-reverse"); } else { - sp_repr_set_css_double(repr, "orient", this->orient); + sp_repr_set_css_double(repr, "orient", this->orient.computed); } } else { repr->setAttribute("orient", NULL); @@ -394,7 +397,7 @@ sp_marker_show_instance ( SPMarker *marker, Inkscape::DrawingItem *parent, m = base; } else { /* fixme: Orient units (Lauris) */ - m = Geom::Rotate::from_degrees(marker->orient); + m = Geom::Rotate::from_degrees(marker->orient.computed); m *= Geom::Translate(base.translation()); } if (marker->markerUnits == SP_MARKER_UNITS_STROKEWIDTH) { diff --git a/src/sp-marker.h b/src/sp-marker.h index b58523251..548a6f6f0 100644 --- a/src/sp-marker.h +++ b/src/sp-marker.h @@ -28,6 +28,7 @@ struct SPMarkerView; #include "enums.h" #include "svg/svg-length.h" +#include "svg/svg-angle.h" #include "sp-item-group.h" #include "uri-references.h" #include "viewbox.h" @@ -58,7 +59,7 @@ public: /* orient */ unsigned int orient_set : 1; markerOrient orient_mode : 2; - float orient; + SVGAngle orient; /* Private views */ SPMarkerView *views; diff --git a/src/sp-namedview.cpp b/src/sp-namedview.cpp index 8b28347f1..1817e74e0 100644 --- a/src/sp-namedview.cpp +++ b/src/sp-namedview.cpp @@ -72,11 +72,13 @@ SPNamedView::SPNamedView() : SPObjectGroup(), snap_manager(this) { this->guidehicolor = 0; this->views = NULL; this->borderlayer = 0; - this->units = NULL; + this->page_size_units = NULL; this->window_x = 0; this->cy = 0; this->window_y = 0; - this->doc_units = NULL; + this->svg_units = unit_table.getUnit("px"); // legacy behavior: if no viewbox present, default to 'px' units + this->display_units = NULL; + this->page_size_units = NULL; this->pagecolor = 0; this->cx = 0; this->pageshadow = 0; @@ -262,6 +264,14 @@ void SPNamedView::build(SPDocument *document, Inkscape::XML::Node *repr) { // backwards compatibility with grid settings (pre 0.46) sp_namedview_generate_old_grid(this, document, repr); + + // If viewbox defined: try to calculate the SVG unit from document width and viewbox + if (document->getRoot()->viewBox_set) { + Inkscape::Util::Quantity svgwidth = document->getWidth(); + Geom::Rect viewbox = document->getRoot()->viewBox; + double factor = svgwidth.value(unit_table.primary(Inkscape::Util::UNIT_TYPE_LINEAR)) / viewbox.width(); + svg_units = unit_table.findUnit(factor, Inkscape::Util::UNIT_TYPE_LINEAR); + } } void SPNamedView::release() { @@ -540,22 +550,13 @@ void SPNamedView::set(unsigned int key, const gchar* value) { this->requestModified(SP_OBJECT_MODIFIED_FLAG); break; case SP_ATTR_INKSCAPE_DOCUMENT_UNITS: { - /* The default unit if the document doesn't override this: e.g. for files saved as + /* The default display unit if the document doesn't override this: e.g. for files saved as * `plain SVG', or non-inkscape files, or files created by an inkscape 0.40 & * earlier. * - * Here we choose `px': useful for screen-destined SVGs, and fewer bug reports - * about "not the same numbers as what's in the SVG file" (at least for documents - * without a viewBox attribute on the root <svg> element). Similarly, it's also - * the most reliable unit (i.e. least likely to be wrong in different viewing - * conditions) for viewBox-less SVG files given that it's the unit that inkscape - * uses for all coordinates. + * Note that these units are not the same as the units used for the values in SVG! * - * For documents that do have a viewBox attribute on the root <svg> element, it - * might be better if we used either viewBox coordinates or if we used the unit of - * say the width attribute of the root <svg> element. However, these pose problems - * in that they aren't in general absolute units as currently required by - * doc_units. + * We default to `px'. */ static Inkscape::Util::Unit const *px = unit_table.getUnit("px"); Inkscape::Util::Unit const *new_unit = px; @@ -576,11 +577,12 @@ void SPNamedView::set(unsigned int key, const gchar* value) { /* fixme: Don't use g_log (see above). */ } } - this->doc_units = new_unit; + this->display_units = new_unit; this->requestModified(SP_OBJECT_MODIFIED_FLAG); break; } case SP_ATTR_UNITS: { + // Only used in "Custom size" section of Document Properties dialog Inkscape::Util::Unit const *new_unit = NULL; if (value) { @@ -599,7 +601,7 @@ void SPNamedView::set(unsigned int key, const gchar* value) { /* fixme: Don't use g_log (see above). */ } } - this->units = new_unit; + this->page_size_units = new_unit; this->requestModified(SP_OBJECT_MODIFIED_FLAG); break; } @@ -1128,11 +1130,17 @@ double SPNamedView::getMarginLength(gchar const * const key, /** * Returns namedview's default unit. - * If no default unit is set, "pt" is returned + * If no default unit is set, "px" is returned */ -Inkscape::Util::Unit const * SPNamedView::getDefaultUnit() const +Inkscape::Util::Unit const * SPNamedView::getDisplayUnit() const +{ + return display_units ? display_units : unit_table.getUnit("px"); +} + +Inkscape::Util::Unit const & SPNamedView::getSVGUnit() const { - return doc_units ? doc_units : unit_table.getUnit("pt"); + assert(svg_units); + return *svg_units; } /** diff --git a/src/sp-namedview.h b/src/sp-namedview.h index 37310dc76..f1ecc12d3 100644 --- a/src/sp-namedview.h +++ b/src/sp-namedview.h @@ -61,8 +61,9 @@ public: GSList * grids; bool grids_visible; - Inkscape::Util::Unit const *doc_units; - Inkscape::Util::Unit const *units; + Inkscape::Util::Unit const *svg_units; // Units used for the values in SVG + Inkscape::Util::Unit const *display_units; // Units used for the UI (*not* the same as units of SVG coordinates) + Inkscape::Util::Unit const *page_size_units; // Only used in "Custom size" part of Document Properties dialog GQuark default_layer_id; @@ -85,7 +86,8 @@ public: char const *getName() const; unsigned int getViewCount(); GSList const *getViewList() const; - Inkscape::Util::Unit const * getDefaultUnit() const; + Inkscape::Util::Unit const * getDisplayUnit() const; + Inkscape::Util::Unit const & getSVGUnit() const; void translateGuides(Geom::Translate const &translation); void translateGrids(Geom::Translate const &translation); diff --git a/src/sp-object.cpp b/src/sp-object.cpp index fcff43aa5..4e45eb824 100644 --- a/src/sp-object.cpp +++ b/src/sp-object.cpp @@ -406,9 +406,9 @@ void SPObject::requestOrphanCollection() { Inkscape::Preferences *prefs = Inkscape::Preferences::get(); // do not remove style or script elements (Bug #276244) - if (SP_IS_STYLE_ELEM(this)) { + if (dynamic_cast<SPStyleElem *>(this)) { // leave it - } else if (SP_IS_SCRIPT(this)) { + } else if (dynamic_cast<SPScript *>(this)) { // leave it } else if ((! prefs->getBool("/options/cleanupswatches/value", false)) && SP_IS_PAINT_SERVER(this) && static_cast<SPPaintServer*>(this)->isSwatch() ) { @@ -1254,6 +1254,16 @@ void SPObject::setAttribute(gchar const *key, gchar const *value, SPException *e //XML Tree being used here. getRepr()->setAttribute(key, value, false); } +void SPObject::setAttribute(char const *key, Glib::ustring const &value, SPException *ex) +{ + setAttribute(key, value.empty() ? NULL : value.c_str(), ex); +} +void SPObject::setAttribute(Glib::ustring const &key, Glib::ustring const &value, SPException *ex) +{ + setAttribute( key.empty() ? NULL : key.c_str(), + value.empty() ? NULL : value.c_str(), ex); +} + void SPObject::removeAttribute(gchar const *key, SPException *ex) { diff --git a/src/sp-object.h b/src/sp-object.h index 575198f36..d08add0bf 100644 --- a/src/sp-object.h +++ b/src/sp-object.h @@ -67,6 +67,9 @@ struct Document; } } +namespace Glib { + class ustring; +} typedef enum { SP_NO_EXCEPTION, @@ -703,7 +706,9 @@ public: */ void setKeyValue(unsigned int key, char const *value); - void setAttribute(char const *key, char const *value, SPException *ex=NULL); + void setAttribute( char const *key, char const *value, SPException *ex=NULL); + void setAttribute( char const *key, Glib::ustring const &value, SPException *ex=NULL); + void setAttribute(Glib::ustring const &key, Glib::ustring const &value, SPException *ex=NULL); /** * Read value of key attribute from XML node into object. diff --git a/src/sp-script.h b/src/sp-script.h index b71f86720..cdacb8493 100644 --- a/src/sp-script.h +++ b/src/sp-script.h @@ -6,6 +6,7 @@ * * Author: * Felipe C. da S. Sanches <juca@members.fsf.org> + * Jon A. Cruz <jon@joncruz.org> * * Copyright (C) 2008 Author * @@ -15,9 +16,6 @@ #include "sp-object.h" #include "document.h" -#define SP_SCRIPT(obj) (dynamic_cast<SPScript*>((SPObject*)obj)) -#define SP_IS_SCRIPT(obj) (dynamic_cast<const SPScript*>((SPObject*)obj) != NULL) - /* SPScript */ class SPScript : public SPObject { public: diff --git a/src/sp-shape.cpp b/src/sp-shape.cpp index 8b7e735e0..6d240fbf5 100644 --- a/src/sp-shape.cpp +++ b/src/sp-shape.cpp @@ -434,7 +434,7 @@ Geom::OptRect SPShape::bbox(Geom::Affine const &transform, SPItem::BBoxType bbox tr = Geom::Rotate::from_degrees( 180.0 ) * tr; } else if (_marker[i]->orient_mode == MARKER_ORIENT_ANGLE) { Geom::Point transl = tr.translation(); - tr = Geom::Rotate::from_degrees(_marker[i]->orient) * Geom::Translate(transl); + tr = Geom::Rotate::from_degrees(_marker[i]->orient.computed) * Geom::Translate(transl); } if (_marker[i]->markerUnits == SP_MARKER_UNITS_STROKEWIDTH) { @@ -472,7 +472,7 @@ Geom::OptRect SPShape::bbox(Geom::Affine const &transform, SPItem::BBoxType bbox if (marker->orient_mode == MARKER_ORIENT_ANGLE) { Geom::Point transl = tr.translation(); - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(transl); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(transl); } if (marker->markerUnits == SP_MARKER_UNITS_STROKEWIDTH) { @@ -502,7 +502,7 @@ Geom::OptRect SPShape::bbox(Geom::Affine const &transform, SPItem::BBoxType bbox if (marker->orient_mode == MARKER_ORIENT_ANGLE) { Geom::Point transl = tr.translation(); - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(transl); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(transl); } if (marker->markerUnits == SP_MARKER_UNITS_STROKEWIDTH) { @@ -525,7 +525,7 @@ Geom::OptRect SPShape::bbox(Geom::Affine const &transform, SPItem::BBoxType bbox if (marker->orient_mode == MARKER_ORIENT_ANGLE) { Geom::Point transl = tr.translation(); - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(transl); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(transl); } if (marker->markerUnits == SP_MARKER_UNITS_STROKEWIDTH) { @@ -560,7 +560,7 @@ Geom::OptRect SPShape::bbox(Geom::Affine const &transform, SPItem::BBoxType bbox if (marker->orient_mode == MARKER_ORIENT_ANGLE) { Geom::Point transl = tr.translation(); - tr = Geom::Rotate::from_degrees(marker->orient) * Geom::Translate(transl); + tr = Geom::Rotate::from_degrees(marker->orient.computed) * Geom::Translate(transl); } if (marker->markerUnits == SP_MARKER_UNITS_STROKEWIDTH) { diff --git a/src/sp-style-elem.cpp b/src/sp-style-elem.cpp index 84f110134..da17b08d9 100644 --- a/src/sp-style-elem.cpp +++ b/src/sp-style-elem.cpp @@ -26,23 +26,18 @@ SPStyleElem::~SPStyleElem() { } void SPStyleElem::set(unsigned int key, const gchar* value) { - SPStyleElem* object = this; - - g_return_if_fail(object); - SPStyleElem &style_elem = *SP_STYLE_ELEM(object); - switch (key) { case SP_ATTR_TYPE: { if (!value) { /* TODO: `type' attribute is required. Give error message as per http://www.w3.org/TR/SVG11/implnote.html#ErrorProcessing. */ - style_elem.is_css = false; + is_css = false; } else { /* fixme: determine what whitespace is allowed. Will probably need to ask on SVG - * list; though the relevant RFC may give info on its lexer. */ - style_elem.is_css = ( g_ascii_strncasecmp(value, "text/css", 8) == 0 - && ( value[8] == '\0' || - value[8] == ';' ) ); + list; though the relevant RFC may give info on its lexer. */ + is_css = ( g_ascii_strncasecmp(value, "text/css", 8) == 0 + && ( value[8] == '\0' || + value[8] == ';' ) ); } break; } @@ -67,14 +62,18 @@ static void child_add_rm_cb(Inkscape::XML::Node *, Inkscape::XML::Node *, Inkscape::XML::Node *, void *const data) { - static_cast<SPObject *>(data)->read_content(); + SPObject *obj = reinterpret_cast<SPObject *>(data); + g_assert(data != NULL); + obj->read_content(); } static void content_changed_cb(Inkscape::XML::Node *, gchar const *, gchar const *, void *const data) { - static_cast<SPObject *>(data)->read_content(); + SPObject *obj = reinterpret_cast<SPObject *>(data); + g_assert(data != NULL); + obj->read_content(); } static void @@ -82,24 +81,22 @@ child_order_changed_cb(Inkscape::XML::Node *, Inkscape::XML::Node *, Inkscape::XML::Node *, Inkscape::XML::Node *, void *const data) { - static_cast<SPObject *>(data)->read_content(); + SPObject *obj = reinterpret_cast<SPObject *>(data); + g_assert(data != NULL); + obj->read_content(); } Inkscape::XML::Node* SPStyleElem::write(Inkscape::XML::Document* xml_doc, Inkscape::XML::Node* repr, guint flags) { - SPStyleElem* object = this; - if ((flags & SP_OBJECT_WRITE_BUILD) && !repr) { repr = xml_doc->createElement("svg:style"); } - g_return_val_if_fail(object, repr); - SPStyleElem &style_elem = *SP_STYLE_ELEM(object); if (flags & SP_OBJECT_WRITE_BUILD) { g_warning("nyi: Forming <style> content for SP_OBJECT_WRITE_BUILD."); /* fixme: Consider having the CRStyleSheet be a member of SPStyleElem, and then pretty-print to a string s, then repr->addChild(xml_doc->createTextNode(s), NULL). */ } - if (style_elem.is_css) { + if (is_css) { repr->setAttribute("type", "text/css"); } /* todo: media */ @@ -263,10 +260,6 @@ property_cb(CRDocHandler *const a_handler, } void SPStyleElem::read_content() { - SPStyleElem* object = this; - - SPStyleElem &style_elem = *SP_STYLE_ELEM(object); - /* fixme: If there's more than one <style> element in a document, then the document stylesheet * will be set to a random one of them, even switching between them. * @@ -283,7 +276,7 @@ void SPStyleElem::read_content() { */ //XML Tree being used directly here while it shouldn't be. - GString *const text = concat_children(*style_elem.getRepr()); + GString *const text = concat_children(*getRepr()); CRParser *parser = cr_parser_new_from_buf(reinterpret_cast<guchar *>(text->str), text->len, CR_UTF_8, FALSE); @@ -312,7 +305,7 @@ void SPStyleElem::read_content() { CRStatus const parse_status = cr_parser_parse(parser); g_assert(sac_handler->app_data == &parse_tmp); if (parse_status == CR_OK) { - cr_cascade_set_sheet(style_elem.document->style_cascade, stylesheet, ORIGIN_AUTHOR); + cr_cascade_set_sheet(document->style_cascade, stylesheet, ORIGIN_AUTHOR); } else { if (parse_status != CR_PARSING_ERROR) { g_printerr("parsing error code=%u\n", unsigned(parse_status)); @@ -323,7 +316,7 @@ void SPStyleElem::read_content() { } } cr_parser_destroy(parser); - //object->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); + //requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); // Style references via class= do not, and actually cannot, use autoupdating URIReferences. // Therefore, if an object refers to a stylesheet which has not yet loaded when the object is being loaded @@ -331,7 +324,6 @@ void SPStyleElem::read_content() { // Below is a partial hack that fixes this for a single case: when the <style> is a child of the object // that uses a style from it. It just forces the parent of <style> to reread its style as soon as the stylesheet // is fully loaded. Naturally, this won't work if the user of the stylesheet is its grandparent or precedent. - SPObject *parent = object->parent; if ( parent ) { sp_style_read_from_object(parent->style, parent); } @@ -351,12 +343,10 @@ rec_add_listener(Inkscape::XML::Node &repr, } void SPStyleElem::build(SPDocument *document, Inkscape::XML::Node *repr) { - SPStyleElem* object = this; - - object->read_content(); + read_content(); - object->readAttr( "type" ); - object->readAttr( "media" ); + readAttr( "type" ); + readAttr( "media" ); static Inkscape::XML::NodeEventVector const nodeEventVector = { child_add_rm_cb, // child_added @@ -365,7 +355,7 @@ void SPStyleElem::build(SPDocument *document, Inkscape::XML::Node *repr) { content_changed_cb, // content_changed child_order_changed_cb, // order_changed }; - rec_add_listener(*repr, &nodeEventVector, object); + rec_add_listener(*repr, &nodeEventVector, this); SPObject::build(document, repr); } diff --git a/src/sp-style-elem.h b/src/sp-style-elem.h index 766770216..a3f4bdc70 100644 --- a/src/sp-style-elem.h +++ b/src/sp-style-elem.h @@ -4,9 +4,6 @@ #include "sp-object.h" #include "media.h" -#define SP_STYLE_ELEM(obj) (dynamic_cast<SPStyleElem*>((SPObject*)obj)) -#define SP_IS_STYLE_ELEM(obj) (dynamic_cast<const SPStyleElem*>((SPObject*)obj) != NULL) - class SPStyleElem : public SPObject { public: SPStyleElem(); diff --git a/src/sp-text.cpp b/src/sp-text.cpp index 93d81e47b..8922d3c73 100644 --- a/src/sp-text.cpp +++ b/src/sp-text.cpp @@ -362,7 +362,7 @@ gchar* SPText::description() const { char *n = xml_quote_strdup( style->font_family.value ); Inkscape::Util::Quantity q = Inkscape::Util::Quantity(style->font_size.computed, "px"); - GString *xs = g_string_new(q.string(sp_desktop_namedview(SP_ACTIVE_DESKTOP)->doc_units).c_str()); + GString *xs = g_string_new(q.string(sp_desktop_namedview(SP_ACTIVE_DESKTOP)->display_units).c_str()); char const *trunc = ""; Inkscape::Text::Layout const *layout = te_get_layout((SPItem *) this); diff --git a/src/svg/stringstream-test.h b/src/svg/stringstream-test.h index ce32683f8..305cf6b8d 100644 --- a/src/svg/stringstream-test.h +++ b/src/svg/stringstream-test.h @@ -37,9 +37,9 @@ public: svg_test_float(-0.0625, "-0.0625"); svg_test_float(30.0, "30"); svg_test_float(12345678.0, "12345678"); - svg_test_float(3e9, "3e+09"); - svg_test_float(-3.5e9, "-3.5e+09"); - svg_test_float(32768e9, "3.2768e+13"); + svg_test_float(3e9, "3e+009"); + svg_test_float(-3.5e9, "-3.5e+009"); + svg_test_float(32768e9, "3.2768e+013"); svg_test_float(-10.5, "-10.5"); } diff --git a/src/svg/svg-color.cpp b/src/svg/svg-color.cpp index c9f22f8a4..693094048 100644 --- a/src/svg/svg-color.cpp +++ b/src/svg/svg-color.cpp @@ -32,8 +32,8 @@ #include "svg-color.h" #include "svg-icc-color.h" -#if defined(HAVE_LIBLCMS1) || defined(HAVE_LIBLCMS2) #include "color.h" +#if defined(HAVE_LIBLCMS1) || defined(HAVE_LIBLCMS2) #include "color-profile.h" #include "document.h" #include "inkscape.h" diff --git a/src/svg/svg-length-test.h b/src/svg/svg-length-test.h index fbdb7588d..796943e45 100644 --- a/src/svg/svg-length-test.h +++ b/src/svg/svg-length-test.h @@ -168,9 +168,9 @@ SvgLengthTest::test_t const SvgLengthTest::absolute_tests[12] = { {"1e2pt", SVGLength::PT , 100 , 400.0/3.0}, {"3pc", SVGLength::PC , 3 , 48}, {"-3.5pc", SVGLength::PC , -3.5 , -3.5*16.0}, - {"1.2345678mm", SVGLength::MM , 1.2345678, 1.2345678*96.0/25.4}, // TODO: More precise constants? (a 7 digit constant when the default precision is 8 digits?) - {"123.45678cm", SVGLength::CM , 123.45678 , 123.45678*96.0/2.54}, - {"73.162987in", SVGLength::INCH, 73.162987 , 73.162987*96}}; + {"1.2345678mm", SVGLength::MM , 1.2345678, 1.2345678f*96.0/25.4}, // TODO: More precise constants? (a 7 digit constant when the default precision is 8 digits?) + {"123.45678cm", SVGLength::CM , 123.45678 , 123.45678f*96.0/2.54}, // Note that svg_length_read is casting the result from g_ascii_strtod to float. + {"73.162987in", SVGLength::INCH, 73.162987 , 73.162987f*96.0/1.00}}; SvgLengthTest::test_t const SvgLengthTest::relative_tests[3] = { {"123em", SVGLength::EM, 123, 123. * 7.}, {"123ex", SVGLength::EX, 123, 123. * 13.}, diff --git a/src/svg/svg-length.cpp b/src/svg/svg-length.cpp index b9b475f4b..ea235b2e4 100644 --- a/src/svg/svg-length.cpp +++ b/src/svg/svg-length.cpp @@ -520,7 +520,8 @@ gchar const *sp_svg_length_get_css_units(SVGLength::Unit unit) case SVGLength::MM: return "mm"; case SVGLength::CM: return "cm"; case SVGLength::INCH: return "in"; - case SVGLength::FOOT: return ""; // Does not have a "foot" unit string in the SVG spec + case SVGLength::FOOT: return ""; // Not in SVG/CSS specification. + case SVGLength::MITRE: return ""; // Not in SVG/CSS specification. case SVGLength::EM: return "em"; case SVGLength::EX: return "ex"; case SVGLength::PERCENT: return "%"; @@ -539,6 +540,8 @@ std::string sp_svg_length_write_with_units(SVGLength const &length) os << 100*length.value << sp_svg_length_get_css_units(length.unit); } else if (length.unit == SVGLength::FOOT) { os << 12*length.value << sp_svg_length_get_css_units(SVGLength::INCH); + } else if (length.unit == SVGLength::MITRE) { + os << 100*length.value << sp_svg_length_get_css_units(SVGLength::CM); } else { os << length.value << sp_svg_length_get_css_units(length.unit); } diff --git a/src/svg/svg-length.h b/src/svg/svg-length.h index c34905d07..1e6b4c96c 100644 --- a/src/svg/svg-length.h +++ b/src/svg/svg-length.h @@ -28,6 +28,7 @@ public: CM, INCH, FOOT, + MITRE, EM, EX, PERCENT, diff --git a/src/test-helpers.h b/src/test-helpers.h index 001356e65..d30449ebb 100644 --- a/src/test-helpers.h +++ b/src/test-helpers.h @@ -5,7 +5,7 @@ #include <cxxtest/TestSuite.h> #include "document.h" -#include "inkscape-private.h" +#include "inkscape.h" // Dummy functions to keep linker happy @@ -28,10 +28,10 @@ T* createSuiteAndDocument( void (*fun)(T*&) ) #endif Inkscape::GC::init(); - if ( !inkscape_get_instance() ) + if ( !Inkscape::Application::exists() ) { // Create the global inkscape object. - static_cast<void>(g_object_new(inkscape_get_type(), NULL)); + Inkscape::Application::create("", false); } SPDocument* tmp = SPDocument::createNewDoc( NULL, TRUE, true ); diff --git a/src/ui/CMakeLists.txt b/src/ui/CMakeLists.txt index e5c605889..98a5a224c 100644 --- a/src/ui/CMakeLists.txt +++ b/src/ui/CMakeLists.txt @@ -4,8 +4,8 @@ set(ui_SRC control-manager.cpp dialog-events.cpp draw-anchor.cpp - interface.cpp - object-edit.cpp + interface.cpp + object-edit.cpp previewholder.cpp shape-editor.cpp tools-switch.cpp diff --git a/src/ui/clipboard.cpp b/src/ui/clipboard.cpp index 931a295d8..7c82fb230 100644 --- a/src/ui/clipboard.cpp +++ b/src/ui/clipboard.cpp @@ -330,6 +330,13 @@ void ClipboardManagerImpl::copySymbol(Inkscape::XML::Node* symbol, gchar const* use->setAttribute("xlink:href", id.c_str() ); // Set a default style in <use> rather than <symbol> so it can be changed. use->setAttribute("style", style ); + + Inkscape::XML::Node *nv_repr = sp_desktop_namedview(SP_ACTIVE_DESKTOP)->getRepr(); + gdouble scale_units = Inkscape::Util::Quantity::convert(1, nv_repr->attribute("inkscape:document-units"), "px"); + gchar *transform_str = sp_svg_transform_write(Geom::Scale(scale_units, scale_units)); + use->setAttribute("transform", transform_str); + g_free(transform_str); + _root->appendChild(use); // This min and max sets offsets, we don't have any so set to zero. diff --git a/src/ui/dialog-events.cpp b/src/ui/dialog-events.cpp index 6bd93bbc3..5bc8088a1 100644 --- a/src/ui/dialog-events.cpp +++ b/src/ui/dialog-events.cpp @@ -6,7 +6,7 @@ * bulia byak <bulia@dr.com> * Johan Engelen <j.b.c.engelen@ewi.utwente.nl> * - * Copyright (C) 2003-2007 Authors + * Copyright (C) 2003-2014 Authors * * Released under GNU GPL, read the file 'COPYING' for more information */ @@ -25,7 +25,7 @@ #include "macros.h" #include <gtk/gtk.h> #include "desktop.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "preferences.h" #include "ui/tools/tool-base.h" @@ -183,12 +183,11 @@ void sp_transientize(GtkWidget *dialog) void on_transientize (SPDesktop *desktop, win_data *wd ) { - sp_transientize_callback (0, desktop, wd); + sp_transientize_callback (desktop, wd); } void -sp_transientize_callback ( InkscapeApplication * /*inkscape*/, - SPDesktop *desktop, win_data *wd ) +sp_transientize_callback ( SPDesktop *desktop, win_data *wd ) { Inkscape::Preferences *prefs = Inkscape::Preferences::get(); gint transient_policy = prefs->getIntLimited( "/options/transientpolicy/value", 1, 0, 2); diff --git a/src/ui/dialog-events.h b/src/ui/dialog-events.h index b33eb3f38..b4a5d7c35 100644 --- a/src/ui/dialog-events.h +++ b/src/ui/dialog-events.h @@ -4,7 +4,7 @@ /* Authors: * bulia byak <bulia@dr.com> * - * Copyright (C) 2003 authors + * Copyright (C) 2003-2014 authors * * Released under GNU GPL, read the file 'COPYING' for more information */ @@ -28,8 +28,6 @@ class Entry; } class SPDesktop; - -struct InkscapeApplication; typedef struct { GtkWidget *win; @@ -53,14 +51,14 @@ void sp_transientize ( GtkWidget *win ); void on_transientize ( SPDesktop *desktop, win_data *wd ); -void sp_transientize_callback ( InkscapeApplication *inkscape, - SPDesktop *desktop, +void sp_transientize_callback ( SPDesktop *desktop, win_data *wd ); void on_dialog_hide (GtkWidget *w); void on_dialog_unhide (GtkWidget *w); -gboolean sp_dialog_hide (GObject *object, gpointer data); -gboolean sp_dialog_unhide (GObject *object, gpointer data); + +//gboolean sp_dialog_hide (GObject *object, gpointer data); +//gboolean sp_dialog_unhide (GObject *object, gpointer data); #endif diff --git a/src/ui/dialog/align-and-distribute.cpp b/src/ui/dialog/align-and-distribute.cpp index 431da7ad1..c538968d6 100644 --- a/src/ui/dialog/align-and-distribute.cpp +++ b/src/ui/dialog/align-and-distribute.cpp @@ -829,14 +829,14 @@ private : -static void on_tool_changed(InkscapeApplication */*inkscape*/, Inkscape::UI::Tools::ToolBase */*context*/, AlignAndDistribute *daad) +static void on_tool_changed(AlignAndDistribute *daad) { SPDesktop *desktop = SP_ACTIVE_DESKTOP; if (desktop && desktop->getEventContext()) daad->setMode(tools_active(desktop) == TOOLS_NODES); } -static void on_selection_changed(InkscapeApplication */*inkscape*/, Inkscape::Selection */*selection*/, AlignAndDistribute *daad) +static void on_selection_changed(AlignAndDistribute *daad) { daad->randomize_bbox = Geom::OptRect(); } @@ -1044,10 +1044,10 @@ AlignAndDistribute::AlignAndDistribute() contents->pack_start(_nodesFrame, true, true); //Connect to the global tool change signal - g_signal_connect (G_OBJECT (INKSCAPE), "set_eventcontext", G_CALLBACK (on_tool_changed), this); + _toolChangeConn = INKSCAPE.signal_eventcontext_set.connect(sigc::hide<0>(sigc::bind(sigc::ptr_fun(&on_tool_changed), this))); // Connect to the global selection change, to invalidate cached randomize_bbox - g_signal_connect (G_OBJECT (INKSCAPE), "change_selection", G_CALLBACK (on_selection_changed), this); + _selChangeConn = INKSCAPE.signal_selection_changed.connect(sigc::hide<0>(sigc::bind(sigc::ptr_fun(&on_selection_changed), this))); randomize_bbox = Geom::OptRect(); _desktopChangeConn = _deskTrack.connectDesktopChanged( sigc::mem_fun(*this, &AlignAndDistribute::setDesktop) ); @@ -1055,18 +1055,18 @@ AlignAndDistribute::AlignAndDistribute() show_all_children(); - on_tool_changed (NULL, NULL, this); // set current mode + on_tool_changed (this); // set current mode } AlignAndDistribute::~AlignAndDistribute() { - sp_signal_disconnect_by_data (G_OBJECT (INKSCAPE), this); - for (std::list<Action *>::iterator it = _actionList.begin(); it != _actionList.end(); ++it) { delete *it; } + _toolChangeConn.disconnect(); + _selChangeConn.disconnect(); _desktopChangeConn.disconnect(); _deskTrack.disconnect(); } @@ -1075,7 +1075,7 @@ void AlignAndDistribute::setTargetDesktop(SPDesktop *desktop) { if (_desktop != desktop) { _desktop = desktop; - on_tool_changed (NULL, NULL, this); + on_tool_changed (this); } } diff --git a/src/ui/dialog/align-and-distribute.h b/src/ui/dialog/align-and-distribute.h index dfd84535b..eecc30ff8 100644 --- a/src/ui/dialog/align-and-distribute.h +++ b/src/ui/dialog/align-and-distribute.h @@ -127,7 +127,8 @@ protected: SPDesktop *_desktop; DesktopTracker _deskTrack; sigc::connection _desktopChangeConn; - + sigc::connection _toolChangeConn; + sigc::connection _selChangeConn; private: AlignAndDistribute(AlignAndDistribute const &d); AlignAndDistribute& operator=(AlignAndDistribute const &d); diff --git a/src/ui/dialog/clonetiler.cpp b/src/ui/dialog/clonetiler.cpp index d1a675735..37881d4ae 100644 --- a/src/ui/dialog/clonetiler.cpp +++ b/src/ui/dialog/clonetiler.cpp @@ -76,15 +76,12 @@ static gdouble trace_zoom; static SPDocument *trace_doc = NULL; -CloneTiler::CloneTiler (void) : +CloneTiler::CloneTiler () : UI::Widget::Panel ("", "/dialogs/clonetiler/", SP_VERB_DIALOG_CLONETILER), dlg(NULL), desktop(NULL), deskTrack(), - table_row_labels(NULL), - selectChangedConn(), - subselChangedConn(), - selectModifiedConn() + table_row_labels(NULL) { Gtk::Box *contents = _getContents(); contents->set_spacing(0); @@ -1096,7 +1093,7 @@ CloneTiler::CloneTiler (void) : // unitmenu unit_menu = new Inkscape::UI::Widget::UnitMenu(); unit_menu->setUnitType(Inkscape::Util::UNIT_TYPE_LINEAR); - unit_menu->setUnit(sp_desktop_namedview(SP_ACTIVE_DESKTOP)->doc_units->abbr); + unit_menu->setUnit(sp_desktop_namedview(SP_ACTIVE_DESKTOP)->display_units->abbr); unitChangedConn = unit_menu->signal_changed().connect(sigc::mem_fun(*this, &CloneTiler::clonetiler_unit_changed)); { @@ -1273,12 +1270,13 @@ CloneTiler::CloneTiler (void) : // connect to global selection changed signal (so we can change desktops) and // external_change (so we're not fooled by undo) - g_signal_connect (G_OBJECT (INKSCAPE), "change_selection", G_CALLBACK (clonetiler_change_selection), dlg); - g_signal_connect (G_OBJECT (INKSCAPE), "external_change", G_CALLBACK (clonetiler_external_change), dlg); - g_signal_connect(G_OBJECT(dlg), "destroy", G_CALLBACK(clonetiler_disconnect_gsignal), G_OBJECT (INKSCAPE)); + selectChangedConn = INKSCAPE.signal_selection_changed.connect(sigc::bind(sigc::ptr_fun(&CloneTiler::clonetiler_change_selection), dlg)); + externChangedConn = INKSCAPE.signal_external_change.connect (sigc::bind(sigc::ptr_fun(&CloneTiler::clonetiler_external_change), dlg)); + + g_signal_connect(G_OBJECT(dlg), "destroy", G_CALLBACK(clonetiler_disconnect_gsignal), this); // update now - clonetiler_change_selection (NULL, sp_desktop_selection(SP_ACTIVE_DESKTOP), dlg); + clonetiler_change_selection (sp_desktop_selection(SP_ACTIVE_DESKTOP), dlg); } { @@ -1350,7 +1348,7 @@ void CloneTiler::on_picker_color_changed(guint rgba) is_updating = false; } -void CloneTiler::clonetiler_change_selection(InkscapeApplication * /*inkscape*/, Inkscape::Selection *selection, GtkWidget *dlg) +void CloneTiler::clonetiler_change_selection(Inkscape::Selection *selection, GtkWidget *dlg) { GtkWidget *buttons = GTK_WIDGET(g_object_get_data (G_OBJECT(dlg), "buttons_on_tiles")); GtkWidget *status = GTK_WIDGET(g_object_get_data (G_OBJECT(dlg), "status")); @@ -1379,16 +1377,18 @@ void CloneTiler::clonetiler_change_selection(InkscapeApplication * /*inkscape*/, } } -void CloneTiler::clonetiler_external_change(InkscapeApplication * /*inkscape*/, GtkWidget *dlg) +void CloneTiler::clonetiler_external_change(GtkWidget *dlg) { - clonetiler_change_selection (NULL, sp_desktop_selection(SP_ACTIVE_DESKTOP), dlg); + clonetiler_change_selection (sp_desktop_selection(SP_ACTIVE_DESKTOP), dlg); } -void CloneTiler::clonetiler_disconnect_gsignal(GObject *widget, gpointer source) +void CloneTiler::clonetiler_disconnect_gsignal(GObject *, gpointer source) { - if (source && G_IS_OBJECT(source)) { - sp_signal_disconnect_by_data (source, widget); - } + g_return_if_fail(source != NULL); + + CloneTiler* dlg = reinterpret_cast<CloneTiler*>(source); + dlg->selectChangedConn.disconnect(); + dlg->externChangedConn.disconnect(); } Geom::Affine CloneTiler::clonetiler_get_transform( @@ -2169,7 +2169,7 @@ void CloneTiler::clonetiler_remove(GtkWidget */*widget*/, GtkWidget *dlg, bool d } g_slist_free (to_delete); - clonetiler_change_selection (NULL, selection, dlg); + clonetiler_change_selection (selection, dlg); if (do_undo) { DocumentUndo::done(sp_desktop_document(desktop), SP_VERB_DIALOG_CLONETILER, @@ -2251,7 +2251,7 @@ void CloneTiler::clonetiler_apply(GtkWidget */*widget*/, GtkWidget *dlg) clonetiler_remove (NULL, dlg, false); - double scale_units = Inkscape::Util::Quantity::convert(1, "px", sp_desktop_document(desktop)->getDefaultUnit()); + double scale_units = Inkscape::Util::Quantity::convert(1, "px", &sp_desktop_document(desktop)->getSVGUnit()); double shiftx_per_i = 0.01 * prefs->getDoubleLimited(prefs_path + "shiftx_per_i", 0, -10000, 10000); double shifty_per_i = 0.01 * prefs->getDoubleLimited(prefs_path + "shifty_per_i", 0, -10000, 10000); @@ -2643,7 +2643,7 @@ void CloneTiler::clonetiler_apply(GtkWidget */*widget*/, GtkWidget *dlg) clonetiler_trace_finish (); } - clonetiler_change_selection (NULL, selection, dlg); + clonetiler_change_selection (selection, dlg); desktop->clearWaitingCursor(); diff --git a/src/ui/dialog/clonetiler.h b/src/ui/dialog/clonetiler.h index 70da86338..e5f5638b2 100644 --- a/src/ui/dialog/clonetiler.h +++ b/src/ui/dialog/clonetiler.h @@ -57,8 +57,8 @@ protected: static void clonetiler_keep_bbox_toggled(GtkToggleButton *tb, gpointer /*data*/); static void clonetiler_apply(GtkWidget */*widget*/, GtkWidget *dlg); static void clonetiler_unclump(GtkWidget */*widget*/, void *); - static void clonetiler_change_selection(InkscapeApplication * /*inkscape*/, Inkscape::Selection *selection, GtkWidget *dlg); - static void clonetiler_external_change(InkscapeApplication * /*inkscape*/, GtkWidget *dlg); + static void clonetiler_change_selection(Inkscape::Selection *selection, GtkWidget *dlg); + static void clonetiler_external_change(GtkWidget *dlg); static void clonetiler_disconnect_gsignal(GObject *widget, gpointer source); static void clonetiler_reset(GtkWidget */*widget*/, GtkWidget *dlg); static guint clonetiler_number_of_clones(SPObject *obj); @@ -129,6 +129,7 @@ private: sigc::connection desktopChangeConn; sigc::connection selectChangedConn; + sigc::connection externChangedConn; sigc::connection subselChangedConn; sigc::connection selectModifiedConn; sigc::connection color_changed_connection; diff --git a/src/ui/dialog/desktop-tracker.cpp b/src/ui/dialog/desktop-tracker.cpp index 3ed998252..0659de67b 100644 --- a/src/ui/dialog/desktop-tracker.cpp +++ b/src/ui/dialog/desktop-tracker.cpp @@ -22,7 +22,6 @@ DesktopTracker::DesktopTracker() : desktop(0), widget(0), hierID(0), - inkID(0), trackActive(false), desktopChangedSig() { @@ -41,7 +40,10 @@ void DesktopTracker::connect(GtkWidget *widget) // Use C/gobject callbacks to avoid gtkmm rewrap-during-destruct issues: hierID = g_signal_connect( G_OBJECT(widget), "hierarchy-changed", G_CALLBACK(hierarchyChangeCB), this ); - inkID = g_signal_connect( G_OBJECT(INKSCAPE), "activate_desktop", G_CALLBACK(activateDesktopCB), this ); + inkID = INKSCAPE.signal_activate_desktop.connect( + sigc::bind( + sigc::ptr_fun(&DesktopTracker::activateDesktopCB), this) + ); GtkWidget *wdgt = gtk_widget_get_ancestor(widget, SP_TYPE_DESKTOP_WIDGET); if (wdgt && !base) { @@ -60,11 +62,8 @@ void DesktopTracker::disconnect() } hierID = 0; } - if (inkID) { - if (INKSCAPE) { - g_signal_handler_disconnect(G_OBJECT(INKSCAPE), inkID); - } - inkID = 0; + if (inkID.connected()) { + inkID.disconnect(); } } @@ -94,12 +93,12 @@ sigc::connection DesktopTracker::connectDesktopChanged( const sigc::slot<void, S return desktopChangedSig.connect(slot); } -gboolean DesktopTracker::activateDesktopCB(InkscapeApplication */*inkscape*/, SPDesktop *desktop, DesktopTracker *self ) +void DesktopTracker::activateDesktopCB(SPDesktop *desktop, DesktopTracker *self ) { if (self && self->trackActive) { self->setDesktop(desktop); } - return FALSE; + //return FALSE; } bool DesktopTracker::hierarchyChangeCB(GtkWidget * /*widget*/, GtkWidget* /*prev*/, DesktopTracker *self) diff --git a/src/ui/dialog/desktop-tracker.h b/src/ui/dialog/desktop-tracker.h index 7b944ddfa..8cb205a35 100644 --- a/src/ui/dialog/desktop-tracker.h +++ b/src/ui/dialog/desktop-tracker.h @@ -36,7 +36,7 @@ public: sigc::connection connectDesktopChanged( const sigc::slot<void, SPDesktop*> & slot ); private: - static gboolean activateDesktopCB(InkscapeApplication *inkscape, SPDesktop *desktop, DesktopTracker *self ); + static void activateDesktopCB(SPDesktop *desktop, DesktopTracker *self ); static bool hierarchyChangeCB(GtkWidget *widget, GtkWidget* prev, DesktopTracker *self); void handleHierarchyChange(); @@ -46,7 +46,7 @@ private: SPDesktop *desktop; GtkWidget *widget; gulong hierID; - gulong inkID; + sigc::connection inkID; bool trackActive; sigc::signal<void, SPDesktop*> desktopChangedSig; }; diff --git a/src/ui/dialog/dialog.cpp b/src/ui/dialog/dialog.cpp index 213965a18..6dabcfb6b 100644 --- a/src/ui/dialog/dialog.cpp +++ b/src/ui/dialog/dialog.cpp @@ -41,12 +41,6 @@ namespace Inkscape { namespace UI { namespace Dialog { -void sp_retransientize(InkscapeApplication */*inkscape*/, SPDesktop *desktop, gpointer dlgPtr) -{ - Dialog *dlg = static_cast<Dialog *>(dlgPtr); - dlg->onDesktopActivated (desktop); -} - gboolean sp_retransientize_again(gpointer dlgPtr) { Dialog *dlg = static_cast<Dialog *>(dlgPtr); @@ -54,30 +48,6 @@ gboolean sp_retransientize_again(gpointer dlgPtr) return FALSE; // so that it is only called once } -void sp_dialog_shutdown(GObject * /*object*/, gpointer dlgPtr) -{ - Dialog *dlg = static_cast<Dialog *>(dlgPtr); - dlg->onShutdown(); -} - - -static void hideCallback(GObject * /*object*/, gpointer dlgPtr) -{ - g_return_if_fail( dlgPtr != NULL ); - - Dialog *dlg = static_cast<Dialog *>(dlgPtr); - dlg->onHideF12(); -} - -static void unhideCallback(GObject * /*object*/, gpointer dlgPtr) -{ - g_return_if_fail( dlgPtr != NULL ); - - Dialog *dlg = static_cast<Dialog *>(dlgPtr); - dlg->onShowF12(); -} - - //===================================================================== Dialog::Dialog(Behavior::BehaviorFactory behavior_factory, const char *prefs_path, int verb_num, @@ -103,10 +73,10 @@ Dialog::Dialog(Behavior::BehaviorFactory behavior_factory, const char *prefs_pat _behavior = behavior_factory(*this); _desktop = SP_ACTIVE_DESKTOP; - g_signal_connect(G_OBJECT(INKSCAPE), "activate_desktop", G_CALLBACK(sp_retransientize), (void *)this); - g_signal_connect(G_OBJECT(INKSCAPE), "dialogs_hide", G_CALLBACK(hideCallback), (void *)this); - g_signal_connect(G_OBJECT(INKSCAPE), "dialogs_unhide", G_CALLBACK(unhideCallback), (void *)this); - g_signal_connect(G_OBJECT(INKSCAPE), "shut_down", G_CALLBACK(sp_dialog_shutdown), (void *)this); + INKSCAPE.signal_activate_desktop.connect(sigc::mem_fun(*this, &Dialog::onDesktopActivated)); + INKSCAPE.signal_dialogs_hide.connect(sigc::mem_fun(*this, &Dialog::onHideF12)); + INKSCAPE.signal_dialogs_unhide.connect(sigc::mem_fun(*this, &Dialog::onShowF12)); + INKSCAPE.signal_shut_down.connect(sigc::mem_fun(*this, &Dialog::onShutdown)); Glib::wrap(gobj())->signal_event().connect(sigc::mem_fun(*this, &Dialog::_onEvent)); Glib::wrap(gobj())->signal_key_press_event().connect(sigc::mem_fun(*this, &Dialog::_onKeyPress)); diff --git a/src/ui/dialog/dialog.h b/src/ui/dialog/dialog.h index ccff43a56..9c7efd47b 100644 --- a/src/ui/dialog/dialog.h +++ b/src/ui/dialog/dialog.h @@ -30,7 +30,6 @@ namespace Dialog { enum BehaviorType { FLOATING, DOCK }; -void sp_retransientize(InkscapeApplication *inkscape, SPDesktop *desktop, gpointer dlgPtr); gboolean sp_retransientize_again(gpointer dlgPtr); void sp_dialog_shutdown(GObject *object, gpointer dlgPtr); diff --git a/src/ui/dialog/document-metadata.cpp b/src/ui/dialog/document-metadata.cpp index 77ea175d9..820d5a8bb 100644 --- a/src/ui/dialog/document-metadata.cpp +++ b/src/ui/dialog/document-metadata.cpp @@ -223,7 +223,7 @@ DocumentMetadata::_handleDocumentReplaced(SPDesktop* desktop, SPDocument *) } void -DocumentMetadata::_handleActivateDesktop(InkscapeApplication *, SPDesktop *desktop) +DocumentMetadata::_handleActivateDesktop(SPDesktop *desktop) { Inkscape::XML::Node *repr = sp_desktop_namedview(desktop)->getRepr(); repr->addListener(&_repr_events, this); @@ -231,7 +231,7 @@ DocumentMetadata::_handleActivateDesktop(InkscapeApplication *, SPDesktop *deskt } void -DocumentMetadata::_handleDeactivateDesktop(InkscapeApplication *, SPDesktop *desktop) +DocumentMetadata::_handleDeactivateDesktop(SPDesktop *desktop) { Inkscape::XML::Node *repr = sp_desktop_namedview(desktop)->getRepr(); repr->removeListenerByData(this); diff --git a/src/ui/dialog/document-metadata.h b/src/ui/dialog/document-metadata.h index 77084bc3d..cde5d92fd 100644 --- a/src/ui/dialog/document-metadata.h +++ b/src/ui/dialog/document-metadata.h @@ -28,6 +28,7 @@ # include <gtkmm/table.h> #endif +#include "inkscape.h" #include "ui/widget/licensor.h" #include "ui/widget/registry.h" @@ -56,8 +57,8 @@ protected: void init(); void _handleDocumentReplaced(SPDesktop* desktop, SPDocument *document); - void _handleActivateDesktop(InkscapeApplication *application, SPDesktop *desktop); - void _handleDeactivateDesktop(InkscapeApplication *application, SPDesktop *desktop); + void _handleActivateDesktop(SPDesktop *desktop); + void _handleDeactivateDesktop(SPDesktop *desktop); Gtk::Notebook _notebook; diff --git a/src/ui/dialog/document-properties.cpp b/src/ui/dialog/document-properties.cpp index dc8a0fee2..13ee8a6c6 100644 --- a/src/ui/dialog/document-properties.cpp +++ b/src/ui/dialog/document-properties.cpp @@ -114,7 +114,7 @@ DocumentProperties::DocumentProperties() _rcb_shad(_("_Show border shadow"), _("If set, page border shows a shadow on its right and lower side"), "inkscape:showpageshadow", _wr, false), _rcp_bg(_("Back_ground color:"), _("Background color"), _("Color of the page background. Note: transparency setting ignored while editing but used when exporting to bitmap."), "pagecolor", "inkscape:pageopacity", _wr), _rcp_bord(_("Border _color:"), _("Page border color"), _("Color of the page border"), "bordercolor", "borderopacity", _wr), - _rum_deflt(_("Default _units:"), "inkscape:document-units", _wr), + _rum_deflt(_("Display _units:"), "inkscape:document-units", _wr), _page_sizer(_wr), //--------------------------------------------------------------- //General snap options @@ -1205,10 +1205,10 @@ void DocumentProperties::removeExternalScript(){ const GSList *current = SP_ACTIVE_DOCUMENT->getResourceList( "script" ); while ( current ) { - if (current->data && SP_IS_OBJECT(current->data)) { - SPObject* obj = SP_OBJECT(current->data); - SPScript* script = SP_SCRIPT(obj); - if (name == script->xlinkhref){ + SPObject* obj = reinterpret_cast<SPObject *>(current->data); + if (obj) { + SPScript* script = dynamic_cast<SPScript *>(obj); + if (script && (name == script->xlinkhref)) { //XML Tree being used directly here while it shouldn't be. Inkscape::XML::Node *repr = obj->getRepr(); @@ -1354,10 +1354,15 @@ void DocumentProperties::populate_script_lists(){ _ExternalScriptsListStore->clear(); _EmbeddedScriptsListStore->clear(); const GSList *current = SP_ACTIVE_DOCUMENT->getResourceList( "script" ); - if (current) _scripts_observer.set(SP_OBJECT(current->data)->parent); + if (current) { + SPObject *obj = reinterpret_cast<SPObject *>(current->data); + g_assert(obj != NULL); + _scripts_observer.set(obj->parent); + } while ( current ) { - SPObject* obj = SP_OBJECT(current->data); - SPScript* script = SP_SCRIPT(obj); + SPObject* obj = reinterpret_cast<SPObject *>(current->data); + SPScript* script = dynamic_cast<SPScript *>(obj); + g_assert(script != NULL); if (script->xlinkhref) { Gtk::TreeModel::Row row = *(_ExternalScriptsListStore->append()); @@ -1475,8 +1480,8 @@ void DocumentProperties::update() _rcb_antialias.set_xml_target(root->getRepr(), dt->getDocument()); _rcb_antialias.setActive(root->style->shape_rendering.computed != SP_CSS_SHAPE_RENDERING_CRISPEDGES); - if (nv->doc_units) { - _rum_deflt.setUnit (nv->doc_units->abbr); + if (nv->display_units) { + _rum_deflt.setUnit (nv->display_units->abbr); } double doc_w = sp_desktop_document(dt)->getRoot()->width.value; @@ -1594,7 +1599,7 @@ void DocumentProperties::_handleDocumentReplaced(SPDesktop* desktop, SPDocument update(); } -void DocumentProperties::_handleActivateDesktop(InkscapeApplication *, SPDesktop *desktop) +void DocumentProperties::_handleActivateDesktop(SPDesktop *desktop) { Inkscape::XML::Node *repr = sp_desktop_namedview(desktop)->getRepr(); repr->addListener(&_repr_events, this); @@ -1603,7 +1608,7 @@ void DocumentProperties::_handleActivateDesktop(InkscapeApplication *, SPDesktop update(); } -void DocumentProperties::_handleDeactivateDesktop(InkscapeApplication *, SPDesktop *desktop) +void DocumentProperties::_handleDeactivateDesktop(SPDesktop *desktop) { Inkscape::XML::Node *repr = sp_desktop_namedview(desktop)->getRepr(); repr->removeListenerByData(this); @@ -1703,7 +1708,10 @@ void DocumentProperties::onDocUnitChange() Inkscape::SVGOStringStream os; os << doc_unit->abbr; repr->setAttribute("inkscape:document-units", os.str().c_str()); - + + // Disable changing of SVG Units. The intent here is to change the units in the UI, not the units in SVG. + // This code should be moved (and fixed) once we have an "SVG Units" setting that sets what units are used in SVG data. +#if 0 // Set viewBox if (doc->getRoot()->viewBox_set) { gdouble scale = Inkscape::Util::Quantity::convert(1, old_doc_unit, doc_unit); @@ -1755,10 +1763,11 @@ void DocumentProperties::onDocUnitChange() prefs->setBool("/options/transform/rectcorners", transform_rectcorners); prefs->setBool("/options/transform/pattern", transform_pattern); prefs->setBool("/options/transform/gradient", transform_gradient); +#endif doc->setModifiedSinceSave(); - DocumentUndo::done(doc, SP_VERB_NONE, _("Changed document unit")); + DocumentUndo::done(doc, SP_VERB_NONE, _("Changed default display unit")); } } // namespace Dialog diff --git a/src/ui/dialog/document-properties.h b/src/ui/dialog/document-properties.h index ee7e88b18..b1f90b4b7 100644 --- a/src/ui/dialog/document-properties.h +++ b/src/ui/dialog/document-properties.h @@ -94,8 +94,8 @@ protected: void save_default_metadata(); void _handleDocumentReplaced(SPDesktop* desktop, SPDocument *document); - void _handleActivateDesktop(InkscapeApplication *application, SPDesktop *desktop); - void _handleDeactivateDesktop(InkscapeApplication *application, SPDesktop *desktop); + void _handleActivateDesktop(SPDesktop *desktop); + void _handleDeactivateDesktop(SPDesktop *desktop); Inkscape::XML::SignalObserver _emb_profiles_observer, _scripts_observer; Gtk::Notebook _notebook; diff --git a/src/ui/dialog/export.cpp b/src/ui/dialog/export.cpp index b044a6e2c..1ebd1fc7c 100644 --- a/src/ui/dialog/export.cpp +++ b/src/ui/dialog/export.cpp @@ -51,7 +51,7 @@ #include "ui/widget/unit-menu.h" #include "util/units.h" #include "helper/window.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "document.h" #include "document-undo.h" #include "desktop-handles.h" @@ -206,7 +206,7 @@ Export::Export (void) : SPDesktop *desktop = SP_ACTIVE_DESKTOP; if (desktop) { - unit_selector.setUnit(sp_desktop_namedview(desktop)->doc_units->abbr); + unit_selector.setUnit(sp_desktop_namedview(desktop)->display_units->abbr); } unitChangedConn = unit_selector.signal_changed().connect(sigc::mem_fun(*this, &Export::onUnitChanged)); unitbox.pack_end(unit_selector, false, false, 0); @@ -588,7 +588,7 @@ Glib::ustring Export::create_filepath_from_id (Glib::ustring id, const Glib::ust } if (directory.empty()) { - directory = homedir_path(NULL); + directory = INKSCAPE.homedir_path(NULL); } Glib::ustring filename = Glib::build_filename(directory, id+".png"); diff --git a/src/ui/dialog/filedialogimpl-gtkmm.cpp b/src/ui/dialog/filedialogimpl-gtkmm.cpp index 5d330f7f0..17cf835cd 100644 --- a/src/ui/dialog/filedialogimpl-gtkmm.cpp +++ b/src/ui/dialog/filedialogimpl-gtkmm.cpp @@ -577,8 +577,9 @@ bool SVGPreview::set(Glib::ustring &fileName, int dialogType) SVGPreview::SVGPreview() { - if (!INKSCAPE) - inkscape_application_init("", false); + // \FIXME Why?!!?? + if (!Inkscape::Application::exists()) + Inkscape::Application::create("", false); document = NULL; viewerGtk = NULL; set_size_request(150, 150); @@ -1083,7 +1084,7 @@ FileSaveDialogImplGtk::FileSaveDialogImplGtk(Gtk::Window &parentWindow, const Gl } // allow easy access to the user's own templates folder - gchar *templates = profile_path("templates"); + gchar *templates = Inkscape::Application::profile_path("templates"); if (Inkscape::IO::file_test(templates, G_FILE_TEST_EXISTS) && Inkscape::IO::file_test(templates, G_FILE_TEST_IS_DIR) && g_path_is_absolute(templates)) { add_shortcut_folder(templates); diff --git a/src/ui/dialog/fill-and-stroke.h b/src/ui/dialog/fill-and-stroke.h index 35c98ef9c..f2a6bf39d 100644 --- a/src/ui/dialog/fill-and-stroke.h +++ b/src/ui/dialog/fill-and-stroke.h @@ -41,8 +41,7 @@ public: virtual void setDesktop(SPDesktop *desktop); - void selectionChanged(InkscapeApplication *inkscape, - Inkscape::Selection *selection); + //void selectionChanged(Inkscape::Selection *selection); void showPageFill(); void showPageStrokePaint(); diff --git a/src/ui/dialog/grid-arrange-tab.cpp b/src/ui/dialog/grid-arrange-tab.cpp index 1417b39fa..2ff647a74 100644 --- a/src/ui/dialog/grid-arrange-tab.cpp +++ b/src/ui/dialog/grid-arrange-tab.cpp @@ -567,17 +567,6 @@ void GridArrangeTab::updateSelection() } - -/*########################## -## Experimental -##########################*/ - -static void updateSelectionCallback(InkscapeApplication */*inkscape*/, Inkscape::Selection */*selection*/, GridArrangeTab *dlg) -{ - dlg->updateSelection(); -} - - //######################################################################### //## C O N S T R U C T O R / D E S T R U C T O R //######################################################################### @@ -605,7 +594,7 @@ GridArrangeTab::GridArrangeTab(ArrangeDialog *parent) { // Selection Change signal - g_signal_connect ( G_OBJECT (INKSCAPE), "change_selection", G_CALLBACK (updateSelectionCallback), this); + INKSCAPE.signal_selection_changed.connect(sigc::hide<0>(sigc::mem_fun(*this, &GridArrangeTab::updateSelection))); } Gtk::Box *contents = this; diff --git a/src/ui/dialog/guides.cpp b/src/ui/dialog/guides.cpp index 4519a905f..221f9a1c0 100644 --- a/src/ui/dialog/guides.cpp +++ b/src/ui/dialog/guides.cpp @@ -216,8 +216,8 @@ void GuidelinePropertiesDialog::_setup() { /* fixme: We should allow percents here too, as percents of the canvas size */ _unit_menu.setUnitType(UNIT_TYPE_LINEAR); _unit_menu.setUnit("px"); - if (_desktop->namedview->doc_units) { - _unit_menu.setUnit( _desktop->namedview->doc_units->abbr ); + if (_desktop->namedview->display_units) { + _unit_menu.setUnit( _desktop->namedview->display_units->abbr ); } _spin_angle.setUnit(_angle_unit_status); diff --git a/src/ui/dialog/inkscape-preferences.cpp b/src/ui/dialog/inkscape-preferences.cpp index 75cfe5bfe..ed4b16008 100644 --- a/src/ui/dialog/inkscape-preferences.cpp +++ b/src/ui/dialog/inkscape-preferences.cpp @@ -461,7 +461,7 @@ void InkscapePreferences::initPageTools() _page_text.add_line( false, _("Text size unit type:"), _font_unit_type, "", _("Set the type of unit used in the text toolbar and text dialogs"), false); _font_output_px.init ( _("Always output text size in pixels (px)"), "/options/font/textOutputPx", true); - _page_text.add_line( false, "", _font_output_px, "", _("Always convert the text size units above into pixels (px) before saving to file")); +// _page_text.add_line( false, "", _font_output_px, "", _("Always convert the text size units above into pixels (px) before saving to file")); this->AddNewObjectsStyle(_page_text, "/tools/text"); @@ -1913,7 +1913,7 @@ void InkscapePreferences::initPageSystem() _page_system.add_group_header( _("System info")); - _sys_user_config.set_text((char const *)profile_path("")); + _sys_user_config.set_text((char const *)Inkscape::Application::profile_path("")); _sys_user_config.set_editable(false); _page_system.add_line(true, _("User config: "), _sys_user_config, "", _("Location of users configuration"), true); diff --git a/src/ui/dialog/livepatheffect-editor.cpp b/src/ui/dialog/livepatheffect-editor.cpp index eb3857ee7..178c32c38 100644 --- a/src/ui/dialog/livepatheffect-editor.cpp +++ b/src/ui/dialog/livepatheffect-editor.cpp @@ -475,9 +475,13 @@ LivePathEffectEditor::onAdd() // run sp_selection_clone_original_path_lpe sp_selection_clone_original_path_lpe(current_desktop); + SPItem *new_item = sel->singleItem(); - new_item->getRepr()->setAttribute("id", id); - new_item->getRepr()->setAttribute("transform", transform); + // Check that the cloning was successful. We don't want to change the ID of the original referenced path! + if (new_item && (new_item != orig)) { + new_item->getRepr()->setAttribute("id", id); + new_item->getRepr()->setAttribute("transform", transform); + } g_free(id); g_free(transform); diff --git a/src/ui/dialog/panel-dialog.h b/src/ui/dialog/panel-dialog.h index b4a355083..39110f47a 100644 --- a/src/ui/dialog/panel-dialog.h +++ b/src/ui/dialog/panel-dialog.h @@ -49,19 +49,10 @@ public: virtual UI::Widget::Panel &getPanel() { return _panel; } protected: - static void handle_deactivate_desktop(InkscapeApplication *application, SPDesktop *desktop, void *data) { - g_return_if_fail(data != NULL); - static_cast<PanelDialogBase *>(data)->_propagateDesktopDeactivated(application, desktop); - } - - static void _handle_activate_desktop(InkscapeApplication *application, SPDesktop *desktop, void *data) { - g_return_if_fail(data != NULL); - static_cast<PanelDialogBase *>(data)->_propagateDesktopActivated(application, desktop); - } inline virtual void _propagateDocumentReplaced(SPDesktop* desktop, SPDocument *document); - inline virtual void _propagateDesktopActivated(InkscapeApplication *, SPDesktop *); - inline virtual void _propagateDesktopDeactivated(InkscapeApplication *, SPDesktop *); + inline virtual void _propagateDesktopActivated(SPDesktop *); + inline virtual void _propagateDesktopDeactivated(SPDesktop *); UI::Widget::Panel &_panel; sigc::connection _document_replaced_connection; @@ -134,17 +125,17 @@ void PanelDialogBase::_propagateDocumentReplaced(SPDesktop *desktop, SPDocument _panel.signalDocumentReplaced().emit(desktop, document); } -void PanelDialogBase::_propagateDesktopActivated(InkscapeApplication *application, SPDesktop *desktop) +void PanelDialogBase::_propagateDesktopActivated(SPDesktop *desktop) { _document_replaced_connection = desktop->connectDocumentReplaced(sigc::mem_fun(*this, &PanelDialogBase::_propagateDocumentReplaced)); - _panel.signalActivateDesktop().emit(application, desktop); + _panel.signalActivateDesktop().emit(desktop); } -void PanelDialogBase::_propagateDesktopDeactivated(InkscapeApplication *application, SPDesktop *desktop) +void PanelDialogBase::_propagateDesktopDeactivated(SPDesktop *desktop) { _document_replaced_connection.disconnect(); - _panel.signalDeactiveDesktop().emit(application, desktop); + _panel.signalDeactiveDesktop().emit(desktop); } @@ -162,7 +153,7 @@ PanelDialog<B>::PanelDialog(Widget::Panel &panel, char const *prefs_path, int co SPDesktop *desktop = SP_ACTIVE_DESKTOP; - _propagateDesktopActivated(INKSCAPE, desktop); + _propagateDesktopActivated(desktop); _document_replaced_connection = desktop->connectDocumentReplaced(sigc::mem_fun(*this, &PanelDialog::_propagateDocumentReplaced)); @@ -211,7 +202,7 @@ PanelDialog<Behavior::FloatingBehavior>::PanelDialog(UI::Widget::Panel &panel, c SPDesktop *desktop = SP_ACTIVE_DESKTOP; - _propagateDesktopActivated(INKSCAPE, desktop); + _propagateDesktopActivated(desktop); _document_replaced_connection = desktop->connectDocumentReplaced(sigc::mem_fun(*this, &PanelDialog::_propagateDocumentReplaced)); @@ -247,8 +238,12 @@ PanelDialog<Behavior::FloatingBehavior> *PanelDialog<Behavior::FloatingBehavior> new PanelDialog<Behavior::FloatingBehavior>(panel, panel.getPrefsPath(), panel.getVerb(), panel.getApplyLabel()); - g_signal_connect(G_OBJECT(INKSCAPE), "activate_desktop", G_CALLBACK(_handle_activate_desktop), instance); - g_signal_connect(G_OBJECT(INKSCAPE), "deactivate_desktop", G_CALLBACK(handle_deactivate_desktop), instance); + INKSCAPE.signal_activate_desktop.connect( + sigc::mem_fun(*instance, &PanelDialog<Behavior::FloatingBehavior>::_propagateDesktopActivated) + ); + INKSCAPE.signal_deactivate_desktop.connect( + sigc::mem_fun(*instance, &PanelDialog<Behavior::FloatingBehavior>::_propagateDesktopDeactivated) + ); return instance; } diff --git a/src/ui/dialog/swatches.cpp b/src/ui/dialog/swatches.cpp index a3cfeeba8..187e31233 100644 --- a/src/ui/dialog/swatches.cpp +++ b/src/ui/dialog/swatches.cpp @@ -527,7 +527,7 @@ static void loadEmUp() beenHere = true; std::list<gchar *> sources; - sources.push_back( profile_path("palettes") ); + sources.push_back( Inkscape::Application::profile_path("palettes") ); sources.push_back( g_strdup(INKSCAPE_PALETTESDIR) ); sources.push_back( g_strdup(CREATE_PALETTESDIR) ); diff --git a/src/ui/dialog/symbols.cpp b/src/ui/dialog/symbols.cpp index a17a03861..0ec071d06 100644 --- a/src/ui/dialog/symbols.cpp +++ b/src/ui/dialog/symbols.cpp @@ -287,7 +287,7 @@ SymbolsDialog::SymbolsDialog( gchar const* prefsPath ) : ++row; /**********************************************************/ - currentDesktop = inkscape_active_desktop(); + currentDesktop = SP_ACTIVE_DESKTOP; currentDocument = sp_desktop_document(currentDesktop); previewDocument = symbols_preview_doc(); /* Template to render symbols in */ @@ -585,13 +585,15 @@ void SymbolsDialog::get_symbols() { std::list<Glib::ustring> directories; +// \TODO optimize this + if( Inkscape::IO::file_test( INKSCAPE_SYMBOLSDIR, G_FILE_TEST_EXISTS ) && Inkscape::IO::file_test( INKSCAPE_SYMBOLSDIR, G_FILE_TEST_IS_DIR ) ) { directories.push_back( INKSCAPE_SYMBOLSDIR ); } - if( Inkscape::IO::file_test( profile_path("symbols"), G_FILE_TEST_EXISTS ) && - Inkscape::IO::file_test( profile_path("symbols"), G_FILE_TEST_IS_DIR ) ) { - directories.push_back( profile_path("symbols") ); + if( Inkscape::IO::file_test( Inkscape::Application::profile_path("symbols"), G_FILE_TEST_EXISTS ) && + Inkscape::IO::file_test( Inkscape::Application::profile_path("symbols"), G_FILE_TEST_IS_DIR ) ) { + directories.push_back( Inkscape::Application::profile_path("symbols") ); } std::list<Glib::ustring>::iterator it; diff --git a/src/ui/dialog/template-load-tab.cpp b/src/ui/dialog/template-load-tab.cpp index 13cb01eef..fca1f7b30 100644 --- a/src/ui/dialog/template-load-tab.cpp +++ b/src/ui/dialog/template-load-tab.cpp @@ -194,7 +194,7 @@ void TemplateLoadTab::_refreshTemplatesList() void TemplateLoadTab::_loadTemplates() { // user's local dir - _getTemplatesFromDir(profile_path("templates") + _loading_path); + _getTemplatesFromDir(Inkscape::Application::profile_path("templates") + _loading_path); // system templates dir _getTemplatesFromDir(INKSCAPE_TEMPLATESDIR + _loading_path); diff --git a/src/ui/dialog/transformation.cpp b/src/ui/dialog/transformation.cpp index 3e135b9b2..2c6692777 100644 --- a/src/ui/dialog/transformation.cpp +++ b/src/ui/dialog/transformation.cpp @@ -47,16 +47,13 @@ namespace Inkscape { namespace UI { namespace Dialog { -static void on_selection_changed(InkscapeApplication */*inkscape*/, Inkscape::Selection *selection, Transformation *daad) +static void on_selection_changed(Inkscape::Selection *selection, Transformation *daad) { int page = daad->getCurrentPage(); daad->updateSelection((Inkscape::UI::Dialog::Transformation::PageType)page, selection); } -static void on_selection_modified( InkscapeApplication */*inkscape*/, - Inkscape::Selection *selection, - guint /*flags*/, - Transformation *daad ) +static void on_selection_modified(Inkscape::Selection *selection, Transformation *daad) { int page = daad->getCurrentPage(); daad->updateSelection((Inkscape::UI::Dialog::Transformation::PageType)page, selection); @@ -159,8 +156,8 @@ Transformation::Transformation() } // Connect to the global selection changed & modified signals - g_signal_connect (G_OBJECT (INKSCAPE), "change_selection", G_CALLBACK (on_selection_changed), this); - g_signal_connect (G_OBJECT (INKSCAPE), "modify_selection", G_CALLBACK (on_selection_modified), this); + _selChangeConn = INKSCAPE.signal_selection_changed.connect(sigc::bind(sigc::ptr_fun(&on_selection_changed), this)); + _selModifyConn = INKSCAPE.signal_selection_modified.connect(sigc::hide<1>(sigc::bind(sigc::ptr_fun(&on_selection_modified), this))); _desktopChangeConn = _deskTrack.connectDesktopChanged( sigc::mem_fun(*this, &Transformation::setDesktop) ); _deskTrack.connect(GTK_WIDGET(gobj())); @@ -170,7 +167,8 @@ Transformation::Transformation() Transformation::~Transformation() { - sp_signal_disconnect_by_data (G_OBJECT (INKSCAPE), this); + _selModifyConn.disconnect(); + _selChangeConn.disconnect(); _desktopChangeConn.disconnect(); _deskTrack.disconnect(); } @@ -208,8 +206,8 @@ void Transformation::layoutPageMove() // Setting default unit to document unit SPDesktop *dt = getDesktop(); SPNamedView *nv = sp_desktop_namedview(dt); - if (nv->doc_units) { - _units_move.setUnit(nv->doc_units->abbr); + if (nv->display_units) { + _units_move.setUnit(nv->display_units->abbr); } _scalar_move_horizontal.initScalar(-1e6, 1e6); diff --git a/src/ui/dialog/transformation.h b/src/ui/dialog/transformation.h index 1d24a0c94..89aa95d90 100644 --- a/src/ui/dialog/transformation.h +++ b/src/ui/dialog/transformation.h @@ -232,6 +232,9 @@ private: Gtk::Button *applyButton; Gtk::Button *resetButton; Gtk::Button *cancelButton; + + sigc::connection _selChangeConn; + sigc::connection _selModifyConn; }; diff --git a/src/ui/interface.cpp b/src/ui/interface.cpp index 7830a8de1..6bc94ab7a 100644 --- a/src/ui/interface.cpp +++ b/src/ui/interface.cpp @@ -29,7 +29,7 @@ #include <gtkmm/imagemenuitem.h> #include <gtkmm/separatormenuitem.h> -#include "inkscape-private.h" +#include "inkscape.h" #include "extension/db.h" #include "extension/effect.h" #include "extension/input.h" @@ -270,7 +270,7 @@ sp_create_window(SPViewWidget *vw, bool editable) // needed because the first ACTIVATE_DESKTOP was sent when there was no window yet if ( SP_IS_DESKTOP_WIDGET(vw) ) { - inkscape_reactivate_desktop(SP_DESKTOP_WIDGET(vw)->desktop); + INKSCAPE.reactivate_desktop(SP_DESKTOP_WIDGET(vw)->desktop); } } @@ -318,13 +318,13 @@ sp_ui_close_view(GtkWidget */*widget*/) // If closing the last document, open a new document so Inkscape doesn't quit. std::list<SPDesktop *> desktops; - inkscape_get_all_desktops(desktops); + INKSCAPE.get_all_desktops(desktops); if (desktops.size() == 1) { Glib::ustring templateUri = sp_file_default_template_uri(); SPDocument *doc = SPDocument::createNewDoc( templateUri.c_str() , TRUE, true ); // Set viewBox if it doesn't exist if (!doc->getRoot()->viewBox_set) { - doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDefaultUnit()), doc->getHeight().value(doc->getDefaultUnit()))); + doc->setViewBox(Geom::Rect::from_xywh(0, 0, doc->getWidth().value(doc->getDisplayUnit()), doc->getHeight().value(doc->getDisplayUnit()))); } dt->change_document(doc); sp_namedview_window_from_document(dt); @@ -921,7 +921,7 @@ static void sp_ui_build_dyn_menus(Inkscape::XML::Node *menus, GtkWidget *menu, I GtkWidget *sp_ui_main_menubar(Inkscape::UI::View::View *view) { GtkWidget *mbar = gtk_menu_bar_new(); - sp_ui_build_dyn_menus(inkscape_get_menus(INKSCAPE), mbar, view); + sp_ui_build_dyn_menus(INKSCAPE.get_menus(), mbar, view); return mbar; } @@ -2117,13 +2117,13 @@ void ContextMenu::ImageEdit(void) void ContextMenu::ImageTraceBitmap(void) { - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); _desktop->_dlg_mgr->showDialog("Trace"); } void ContextMenu::ImageTracePixelArt(void) { - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); _desktop->_dlg_mgr->showDialog("PixelArt"); } diff --git a/src/ui/tool/node.cpp b/src/ui/tool/node.cpp index 4abc901d2..8c22f7c6e 100644 --- a/src/ui/tool/node.cpp +++ b/src/ui/tool/node.cpp @@ -60,10 +60,10 @@ Inkscape::ControlType nodeTypeToCtrlType(Inkscape::UI::NodeType type) namespace Inkscape { namespace UI { -const double handleCubicGap = 0.01; +/*const double handleCubicGap = 0.01;*/ const double noPower = 0.0; const double defaultStartPower = 0.3334; -const double defaultEndPower = 0.6667; +/*const double defaultEndPower = 0.6667;*/ ControlPoint::ColorSet Node::node_colors = { {0xbfbfbf00, 0x000000ff}, // normal fill, stroke @@ -566,9 +566,9 @@ Glib::ustring Handle::_getDragTip(GdkEventMotion */*event*/) const Inkscape::Util::Quantity x_q = Inkscape::Util::Quantity(dist[Geom::X], "px"); Inkscape::Util::Quantity y_q = Inkscape::Util::Quantity(dist[Geom::Y], "px"); Inkscape::Util::Quantity len_q = Inkscape::Util::Quantity(length(), "px"); - GString *x = g_string_new(x_q.string(_desktop->namedview->doc_units).c_str()); - GString *y = g_string_new(y_q.string(_desktop->namedview->doc_units).c_str()); - GString *len = g_string_new(len_q.string(_desktop->namedview->doc_units).c_str()); + GString *x = g_string_new(x_q.string(_desktop->namedview->display_units).c_str()); + GString *y = g_string_new(y_q.string(_desktop->namedview->display_units).c_str()); + GString *len = g_string_new(len_q.string(_desktop->namedview->display_units).c_str()); Glib::ustring ret = format_tip(C_("Path handle tip", "Move handle by %s, %s; angle %.2f°, length %s"), x->str, y->str, angle, len->str); g_string_free(x, TRUE); @@ -1490,8 +1490,8 @@ Glib::ustring Node::_getDragTip(GdkEventMotion */*event*/) const Inkscape::Util::Quantity x_q = Inkscape::Util::Quantity(dist[Geom::X], "px"); Inkscape::Util::Quantity y_q = Inkscape::Util::Quantity(dist[Geom::Y], "px"); - GString *x = g_string_new(x_q.string(_desktop->namedview->doc_units).c_str()); - GString *y = g_string_new(y_q.string(_desktop->namedview->doc_units).c_str()); + GString *x = g_string_new(x_q.string(_desktop->namedview->display_units).c_str()); + GString *y = g_string_new(y_q.string(_desktop->namedview->display_units).c_str()); Glib::ustring ret = format_tip(C_("Path node tip", "Move node by %s, %s"), x->str, y->str); g_string_free(x, TRUE); g_string_free(y, TRUE); diff --git a/src/ui/tools-switch.cpp b/src/ui/tools-switch.cpp index 47b9d2832..07d68471f 100644 --- a/src/ui/tools-switch.cpp +++ b/src/ui/tools-switch.cpp @@ -16,7 +16,7 @@ #include <cstring> #include <string> -#include "inkscape-private.h" +#include "inkscape.h" #include "desktop.h" #include "desktop-handles.h" #include <glibmm/i18n.h> @@ -159,7 +159,7 @@ tools_switch(SPDesktop *dt, int num) /* fixme: This is really ugly hack. We should bind and unbind class methods */ /* First 4 tools use guides, first is undefined but we don't care */ dt->activate_guides(num < 5); - inkscape_eventcontext_set(dt->getEventContext()); + INKSCAPE.eventcontext_set(dt->getEventContext()); } void tools_switch_by_item(SPDesktop *dt, SPItem *item, Geom::Point const p) diff --git a/src/ui/tools/arc-tool.cpp b/src/ui/tools/arc-tool.cpp index 4f64ade25..9c3195a42 100644 --- a/src/ui/tools/arc-tool.cpp +++ b/src/ui/tools/arc-tool.cpp @@ -405,8 +405,8 @@ void ArcTool::drag(Geom::Point pt, guint state) { Inkscape::Util::Quantity rdimx_q = Inkscape::Util::Quantity(rdimx, "px"); Inkscape::Util::Quantity rdimy_q = Inkscape::Util::Quantity(rdimy, "px"); - GString *xs = g_string_new(rdimx_q.string(desktop->namedview->doc_units).c_str()); - GString *ys = g_string_new(rdimy_q.string(desktop->namedview->doc_units).c_str()); + GString *xs = g_string_new(rdimx_q.string(desktop->namedview->display_units).c_str()); + GString *ys = g_string_new(rdimy_q.string(desktop->namedview->display_units).c_str()); if (state & GDK_CONTROL_MASK) { int ratio_x, ratio_y; diff --git a/src/ui/tools/connector-tool.cpp b/src/ui/tools/connector-tool.cpp index 7b5c84c16..23450fcbd 100644 --- a/src/ui/tools/connector-tool.cpp +++ b/src/ui/tools/connector-tool.cpp @@ -1304,7 +1304,7 @@ bool cc_item_is_connector(SPItem *item) void cc_selection_set_avoid(bool const set_avoid) { - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; if (desktop == NULL) { return; } diff --git a/src/ui/tools/freehand-base.cpp b/src/ui/tools/freehand-base.cpp index 6434c30d2..32702a17e 100644 --- a/src/ui/tools/freehand-base.cpp +++ b/src/ui/tools/freehand-base.cpp @@ -256,7 +256,7 @@ static void spdc_apply_powerstroke_shape(const std::vector<Geom::Point> & points std::ostringstream s; s.imbue(std::locale::classic()); - s << "0," << stroke_width / 2.; + s << points[0][Geom::X] << "," << stroke_width / 2.; // write powerstroke parameters: lpe->getRepr()->setAttribute("start_linecap_type", "zerowidth"); @@ -703,8 +703,8 @@ static void spdc_flush_white(FreehandBase *dc, SPCurve *gc) dc->selection->set(repr); Inkscape::GC::release(repr); item->transform = SP_ITEM(desktop->currentLayer())->i2doc_affine().inverse(); - item->doWriteTransform(item->getRepr(), item->transform, NULL, true); item->updateRepr(); + item->doWriteTransform(item->getRepr(), item->transform, NULL, true); } DocumentUndo::done(doc, SP_IS_PEN_CONTEXT(dc)? SP_VERB_CONTEXT_PEN : SP_VERB_CONTEXT_PENCIL, diff --git a/src/ui/tools/pen-tool.cpp b/src/ui/tools/pen-tool.cpp index 92937a135..fbcdf6142 100644 --- a/src/ui/tools/pen-tool.cpp +++ b/src/ui/tools/pen-tool.cpp @@ -1366,7 +1366,7 @@ void PenTool::_setAngleDistanceStatusMessage(Geom::Point const p, int pc_point_t Geom::Point rel = p - this->p[pc_point_to_compare]; Inkscape::Util::Quantity q = Inkscape::Util::Quantity(Geom::L2(rel), "px"); - GString *dist = g_string_new(q.string(desktop->namedview->doc_units).c_str()); + GString *dist = g_string_new(q.string(desktop->namedview->display_units).c_str()); double angle = atan2(rel[Geom::Y], rel[Geom::X]) * 180 / M_PI; Inkscape::Preferences *prefs = Inkscape::Preferences::get(); if (prefs->getBool("/options/compassangledisplay/value", 0) != 0) { diff --git a/src/ui/tools/rect-tool.cpp b/src/ui/tools/rect-tool.cpp index de91dcff4..67df0d9a5 100644 --- a/src/ui/tools/rect-tool.cpp +++ b/src/ui/tools/rect-tool.cpp @@ -422,8 +422,8 @@ void RectTool::drag(Geom::Point const pt, guint state) { Inkscape::Util::Quantity rdimx_q = Inkscape::Util::Quantity(rdimx, "px"); Inkscape::Util::Quantity rdimy_q = Inkscape::Util::Quantity(rdimy, "px"); - GString *xs = g_string_new(rdimx_q.string(desktop->namedview->doc_units).c_str()); - GString *ys = g_string_new(rdimy_q.string(desktop->namedview->doc_units).c_str()); + GString *xs = g_string_new(rdimx_q.string(desktop->namedview->display_units).c_str()); + GString *ys = g_string_new(rdimy_q.string(desktop->namedview->display_units).c_str()); if (state & GDK_CONTROL_MASK) { int ratio_x, ratio_y; diff --git a/src/ui/tools/rect-tool.h b/src/ui/tools/rect-tool.h index a50fd7b24..a22f1caa8 100644 --- a/src/ui/tools/rect-tool.h +++ b/src/ui/tools/rect-tool.h @@ -6,6 +6,7 @@ * * Author: * Lauris Kaplinski <lauris@kaplinski.com> + * Jon A. Cruz <jon@joncruz.org> * * Copyright (C) 2000 Lauris Kaplinski * Copyright (C) 2000-2001 Ximian, Inc. @@ -21,9 +22,6 @@ #include "sp-rect.h" -#define SP_RECT_CONTEXT(obj) (dynamic_cast<Inkscape::UI::Tools::RectTool*>((Inkscape::UI::Tools::ToolBase*)obj)) -#define SP_IS_RECT_CONTEXT(obj) (dynamic_cast<const Inkscape::UI::Tools::RectTool*>((const Inkscape::UI::Tools::ToolBase*)obj) != NULL) - namespace Inkscape { namespace UI { namespace Tools { diff --git a/src/ui/tools/spiral-tool.cpp b/src/ui/tools/spiral-tool.cpp index 18c3e4e2d..31c4e8829 100644 --- a/src/ui/tools/spiral-tool.cpp +++ b/src/ui/tools/spiral-tool.cpp @@ -395,7 +395,7 @@ void SpiralTool::drag(Geom::Point const &p, guint state) { /* status text */ Inkscape::Util::Quantity q = Inkscape::Util::Quantity(rad, "px"); - GString *rads = g_string_new(q.string(desktop->namedview->doc_units).c_str()); + GString *rads = g_string_new(q.string(desktop->namedview->display_units).c_str()); this->message_context->setF(Inkscape::IMMEDIATE_MESSAGE, _("<b>Spiral</b>: radius %s, angle %5g°; with <b>Ctrl</b> to snap angle"), rads->str, sp_round((arg + 2.0*M_PI*this->spiral->revo)*180/M_PI, 0.0001)); diff --git a/src/ui/tools/star-tool.cpp b/src/ui/tools/star-tool.cpp index 7604ba04e..b5544d263 100644 --- a/src/ui/tools/star-tool.cpp +++ b/src/ui/tools/star-tool.cpp @@ -411,7 +411,7 @@ void StarTool::drag(Geom::Point p, guint state) /* status text */ Inkscape::Util::Quantity q = Inkscape::Util::Quantity(r1, "px"); - GString *rads = g_string_new(q.string(desktop->namedview->doc_units).c_str()); + GString *rads = g_string_new(q.string(desktop->namedview->display_units).c_str()); this->message_context->setF(Inkscape::IMMEDIATE_MESSAGE, ( this->isflatsided? _("<b>Polygon</b>: radius %s, angle %5g°; with <b>Ctrl</b> to snap angle") diff --git a/src/ui/tools/text-tool.cpp b/src/ui/tools/text-tool.cpp index a72748733..578add843 100644 --- a/src/ui/tools/text-tool.cpp +++ b/src/ui/tools/text-tool.cpp @@ -590,8 +590,8 @@ bool TextTool::root_handler(GdkEvent* event) { // status text Inkscape::Util::Quantity x_q = Inkscape::Util::Quantity(fabs((p - this->p0)[Geom::X]), "px"); Inkscape::Util::Quantity y_q = Inkscape::Util::Quantity(fabs((p - this->p0)[Geom::Y]), "px"); - GString *xs = g_string_new(x_q.string(desktop->namedview->doc_units).c_str()); - GString *ys = g_string_new(y_q.string(desktop->namedview->doc_units).c_str()); + GString *xs = g_string_new(x_q.string(desktop->namedview->display_units).c_str()); + GString *ys = g_string_new(y_q.string(desktop->namedview->display_units).c_str()); this->message_context->setF(Inkscape::IMMEDIATE_MESSAGE, _("<b>Flowed text frame</b>: %s × %s"), xs->str, ys->str); g_string_free(xs, FALSE); diff --git a/src/ui/view/view.cpp b/src/ui/view/view.cpp index 72548e213..47e2a1e0d 100644 --- a/src/ui/view/view.cpp +++ b/src/ui/view/view.cpp @@ -20,7 +20,7 @@ #include "message-stack.h" #include "message-context.h" #include "verbs.h" -#include "inkscape-private.h" +#include "inkscape.h" namespace Inkscape { namespace UI { @@ -85,7 +85,7 @@ void View::_close() { if (_doc) { _document_uri_set_connection.disconnect(); _document_resized_connection.disconnect(); - if (inkscape_remove_document(_doc)) { + if (INKSCAPE.remove_document(_doc)) { // this was the last view of this document, so delete it delete _doc; } @@ -111,13 +111,13 @@ void View::setDocument(SPDocument *doc) { if (_doc) { _document_uri_set_connection.disconnect(); _document_resized_connection.disconnect(); - if (inkscape_remove_document(_doc)) { + if (INKSCAPE.remove_document(_doc)) { // this was the last view of this document, so delete it delete _doc; } } - inkscape_add_document(doc); + INKSCAPE.add_document(doc); _doc = doc; _document_uri_set_connection = diff --git a/src/ui/widget/dock.cpp b/src/ui/widget/dock.cpp index 52e9ea605..c5e14d4f0 100644 --- a/src/ui/widget/dock.cpp +++ b/src/ui/widget/dock.cpp @@ -119,8 +119,9 @@ Dock::Dock(Gtk::Orientation orientation) gdl_dock_bar_set_style(_gdl_dock_bar, gdl_dock_bar_style); - g_signal_connect(G_OBJECT(INKSCAPE), "dialogs_hide", G_CALLBACK(hideCallback), (void *)this); - g_signal_connect(G_OBJECT(INKSCAPE), "dialogs_unhide", G_CALLBACK(unhideCallback), (void *)this); + + INKSCAPE.signal_dialogs_hide.connect(sigc::mem_fun(*this, &Dock::hide)); + INKSCAPE.signal_dialogs_unhide.connect(sigc::mem_fun(*this, &Dock::show)); g_signal_connect(_paned->gobj(), "button-press-event", G_CALLBACK(_on_paned_button_event), (void *)this); g_signal_connect(_paned->gobj(), "button-release-event", G_CALLBACK(_on_paned_button_event), (void *)this); diff --git a/src/ui/widget/imageicon.cpp b/src/ui/widget/imageicon.cpp index 22abd04ba..df261b69a 100644 --- a/src/ui/widget/imageicon.cpp +++ b/src/ui/widget/imageicon.cpp @@ -88,8 +88,9 @@ ImageIcon::~ImageIcon() */ void ImageIcon::init() { - if (!INKSCAPE) - inkscape_application_init("",false); + // \FIXME Why? + if (!Inkscape::Application::exists()) + Inkscape::Application::create("", false); document = NULL; viewerGtkmm = NULL; //set_size_request(150,150); diff --git a/src/ui/widget/object-composite-settings.cpp b/src/ui/widget/object-composite-settings.cpp index e4cd76345..a377bf118 100644 --- a/src/ui/widget/object-composite-settings.cpp +++ b/src/ui/widget/object-composite-settings.cpp @@ -39,26 +39,6 @@ namespace Inkscape { namespace UI { namespace Widget { -/*void ObjectCompositeSettings::_on_desktop_activate( - InkscapeApplication *application, - SPDesktop *desktop, - ObjectCompositeSettings *w -) { - if (w->_subject) { - w->_subject->setDesktop(desktop); - } -} - -void ObjectCompositeSettings::_on_desktop_deactivate( - InkscapeApplication *application, - SPDesktop *desktop, - ObjectCompositeSettings *w -) { - if (w->_subject) { - w->_subject->setDesktop(NULL); - } -}*/ - ObjectCompositeSettings::ObjectCompositeSettings(unsigned int verb_code, char const *history_prefix, int flags) : _verb_code(verb_code), _blur_tag(Glib::ustring(history_prefix) + ":blur"), @@ -102,7 +82,6 @@ ObjectCompositeSettings::ObjectCompositeSettings(unsigned int verb_code, char co ObjectCompositeSettings::~ObjectCompositeSettings() { setSubject(NULL); - g_signal_handler_disconnect(G_OBJECT(INKSCAPE), _desktop_activated); } void ObjectCompositeSettings::setSubject(StyleSubject *subject) { diff --git a/src/ui/widget/object-composite-settings.h b/src/ui/widget/object-composite-settings.h index e375bf24a..5a723a2fd 100644 --- a/src/ui/widget/object-composite-settings.h +++ b/src/ui/widget/object-composite-settings.h @@ -66,8 +66,8 @@ private: gulong _desktop_activated; sigc::connection _subject_changed; - static void _on_desktop_activate(InkscapeApplication *application, SPDesktop *desktop, ObjectCompositeSettings *w); - static void _on_desktop_deactivate(InkscapeApplication *application, SPDesktop *desktop, ObjectCompositeSettings *w); + static void _on_desktop_activate(SPDesktop *desktop, ObjectCompositeSettings *w); + static void _on_desktop_deactivate(SPDesktop *desktop, ObjectCompositeSettings *w); void _subjectChanged(); void _blendBlurValueChanged(); void _opacityValueChanged(); diff --git a/src/ui/widget/page-sizer.cpp b/src/ui/widget/page-sizer.cpp index 89b0b8f7e..df464fbb0 100644 --- a/src/ui/widget/page-sizer.cpp +++ b/src/ui/widget/page-sizer.cpp @@ -311,10 +311,10 @@ PageSizer::PageSizer(Registry & _wr) SPDesktop *dt = SP_ACTIVE_DESKTOP; SPNamedView *nv = sp_desktop_namedview(dt); _wr.setUpdating (true); - if (nv->units) { - _dimensionUnits.setUnit(nv->units->abbr); - } else if (nv->doc_units) { - _dimensionUnits.setUnit(nv->doc_units->abbr); + if (nv->page_size_units) { + _dimensionUnits.setUnit(nv->page_size_units->abbr); + } else if (nv->display_units) { + _dimensionUnits.setUnit(nv->display_units->abbr); } _wr.setUpdating (false); @@ -459,7 +459,7 @@ PageSizer::init () * \param changeList whether to modify the paper size list */ void -PageSizer::setDim (Inkscape::Util::Quantity w, Inkscape::Util::Quantity h, bool changeList) +PageSizer::setDim (Inkscape::Util::Quantity w, Inkscape::Util::Quantity h, bool changeList, bool changeSize) { static bool _called = false; if (_called) { @@ -479,8 +479,8 @@ PageSizer::setDim (Inkscape::Util::Quantity w, Inkscape::Util::Quantity h, bool if (SP_ACTIVE_DESKTOP && !_widgetRegistry->isUpdating()) { SPDocument *doc = sp_desktop_document(SP_ACTIVE_DESKTOP); Inkscape::Util::Quantity const old_height = doc->getHeight(); - doc->setWidth (w); - doc->setHeight (h); + doc->setWidth (w, changeSize); + doc->setHeight (h, changeSize); // The origin for the user is in the lower left corner; this point should remain stationary when // changing the page size. The SVG's origin however is in the upper left corner, so we must compensate for this Geom::Translate const vert_offset(Geom::Point(0, (old_height.value("px") - h.value("px")))); @@ -717,7 +717,8 @@ PageSizer::on_units_changed() if (_widgetRegistry->isUpdating()) return; _unit = _dimensionUnits.getUnit()->abbr; setDim (Inkscape::Util::Quantity(_dimensionWidth.getValue(""), _dimensionUnits.getUnit()), - Inkscape::Util::Quantity(_dimensionHeight.getValue(""), _dimensionUnits.getUnit())); + Inkscape::Util::Quantity(_dimensionHeight.getValue(""), _dimensionUnits.getUnit()), + true, false); } } // namespace Widget diff --git a/src/ui/widget/page-sizer.h b/src/ui/widget/page-sizer.h index f4bcae4b6..bed117e5a 100644 --- a/src/ui/widget/page-sizer.h +++ b/src/ui/widget/page-sizer.h @@ -161,7 +161,7 @@ public: * Set the page size to the given dimensions. If 'changeList' is * true, then reset the paper size list to the closest match */ - void setDim (Inkscape::Util::Quantity w, Inkscape::Util::Quantity h, bool changeList=true); + void setDim (Inkscape::Util::Quantity w, Inkscape::Util::Quantity h, bool changeList=true, bool changeSize=true); /** * Updates the scalar widgets for the fit margins. (Just changes the value diff --git a/src/ui/widget/panel.cpp b/src/ui/widget/panel.cpp index 0abd81b16..c96eac838 100644 --- a/src/ui/widget/panel.cpp +++ b/src/ui/widget/panel.cpp @@ -293,7 +293,7 @@ void Panel::_init() signalResponse().connect(sigc::mem_fun(*this, &Panel::_handleResponse)); - signalActivateDesktop().connect(sigc::hide<0>(sigc::mem_fun(*this, &Panel::setDesktop))); + signalActivateDesktop().connect(sigc::mem_fun(*this, &Panel::setDesktop)); show_all_children(); @@ -643,13 +643,13 @@ Panel::signalDocumentReplaced() return _signal_document_replaced; } -sigc::signal<void, InkscapeApplication *, SPDesktop *> & +sigc::signal<void, SPDesktop *> & Panel::signalActivateDesktop() { return _signal_activate_desktop; } -sigc::signal<void, InkscapeApplication *, SPDesktop *> & +sigc::signal<void, SPDesktop *> & Panel::signalDeactiveDesktop() { return _signal_deactive_desktop; diff --git a/src/ui/widget/panel.h b/src/ui/widget/panel.h index 177314797..5680cac30 100644 --- a/src/ui/widget/panel.h +++ b/src/ui/widget/panel.h @@ -48,6 +48,7 @@ namespace Gtk { struct InkscapeApplication; namespace Inkscape { + class Selection; namespace UI { @@ -116,8 +117,8 @@ public: void setResponseSensitive(int response_id, bool setting); virtual sigc::signal<void, SPDesktop *, SPDocument *> &signalDocumentReplaced(); - virtual sigc::signal<void, InkscapeApplication *, SPDesktop *> &signalActivateDesktop(); - virtual sigc::signal<void, InkscapeApplication *, SPDesktop *> &signalDeactiveDesktop(); + virtual sigc::signal<void, SPDesktop *> &signalActivateDesktop(); + virtual sigc::signal<void, SPDesktop *> &signalDeactiveDesktop(); protected: /** @@ -147,8 +148,8 @@ protected: sigc::signal<void, int> _signal_response; sigc::signal<void> _signal_present; sigc::signal<void, SPDesktop *, SPDocument *> _signal_document_replaced; - sigc::signal<void, InkscapeApplication *, SPDesktop *> _signal_activate_desktop; - sigc::signal<void, InkscapeApplication *, SPDesktop *> _signal_deactive_desktop; + sigc::signal<void, SPDesktop *> _signal_activate_desktop; + sigc::signal<void, SPDesktop *> _signal_deactive_desktop; private: void _init(); diff --git a/src/ui/widget/selected-style.cpp b/src/ui/widget/selected-style.cpp index d22c59aa4..aebef2c4e 100644 --- a/src/ui/widget/selected-style.cpp +++ b/src/ui/widget/selected-style.cpp @@ -498,7 +498,7 @@ SelectedStyle::setDesktop(SPDesktop *desktop) this ) )); - _sw_unit = sp_desktop_namedview(desktop)->doc_units; + _sw_unit = sp_desktop_namedview(desktop)->display_units; // Set the doc default unit active in the units list gint length = g_slist_length(_unit_mis); diff --git a/src/util/units.cpp b/src/util/units.cpp index eb4a313e0..2c72ec3ae 100644 --- a/src/util/units.cpp +++ b/src/util/units.cpp @@ -16,11 +16,14 @@ #include <cmath> #include <cerrno> #include <iomanip> +#include <iostream> #include <glib.h> #include <glibmm/regex.h> #include <glibmm/fileutils.h> #include <glibmm/markup.h> +#include <2geom/coord.h> + #include "util/units.h" #include "path-prefix.h" #include "streq.h" @@ -44,6 +47,7 @@ enum UnitCode { UNIT_CODE_CM = MAKE_UNIT_CODE('c','m'), UNIT_CODE_IN = MAKE_UNIT_CODE('i','n'), UNIT_CODE_FT = MAKE_UNIT_CODE('f','t'), + UNIT_CODE_MT = MAKE_UNIT_CODE('m',' '), UNIT_CODE_EM = MAKE_UNIT_CODE('e','m'), UNIT_CODE_EX = MAKE_UNIT_CODE('e','x'), UNIT_CODE_PERCENT = MAKE_UNIT_CODE('%',0) @@ -71,6 +75,7 @@ unsigned const svg_length_lookup[] = { UNIT_CODE_CM, UNIT_CODE_IN, UNIT_CODE_FT, + UNIT_CODE_MT, UNIT_CODE_EM, UNIT_CODE_EX, UNIT_CODE_PERCENT @@ -206,7 +211,6 @@ bool Unit::compatibleWith(Unit const *u) const } bool Unit::compatibleWith(Glib::ustring const &u) const { - static UnitTable unit_table; return compatibleWith(unit_table.getUnit(u)); } @@ -280,6 +284,28 @@ Unit const *UnitTable::getUnit(SVGLength::Unit u) const return &_empty_unit; } +Unit const *UnitTable::findUnit(double factor, UnitType type) const +{ + const double eps = factor * 0.01; // allow for 1% deviation + + UnitCodeMap::const_iterator cit = _unit_map.begin(); + while (cit != _unit_map.end()) { + if (cit->second->type == type) { + if (Geom::are_near(cit->second->factor, factor, eps)) { + // unit found! + break; + } + } + ++cit; + } + + if (cit != _unit_map.end()) { + return cit->second; + } else { + return getUnit(_primary_unit[type]); + } +} + Quantity UnitTable::parseQuantity(Glib::ustring const &q) const { Glib::MatchInfo match_info; diff --git a/src/util/units.h b/src/util/units.h index efe1dbec7..13777fd1b 100644 --- a/src/util/units.h +++ b/src/util/units.h @@ -141,6 +141,9 @@ public: /** Retrieve a given unit based on its string identifier */ Unit const *getUnit(Glib::ustring const &name) const; Unit const *getUnit(char const *name) const; + + /** Try to find a unit based on its conversion factor to the primary */ + Unit const *findUnit(double factor, UnitType type) const; /** Retrieve a given unit based on its SVGLength unit */ Unit const *getUnit(SVGLength::Unit u) const; diff --git a/src/vanishing-point.cpp b/src/vanishing-point.cpp index 13dd03ee3..1ddba7bdb 100644 --- a/src/vanishing-point.cpp +++ b/src/vanishing-point.cpp @@ -94,7 +94,7 @@ vp_knot_moved_handler (SPKnot *knot, Geom::Point const &ppointer, guint state, g Geom::Point p = ppointer; // FIXME: take from prefs - double snap_dist = SNAP_DIST / inkscape_active_desktop()->current_zoom(); + double snap_dist = SNAP_DIST / SP_ACTIVE_DESKTOP->current_zoom(); /* * We use dragging_started to indicate if we have already checked for the need to split Draggers up. @@ -110,7 +110,7 @@ vp_knot_moved_handler (SPKnot *knot, Geom::Point const &ppointer, guint state, g for (std::set<VanishingPoint*, less_ptr>::iterator vp = sel_vps.begin(); vp != sel_vps.end(); ++vp) { // for each VP that has selected boxes: Persp3D *old_persp = (*vp)->get_perspective(); - sel_boxes = (*vp)->selectedBoxes(sp_desktop_selection(inkscape_active_desktop())); + sel_boxes = (*vp)->selectedBoxes(sp_desktop_selection(SP_ACTIVE_DESKTOP)); // we create a new perspective ... Persp3D *new_persp = persp3d_create_xml_element (dragger->parent->document, old_persp->perspective_impl); @@ -129,7 +129,7 @@ vp_knot_moved_handler (SPKnot *knot, Geom::Point const &ppointer, guint state, g } // FIXME: Do we need to create a new dragger as well? dragger->updateZOrders (); - DocumentUndo::done(sp_desktop_document (inkscape_active_desktop()), SP_VERB_CONTEXT_3DBOX, + DocumentUndo::done(sp_desktop_document (SP_ACTIVE_DESKTOP), SP_VERB_CONTEXT_3DBOX, _("Split vanishing points")); return; } @@ -174,7 +174,7 @@ vp_knot_moved_handler (SPKnot *knot, Geom::Point const &ppointer, guint state, g // deleted according to changes in the svg representation, not based on any user input // as is currently the case. - DocumentUndo::done(sp_desktop_document (inkscape_active_desktop()), SP_VERB_CONTEXT_3DBOX, + DocumentUndo::done(sp_desktop_document (SP_ACTIVE_DESKTOP), SP_VERB_CONTEXT_3DBOX, _("Merge vanishing points")); return; @@ -182,7 +182,7 @@ vp_knot_moved_handler (SPKnot *knot, Geom::Point const &ppointer, guint state, g } // We didn't snap to another dragger, so we'll try a regular snap - SPDesktop *desktop = inkscape_active_desktop(); + SPDesktop *desktop = SP_ACTIVE_DESKTOP; SnapManager &m = desktop->namedview->snap_manager; m.setup(desktop); Inkscape::SnappedPoint s = m.freeSnap(Inkscape::SnapCandidatePoint(p, Inkscape::SNAPSOURCE_OTHER_HANDLE)); @@ -277,7 +277,7 @@ VPDragger::VPDragger(VPDrag *parent, Geom::Point p, VanishingPoint &vp) if (vp.is_finite()) { // create the knot - this->knot = new SPKnot(inkscape_active_desktop(), NULL); + this->knot = new SPKnot(SP_ACTIVE_DESKTOP, NULL); this->knot->setMode(SP_KNOT_MODE_XOR); this->knot->setFill(VP_KNOT_COLOR_NORMAL, VP_KNOT_COLOR_NORMAL, VP_KNOT_COLOR_NORMAL); this->knot->setStroke(0x000000ff, 0x000000ff, 0x000000ff); @@ -394,7 +394,7 @@ VPDragger::VPsOfSelectedBoxes() { std::set<VanishingPoint*, less_ptr> sel_vps; VanishingPoint *vp; // FIXME: Should we take the selection from the parent VPDrag? I guess it shouldn't make a difference. - Inkscape::Selection *sel = sp_desktop_selection(inkscape_active_desktop()); + Inkscape::Selection *sel = sp_desktop_selection(SP_ACTIVE_DESKTOP); for (GSList const* i = sel->itemList(); i != NULL; i = i->next) { SPItem *item = static_cast<SPItem *>(i->data); SPBox3D *box = dynamic_cast<SPBox3D *>(item); @@ -488,7 +488,7 @@ VPDragger::printVPs() { VPDrag::VPDrag (SPDocument *document) { this->document = document; - this->selection = sp_desktop_selection(inkscape_active_desktop()); + this->selection = sp_desktop_selection(SP_ACTIVE_DESKTOP); this->draggers = NULL; this->lines = NULL; @@ -635,7 +635,7 @@ VPDrag::updateBoxHandles () return; } - Inkscape::UI::Tools::ToolBase *ec = inkscape_active_event_context(); + Inkscape::UI::Tools::ToolBase *ec = INKSCAPE.active_event_context(); g_assert (ec != NULL); if (ec->shape_editor != NULL) { ec->shape_editor->update_knotholder(); @@ -708,7 +708,7 @@ void VPDrag::drawLinesForFace(const SPBox3D *box, Proj::Axis axis) //, guint cor // draw perspective lines for infinite VPs boost::optional<Geom::Point> pt1, pt2, pt3, pt4; Persp3D *persp = box3d_get_perspective(box); - SPDesktop *desktop = inkscape_active_desktop (); // FIXME: Store the desktop in VPDrag + SPDesktop *desktop = SP_ACTIVE_DESKTOP; // FIXME: Store the desktop in VPDrag Box3D::PerspectiveLine pl (corner1, axis, persp); pt1 = pl.intersection_with_viewbox(desktop); @@ -782,7 +782,7 @@ VPDrag::swap_perspectives_of_VPs(Persp3D *persp2, Persp3D *persp1) void VPDrag::addLine(Geom::Point const &p1, Geom::Point const &p2, Inkscape::CtrlLineType type) { - SPCtrlLine *line = ControlManager::getManager().createControlLine(sp_desktop_controls(inkscape_active_desktop()), p1, p2, type); + SPCtrlLine *line = ControlManager::getManager().createControlLine(sp_desktop_controls(SP_ACTIVE_DESKTOP), p1, p2, type); sp_canvas_item_show(line); this->lines = g_slist_append(this->lines, line); } diff --git a/src/verbs.cpp b/src/verbs.cpp index b4743751e..bafb6f89b 100644 --- a/src/verbs.cpp +++ b/src/verbs.cpp @@ -52,7 +52,7 @@ #include "helper/action.h" #include "helper/action-context.h" #include "help.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "ui/interface.h" #include "layer-fns.h" #include "layer-manager.h" @@ -906,10 +906,10 @@ void FileVerb::perform(SPAction *action, void *data) // sp_file_export_to_ocal(*parent); // break; case SP_VERB_FILE_NEXT_DESKTOP: - inkscape_switch_desktops_next(); + INKSCAPE.switch_desktops_next(); break; case SP_VERB_FILE_PREV_DESKTOP: - inkscape_switch_desktops_prev(); + INKSCAPE.switch_desktops_prev(); break; case SP_VERB_FILE_CLOSE_VIEW: sp_ui_close_view(NULL); @@ -1203,11 +1203,11 @@ void SelectionVerb::perform(SPAction *action, void *data) SelectionHelper::reverse(dt); break; case SP_VERB_SELECTION_TRACE: - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); dt->_dlg_mgr->showDialog("Trace"); break; case SP_VERB_SELECTION_PIXEL_ART: - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); dt->_dlg_mgr->showDialog("PixelArt"); break; case SP_VERB_SELECTION_CREATE_BITMAP: @@ -1221,7 +1221,7 @@ void SelectionVerb::perform(SPAction *action, void *data) sp_selected_path_break_apart(dt); break; case SP_VERB_SELECTION_ARRANGE: - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); dt->_dlg_mgr->showDialog("TileDialog"); //FIXME: denis: What's this string (to be changed) break; default: @@ -1860,7 +1860,7 @@ void ZoomVerb::perform(SPAction *action, void *data) double zcorr = 1.0; Glib::ustring abbr = prefs->getString("/options/zoomcorrection/unit"); - if (dt->namedview->doc_units && dt->namedview->doc_units->abbr == abbr) + if (dt->namedview->display_units && (dt->namedview->display_units->abbr == abbr)) zcorr = prefs->getDouble("/options/zoomcorrection/value", 1.0); Geom::Rect const d = dt->get_display_area(); @@ -2006,7 +2006,7 @@ void ZoomVerb::perform(SPAction *action, void *data) dt->toggleColorProfAdjust(); break; case SP_VERB_VIEW_ICON_PREVIEW: - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); dt->_dlg_mgr->showDialog("IconPreviewPanel"); break; @@ -2025,7 +2025,7 @@ void DialogVerb::perform(SPAction *action, void *data) { if (reinterpret_cast<std::size_t>(data) != SP_VERB_DIALOG_TOGGLE) { // unhide all when opening a new dialog - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); } g_return_if_fail(ensure_desktop_valid(action)); @@ -2088,7 +2088,7 @@ void DialogVerb::perform(SPAction *action, void *data) dt->_dlg_mgr->showDialog("UndoHistory"); break; case SP_VERB_DIALOG_TOGGLE: - inkscape_dialogs_toggle(); + INKSCAPE.dialogs_toggle(); break; case SP_VERB_DIALOG_CLONETILER: //clonetiler_dialog(); @@ -2166,7 +2166,7 @@ void HelpVerb::perform(SPAction *action, void *data) */ case SP_VERB_HELP_MEMORY: - inkscape_dialogs_unhide(); + INKSCAPE.dialogs_unhide(); dt->_dlg_mgr->showDialog("Memory"); break; default: diff --git a/src/widgets/box3d-toolbar.cpp b/src/widgets/box3d-toolbar.cpp index 02d102a11..4cc2976f8 100644 --- a/src/widgets/box3d-toolbar.cpp +++ b/src/widgets/box3d-toolbar.cpp @@ -195,7 +195,7 @@ static void box3d_toolbox_selection_changed(Inkscape::Selection *selection, GObj sp_repr_synthesize_events(persp_repr, &box3d_persp_tb_repr_events, tbl); } - inkscape_active_document()->setCurrentPersp3D(persp3d_get_from_repr(persp_repr)); + SP_ACTIVE_DOCUMENT->setCurrentPersp3D(persp3d_get_from_repr(persp_repr)); Inkscape::Preferences *prefs = Inkscape::Preferences::get(); prefs->setString("/tools/shapes/3dbox/persp", persp_repr->attribute("id")); @@ -255,7 +255,7 @@ static void box3d_angle_z_value_changed(GtkAdjustment *adj, GObject *dataKludge) static void box3d_vp_state_changed( GtkToggleAction *act, GtkAction * /*box3d_angle*/, Proj::Axis axis ) { // TODO: Take all selected perspectives into account - std::list<Persp3D *> sel_persps = sp_desktop_selection(inkscape_active_desktop())->perspList(); + std::list<Persp3D *> sel_persps = sp_desktop_selection(SP_ACTIVE_DESKTOP)->perspList(); if (sel_persps.empty()) { // this can happen when the document is created; we silently ignore it return; diff --git a/src/widgets/desktop-widget.cpp b/src/widgets/desktop-widget.cpp index 9c8dac7dc..e117e7f60 100644 --- a/src/widgets/desktop-widget.cpp +++ b/src/widgets/desktop-widget.cpp @@ -45,7 +45,7 @@ #include "helper/action-context.h" #include "util/units.h" #include "ui/widget/unit-tracker.h" -#include "inkscape-private.h" +#include "inkscape.h" #include "ui/interface.h" #include "macros.h" #include "preferences.h" @@ -795,7 +795,7 @@ static void sp_desktop_widget_dispose(GObject *object) dtw->layer_selector->setDesktop(NULL); dtw->layer_selector->unreference(); - inkscape_remove_desktop (dtw->desktop); // clears selection too + INKSCAPE.remove_desktop (dtw->desktop); // clears selection too dtw->modified_connection.disconnect(); dtw->desktop->destroy(); Inkscape::GC::release (dtw->desktop); @@ -1091,7 +1091,7 @@ SPDesktopWidget::shutdown() { g_assert(desktop != NULL); - if (inkscape_is_sole_desktop_for_document(*desktop)) { + if (INKSCAPE.sole_desktop_for_document(*desktop)) { SPDocument *doc = desktop->doc(); if (doc->isModifiedSinceSave()) { GtkWidget *dialog; @@ -1665,14 +1665,14 @@ SPDesktopWidget* SPDesktopWidget::createInstance(SPNamedView *namedview) { SPDesktopWidget *dtw = static_cast<SPDesktopWidget*>(g_object_new(SP_TYPE_DESKTOP_WIDGET, NULL)); - dtw->dt2r = 1. / namedview->doc_units->factor; + dtw->dt2r = 1. / namedview->display_units->factor; dtw->ruler_origin = Geom::Point(0,0); //namedview->gridorigin; Why was the grid origin used here? dtw->desktop = new SPDesktop(); dtw->stub = new SPDesktopWidget::WidgetStub (dtw); dtw->desktop->init (namedview, dtw->canvas, dtw->stub); - inkscape_add_desktop (dtw->desktop); + INKSCAPE.add_desktop (dtw->desktop); // Add the shape geometry to libavoid for autorouting connectors. // This needs desktop set for its spacing preferences. @@ -1737,11 +1737,11 @@ void SPDesktopWidget::namedviewModified(SPObject *obj, guint flags) SPNamedView *nv=SP_NAMEDVIEW(obj); if (flags & SP_OBJECT_MODIFIED_FLAG) { - this->dt2r = 1. / nv->doc_units->factor; + this->dt2r = 1. / nv->display_units->factor; this->ruler_origin = Geom::Point(0,0); //nv->gridorigin; Why was the grid origin used here? - sp_ruler_set_unit(SP_RULER (this->vruler), nv->getDefaultUnit()); - sp_ruler_set_unit(SP_RULER (this->hruler), nv->getDefaultUnit()); + sp_ruler_set_unit(SP_RULER (this->vruler), nv->getDisplayUnit()); + sp_ruler_set_unit(SP_RULER (this->hruler), nv->getDisplayUnit()); /* This loops through all the grandchildren of aux toolbox, * and for each that it finds, it performs an sp_search_by_data_recursive(), @@ -1771,14 +1771,14 @@ void SPDesktopWidget::namedviewModified(SPObject *obj, guint flags) if (tracker == NULL) // it's null when inkscape is first opened continue; - tracker->setActiveUnit( nv->doc_units ); + tracker->setActiveUnit( nv->display_units ); } // grandchildren } // if child is a container } // children } // if aux_toolbox is a container - gtk_widget_set_tooltip_text(this->hruler_box, gettext(nv->doc_units->name_plural.c_str())); - gtk_widget_set_tooltip_text(this->vruler_box, gettext(nv->doc_units->name_plural.c_str())); + gtk_widget_set_tooltip_text(this->hruler_box, gettext(nv->display_units->name_plural.c_str())); + gtk_widget_set_tooltip_text(this->vruler_box, gettext(nv->display_units->name_plural.c_str())); sp_desktop_widget_update_rulers(this); ToolboxFactory::updateSnapToolbox(this->desktop, 0, this->snap_toolbox); @@ -1818,7 +1818,7 @@ bool SPDesktopWidget::onFocusInEvent(GdkEventFocus*) } } - inkscape_activate_desktop (desktop); + INKSCAPE.activate_desktop (desktop); return false; } diff --git a/src/widgets/gradient-vector.cpp b/src/widgets/gradient-vector.cpp index 6607c90d2..d2c46ffec 100644 --- a/src/widgets/gradient-vector.cpp +++ b/src/widgets/gradient-vector.cpp @@ -1012,13 +1012,28 @@ GtkWidget * sp_gradient_vector_editor_new(SPGradient *gradient, SPStop *stop) sp_transientize(dlg); wd.win = dlg; wd.stop = 0; - g_signal_connect(G_OBJECT(INKSCAPE), "activate_desktop", G_CALLBACK(sp_transientize_callback), &wd); - g_signal_connect(G_OBJECT(dlg), "event", G_CALLBACK(sp_dialog_event_handler), dlg); - g_signal_connect(G_OBJECT(dlg), "destroy", G_CALLBACK(sp_gradient_vector_dialog_destroy), dlg); - g_signal_connect(G_OBJECT(dlg), "delete_event", G_CALLBACK(sp_gradient_vector_dialog_delete), dlg); - g_signal_connect(G_OBJECT(INKSCAPE), "shut_down", G_CALLBACK(sp_gradient_vector_dialog_delete), dlg); - g_signal_connect( G_OBJECT(INKSCAPE), "dialogs_hide", G_CALLBACK(sp_dialog_hide), dlg ); - g_signal_connect( G_OBJECT(INKSCAPE), "dialogs_unhide", G_CALLBACK(sp_dialog_unhide), dlg ); + + GObject *obj = G_OBJECT(dlg); + sigc::connection *conn = NULL; + + conn = new sigc::connection(INKSCAPE.signal_activate_desktop.connect(sigc::bind(sigc::ptr_fun(&sp_transientize_callback), &wd))); + g_object_set_data(obj, "desktop-activate-connection", conn); + + g_signal_connect(obj, "event", G_CALLBACK(sp_dialog_event_handler), dlg); + g_signal_connect(obj, "destroy", G_CALLBACK(sp_gradient_vector_dialog_destroy), dlg); + g_signal_connect(obj, "delete_event", G_CALLBACK(sp_gradient_vector_dialog_delete), dlg); + + conn = new sigc::connection(INKSCAPE.signal_shut_down.connect( + sigc::hide_return( + sigc::bind(sigc::ptr_fun(&sp_gradient_vector_dialog_delete), (GtkWidget *) NULL, (GdkEvent *) NULL, (GtkWidget *) NULL) + ))); + g_object_set_data(obj, "shutdown-connection", conn); + + conn = new sigc::connection(INKSCAPE.signal_dialogs_hide.connect(sigc::bind(sigc::ptr_fun(>k_widget_hide), dlg))); + g_object_set_data(obj, "dialog-hide-connection", conn); + + conn = new sigc::connection(INKSCAPE.signal_dialogs_unhide.connect(sigc::bind(sigc::ptr_fun(>k_widget_show), dlg))); + g_object_set_data(obj, "dialog-unhide-connection", conn); gtk_container_set_border_width(GTK_CONTAINER(dlg), PAD); @@ -1141,7 +1156,29 @@ static void sp_gradient_vector_dialog_destroy(GtkWidget * /*object*/, gpointer / static void sp_gradient_vector_dialog_destroy(GtkObject * /*object*/, gpointer /*data*/) #endif { - sp_signal_disconnect_by_data(INKSCAPE, dlg); + GObject *obj = G_OBJECT(dlg); + assert(obj != NULL); + + sigc::connection *conn = static_cast<sigc::connection *>(g_object_get_data(obj, "desktop-activate-connection")); + assert(conn != NULL); + conn->disconnect(); + delete conn; + + conn = static_cast<sigc::connection *>(g_object_get_data(obj, "shutdown-connection")); + assert(conn != NULL); + conn->disconnect(); + delete conn; + + conn = static_cast<sigc::connection *>(g_object_get_data(obj, "dialog-hide-connection")); + assert(conn != NULL); + conn->disconnect(); + delete conn; + + conn = static_cast<sigc::connection *>(g_object_get_data(obj, "dialog-unhide-connection")); + assert(conn != NULL); + conn->disconnect(); + delete conn; + wd.win = dlg = NULL; wd.stop = 0; } diff --git a/src/widgets/icon.cpp b/src/widgets/icon.cpp index a6e53d638..afc4fcfb0 100644 --- a/src/widgets/icon.cpp +++ b/src/widgets/icon.cpp @@ -1261,7 +1261,7 @@ std::list<gchar*> &IconImpl::icons_svg_paths() static bool initialized = false; if (!initialized) { // Fall back from user prefs dir into system locations. - gchar *userdir = profile_path("icons"); + gchar *userdir = Inkscape::Application::profile_path("icons"); sources.push_back(g_build_filename(userdir,"icons.svg", NULL)); sources.push_back(g_build_filename(INKSCAPE_PIXMAPDIR, "icons.svg", NULL)); g_free(userdir); @@ -1572,7 +1572,7 @@ void IconImpl::addPreRender( GtkIconSize lsize, gchar const *name ) } gboolean IconImpl::prerenderTask(gpointer /*data*/) { - if ( inkscapeIsCrashing() ) { + if ( Inkscape::Application::isCrashing() ) { // stop } else if (!pendingRenders.empty()) { bool workDone = false; @@ -1584,7 +1584,7 @@ gboolean IconImpl::prerenderTask(gpointer /*data*/) { } while (!pendingRenders.empty() && !workDone); } - if (!inkscapeIsCrashing() && !pendingRenders.empty()) { + if (!Inkscape::Application::isCrashing() && !pendingRenders.empty()) { return TRUE; } else { callbackHooked = false; diff --git a/src/widgets/lpe-toolbar.cpp b/src/widgets/lpe-toolbar.cpp index a85f3ae78..c6da46956 100644 --- a/src/widgets/lpe-toolbar.cpp +++ b/src/widgets/lpe-toolbar.cpp @@ -280,7 +280,7 @@ static void lpetool_toolbox_watch_ec(SPDesktop* dt, Inkscape::UI::Tools::ToolBas void sp_lpetool_toolbox_prep(SPDesktop *desktop, GtkActionGroup* mainActions, GObject* holder) { UnitTracker* tracker = new UnitTracker(Inkscape::Util::UNIT_TYPE_LINEAR); - tracker->setActiveUnit(sp_desktop_namedview(desktop)->doc_units); + tracker->setActiveUnit(sp_desktop_namedview(desktop)->display_units); g_object_set_data(holder, "tracker", tracker); Unit const *unit = tracker->getActiveUnit(); g_return_if_fail(unit != NULL); diff --git a/src/widgets/node-toolbar.cpp b/src/widgets/node-toolbar.cpp index 467325d08..1224ab355 100644 --- a/src/widgets/node-toolbar.cpp +++ b/src/widgets/node-toolbar.cpp @@ -330,7 +330,7 @@ static void node_toolbox_watch_ec(SPDesktop* dt, Inkscape::UI::Tools::ToolBase* void sp_node_toolbox_prep(SPDesktop *desktop, GtkActionGroup* mainActions, GObject* holder) { UnitTracker* tracker = new UnitTracker(Inkscape::Util::UNIT_TYPE_LINEAR); - Unit doc_units = *sp_desktop_namedview(desktop)->doc_units; + Unit doc_units = *sp_desktop_namedview(desktop)->display_units; tracker->setActiveUnit(&doc_units); g_object_set_data( holder, "tracker", tracker ); diff --git a/src/widgets/rect-toolbar.cpp b/src/widgets/rect-toolbar.cpp index e1ce01eaf..5356ebb0d 100644 --- a/src/widgets/rect-toolbar.cpp +++ b/src/widgets/rect-toolbar.cpp @@ -109,7 +109,7 @@ static void sp_rtb_value_changed(GtkAdjustment *adj, GObject *tbl, gchar const * for (GSList const *items = selection->itemList(); items != NULL; items = items->next) { if (SP_IS_RECT(items->data)) { if (gtk_adjustment_get_value(adj) != 0) { - (SP_RECT(items->data)->*setter)(Quantity::convert(gtk_adjustment_get_value(adj), unit, sp_desktop_namedview(desktop)->doc_units)); + (SP_RECT(items->data)->*setter)(Quantity::convert(gtk_adjustment_get_value(adj), unit, sp_desktop_namedview(desktop)->svg_units)); } else { SP_OBJECT(items->data)->getRepr()->setAttribute(value_name, NULL); } @@ -181,7 +181,7 @@ static void rect_tb_event_attr_changed(Inkscape::XML::Node * /*repr*/, gchar con UnitTracker* tracker = reinterpret_cast<UnitTracker*>( g_object_get_data( tbl, "tracker" ) ); Unit const *unit = tracker->getActiveUnit(); - Unit const *doc_unit = sp_desktop_namedview(SP_ACTIVE_DESKTOP)->doc_units; + Unit const *svg_unit = sp_desktop_namedview(SP_ACTIVE_DESKTOP)->svg_units; g_return_if_fail(unit != NULL); gpointer item = g_object_get_data( tbl, "item" ); @@ -190,28 +190,28 @@ static void rect_tb_event_attr_changed(Inkscape::XML::Node * /*repr*/, gchar con GtkAdjustment *adj = GTK_ADJUSTMENT( g_object_get_data( tbl, "rx" ) ); gdouble rx = SP_RECT(item)->getVisibleRx(); - gtk_adjustment_set_value(adj, Quantity::convert(rx, doc_unit, unit)); + gtk_adjustment_set_value(adj, Quantity::convert(rx, svg_unit, unit)); } { GtkAdjustment *adj = GTK_ADJUSTMENT( g_object_get_data( tbl, "ry" ) ); gdouble ry = SP_RECT(item)->getVisibleRy(); - gtk_adjustment_set_value(adj, Quantity::convert(ry, doc_unit, unit)); + gtk_adjustment_set_value(adj, Quantity::convert(ry, svg_unit, unit)); } { GtkAdjustment *adj = GTK_ADJUSTMENT( g_object_get_data( tbl, "width" ) ); gdouble width = SP_RECT(item)->getVisibleWidth(); - gtk_adjustment_set_value(adj, Quantity::convert(width, doc_unit, unit)); + gtk_adjustment_set_value(adj, Quantity::convert(width, svg_unit, unit)); } { GtkAdjustment *adj = GTK_ADJUSTMENT( g_object_get_data( tbl, "height" ) ); gdouble height = SP_RECT(item)->getVisibleHeight(); - gtk_adjustment_set_value(adj, Quantity::convert(height, doc_unit, unit)); + gtk_adjustment_set_value(adj, Quantity::convert(height, svg_unit, unit)); } } @@ -307,7 +307,7 @@ void sp_rect_toolbox_prep(SPDesktop *desktop, GtkActionGroup* mainActions, GObje UnitTracker* tracker = new UnitTracker(Inkscape::Util::UNIT_TYPE_LINEAR); //tracker->addUnit( SP_UNIT_PERCENT, 0 ); // fixme: add % meaning per cent of the width/height - tracker->setActiveUnit( sp_desktop_namedview(desktop)->doc_units ); + tracker->setActiveUnit( sp_desktop_namedview(desktop)->display_units ); g_object_set_data( holder, "tracker", tracker ); /* W */ @@ -404,7 +404,8 @@ static void rect_toolbox_watch_ec(SPDesktop* desktop, Inkscape::UI::Tools::ToolB { static sigc::connection changed; - if (SP_IS_RECT_CONTEXT(ec)) { + // TODO fixme: use of dynamic_cast<> seems wrong here. + if (dynamic_cast<Inkscape::UI::Tools::RectTool *>(ec)) { changed = sp_desktop_selection(desktop)->connectChanged(sigc::bind(sigc::ptr_fun(sp_rect_toolbox_selection_changed), holder)); } else { if (changed) diff --git a/src/widgets/select-toolbar.cpp b/src/widgets/select-toolbar.cpp index 08a46354e..e59d459b9 100644 --- a/src/widgets/select-toolbar.cpp +++ b/src/widgets/select-toolbar.cpp @@ -470,7 +470,7 @@ void sp_select_toolbox_prep(SPDesktop *desktop, GtkActionGroup* mainActions, GOb contextActions->push_back( act ); // Create the parent widget for x y w h tracker. - GtkWidget *spw = sp_widget_new_global(INKSCAPE); + GtkWidget *spw = sp_widget_new_global(); // Remember the desktop's canvas widget, to be used for defocusing. g_object_set_data(G_OBJECT(spw), "dtw", sp_desktop_canvas(desktop)); @@ -488,7 +488,7 @@ void sp_select_toolbox_prep(SPDesktop *desktop, GtkActionGroup* mainActions, GOb // Create the units menu. UnitTracker* tracker = new UnitTracker(Inkscape::Util::UNIT_TYPE_LINEAR); tracker->addUnit(unit_table.getUnit("%")); - tracker->setActiveUnit( sp_desktop_namedview(desktop)->doc_units ); + tracker->setActiveUnit( sp_desktop_namedview(desktop)->display_units ); g_object_set_data( G_OBJECT(spw), "tracker", tracker ); g_signal_connect( G_OBJECT(spw), "destroy", G_CALLBACK(destroy_tracker), spw ); diff --git a/src/widgets/sp-widget.cpp b/src/widgets/sp-widget.cpp index fdf5ec500..5ab6b1bb5 100644 --- a/src/widgets/sp-widget.cpp +++ b/src/widgets/sp-widget.cpp @@ -15,6 +15,7 @@ #include "macros.h" #include "document.h" +#include "inkscape.h" #include "sp-widget.h" #include "helper/sp-marshal.h" @@ -55,15 +56,15 @@ public: #endif static void sizeAllocate(GtkWidget *widget, GtkAllocation *allocation); - static void modifySelectionCB(Application *inkscape, Selection *selection, guint flags, SPWidget *spw); - static void changeSelectionCB(Application *inkscape, Selection *selection, SPWidget *spw); - static void setSelectionCB(Application *inkscape, Selection *selection, SPWidget *spw); + static void modifySelectionCB(Selection *selection, guint flags, SPWidget *spw); + static void changeSelectionCB(Selection *selection, SPWidget *spw); + static void setSelectionCB(Selection *selection, SPWidget *spw); - static GtkWidget *constructGlobal(SPWidget *spw, InkscapeApplication *inkscape); + static GtkWidget *constructGlobal(SPWidget *spw); - void modifySelection(Application *inkscape, Selection *selection, guint flags); - void changeSelection(Application *inkscape, Selection *selection); - void setSelection(Application *inkscape, Selection *selection); + void modifySelection(Selection *selection, guint flags); + void changeSelection(Selection *selection); + void setSelection(Selection *selection); private: SPWidget &_target; @@ -132,7 +133,6 @@ sp_widget_class_init(SPWidgetClass *klass) static void sp_widget_init(SPWidget *spw) { - spw->inkscape = NULL; spw->_impl = new SPWidgetImpl(*spw); // ctor invoked after all other init } @@ -151,16 +151,12 @@ void SPWidgetImpl::dispose(GObject *object) { SPWidget *spw = reinterpret_cast<SPWidget *>(object); - if (spw->inkscape) { - // Disconnect signals - - // the checks are necessary because when destroy is caused by the program shutting down, - // the inkscape object may already be (partly?) invalid --bb - if (G_IS_OBJECT(spw->inkscape) && G_OBJECT_GET_CLASS(spw->inkscape)) { - sp_signal_disconnect_by_data(spw->inkscape, spw); - } - spw->inkscape = NULL; - } + // Disconnect signals + if (Application::exists()) { + spw->selModified.disconnect(); + spw->selChanged.disconnect(); + spw->selSet.disconnect(); + } delete spw->_impl; spw->_impl = 0; @@ -174,11 +170,20 @@ void SPWidgetImpl::show(GtkWidget *widget) { SPWidget *spw = SP_WIDGET(widget); - if (spw->inkscape) { + if (Application::exists()) { // Connect signals - g_signal_connect(spw->inkscape, "modify_selection", G_CALLBACK(SPWidgetImpl::modifySelectionCB), spw); - g_signal_connect(spw->inkscape, "change_selection", G_CALLBACK(SPWidgetImpl::changeSelectionCB), spw); - g_signal_connect(spw->inkscape, "set_selection", G_CALLBACK(SPWidgetImpl::setSelectionCB), spw); + spw->selModified = INKSCAPE.signal_selection_modified.connect( + sigc::bind( + sigc::ptr_fun(SPWidgetImpl::modifySelectionCB), spw) + ); + spw->selChanged = INKSCAPE.signal_selection_changed.connect( + sigc::bind( + sigc::ptr_fun(SPWidgetImpl::changeSelectionCB), spw) + ); + spw->selSet = INKSCAPE.signal_selection_set.connect( + sigc::bind( + sigc::ptr_fun(SPWidgetImpl::setSelectionCB), spw) + ); } if (GTK_WIDGET_CLASS(sp_widget_parent_class)->show) { @@ -190,9 +195,11 @@ void SPWidgetImpl::hide(GtkWidget *widget) { SPWidget *spw = SP_WIDGET (widget); - if (spw->inkscape) { + if (Application::exists()) { // Disconnect signals - sp_signal_disconnect_by_data(spw->inkscape, spw); + spw->selModified.disconnect(); + spw->selChanged.disconnect(); + spw->selSet.disconnect(); } if (GTK_WIDGET_CLASS(sp_widget_parent_class)->hide) { @@ -264,15 +271,21 @@ void SPWidgetImpl::sizeAllocate(GtkWidget *widget, GtkAllocation *allocation) } } -GtkWidget *SPWidgetImpl::constructGlobal(SPWidget *spw, InkscapeApplication *inkscape) +GtkWidget *SPWidgetImpl::constructGlobal(SPWidget *spw) { - g_return_val_if_fail(!spw->inkscape, NULL); - - spw->inkscape = inkscape; if (gtk_widget_get_visible(GTK_WIDGET(spw))) { - g_signal_connect(inkscape, "modify_selection", G_CALLBACK(SPWidgetImpl::modifySelectionCB), spw); - g_signal_connect(inkscape, "change_selection", G_CALLBACK(SPWidgetImpl::changeSelectionCB), spw); - g_signal_connect(inkscape, "set_selection", G_CALLBACK(SPWidgetImpl::setSelectionCB), spw); + spw->selModified = INKSCAPE.signal_selection_modified.connect( + sigc::bind( + sigc::ptr_fun(SPWidgetImpl::modifySelectionCB), spw) + ); + spw->selChanged = INKSCAPE.signal_selection_changed.connect( + sigc::bind( + sigc::ptr_fun(SPWidgetImpl::changeSelectionCB), spw) + ); + spw->selSet = INKSCAPE.signal_selection_set.connect( + sigc::bind( + sigc::ptr_fun(SPWidgetImpl::setSelectionCB), spw) + ); } g_signal_emit(spw, signals[CONSTRUCT], 0); @@ -280,32 +293,32 @@ GtkWidget *SPWidgetImpl::constructGlobal(SPWidget *spw, InkscapeApplication *ink return GTK_WIDGET(spw); } -void SPWidgetImpl::modifySelectionCB(Application *inkscape, Selection *selection, guint flags, SPWidget *spw) +void SPWidgetImpl::modifySelectionCB(Selection *selection, guint flags, SPWidget *spw) { - spw->_impl->modifySelection(inkscape, selection, flags); + spw->_impl->modifySelection(selection, flags); } -void SPWidgetImpl::changeSelectionCB(Application *inkscape, Selection *selection, SPWidget *spw) +void SPWidgetImpl::changeSelectionCB(Selection *selection, SPWidget *spw) { - spw->_impl->changeSelection(inkscape, selection); + spw->_impl->changeSelection(selection); } -void SPWidgetImpl::setSelectionCB(Application *inkscape, Selection *selection, SPWidget *spw) +void SPWidgetImpl::setSelectionCB(Selection *selection, SPWidget *spw) { - spw->_impl->setSelection(inkscape, selection); + spw->_impl->setSelection(selection); } -void SPWidgetImpl::modifySelection(Application * /*inkscape*/, Selection *selection, guint flags) +void SPWidgetImpl::modifySelection(Selection *selection, guint flags) { g_signal_emit(&_target, signals[MODIFY_SELECTION], 0, selection, flags); } -void SPWidgetImpl::changeSelection(Application * /*inkscape*/, Selection *selection) +void SPWidgetImpl::changeSelection(Selection *selection) { g_signal_emit(&_target, signals[CHANGE_SELECTION], 0, selection); } -void SPWidgetImpl::setSelection(Application * /*inkscape*/, Selection *selection) +void SPWidgetImpl::setSelection(Selection *selection) { // Emit "set_selection" signal g_signal_emit(&_target, signals[SET_SELECTION], 0, selection); @@ -316,11 +329,11 @@ void SPWidgetImpl::setSelection(Application * /*inkscape*/, Selection *selection // Methods -GtkWidget *sp_widget_new_global(InkscapeApplication *inkscape) +GtkWidget *sp_widget_new_global() { SPWidget *spw = reinterpret_cast<SPWidget*>(g_object_new(SP_TYPE_WIDGET, NULL)); - if (!SPWidgetImpl::constructGlobal(spw, inkscape)) { + if (!SPWidgetImpl::constructGlobal(spw)) { g_object_unref(spw); spw = 0; } diff --git a/src/widgets/sp-widget.h b/src/widgets/sp-widget.h index 6227c3a72..a53062cf4 100644 --- a/src/widgets/sp-widget.h +++ b/src/widgets/sp-widget.h @@ -16,6 +16,7 @@ */ #include <gtk/gtk.h> +#include "inkscape.h" #define SP_TYPE_WIDGET (sp_widget_get_type()) #define SP_WIDGET(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), SP_TYPE_WIDGET, SPWidget)) @@ -23,9 +24,8 @@ #define SP_IS_WIDGET(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), SP_TYPE_WIDGET)) #define SP_IS_WIDGET_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), SP_TYPE_WIDGET)) -struct InkscapeApplication; - namespace Inkscape { + class Selection; class SPWidgetImpl; } @@ -33,10 +33,15 @@ class SPWidgetImpl; struct SPWidget { friend class Inkscape::SPWidgetImpl; + static GType getType(); + GtkBin bin; - InkscapeApplication *inkscape; Inkscape::SPWidgetImpl *_impl; +private: + sigc::connection selModified; + sigc::connection selChanged; + sigc::connection selSet; }; struct SPWidgetClass { @@ -53,7 +58,7 @@ struct SPWidgetClass { GType sp_widget_get_type(); /** Generic constructor for global widget. */ -GtkWidget *sp_widget_new_global(InkscapeApplication *inkscape); +GtkWidget *sp_widget_new_global(); #endif // SEEN_SP_WIDGET_H /* diff --git a/src/widgets/stroke-marker-selector.cpp b/src/widgets/stroke-marker-selector.cpp index 23da54e94..c62262e81 100644 --- a/src/widgets/stroke-marker-selector.cpp +++ b/src/widgets/stroke-marker-selector.cpp @@ -64,7 +64,7 @@ MarkerComboBox::MarkerComboBox(gchar const *id, int l) : sp_pixbuf_new( Inkscape::ICON_SIZE_SMALL_TOOLBAR, INKSCAPE_ICON("no-marker") ) ) ); sandbox = ink_markers_preview_doc (); - desktop = inkscape_active_desktop(); + desktop = SP_ACTIVE_DESKTOP; doc = sp_desktop_document(desktop); modified_connection = doc->getDefs()->connectModified( sigc::hide(sigc::hide(sigc::bind(sigc::ptr_fun(&MarkerComboBox::handleDefsModified), this))) ); diff --git a/src/widgets/stroke-style.cpp b/src/widgets/stroke-style.cpp index 02dd5df6e..51880ba85 100644 --- a/src/widgets/stroke-style.cpp +++ b/src/widgets/stroke-style.cpp @@ -204,8 +204,8 @@ StrokeStyle::StrokeStyle() : unitSelector->addUnit(*unit_table.getUnit("%")); _old_unit = unitSelector->getUnit(); if (desktop) { - unitSelector->setUnit(sp_desktop_namedview(desktop)->doc_units->abbr); - _old_unit = sp_desktop_namedview(desktop)->doc_units; + unitSelector->setUnit(sp_desktop_namedview(desktop)->display_units->abbr); + _old_unit = sp_desktop_namedview(desktop)->display_units; } widthSpin->setUnitMenu(unitSelector); unitChangedConn = unitSelector->signal_changed().connect(sigc::mem_fun(*this, &StrokeStyle::unitChangedCB)); @@ -839,7 +839,7 @@ StrokeStyle::updateLine() // same width, or only one object; no sense to keep percent, switch to absolute Inkscape::Util::Unit const *tempunit = unitSelector->getUnit(); if (tempunit->type != Inkscape::Util::UNIT_TYPE_LINEAR) { - unitSelector->setUnit(sp_desktop_namedview(SP_ACTIVE_DESKTOP)->doc_units->abbr); + unitSelector->setUnit(sp_desktop_namedview(SP_ACTIVE_DESKTOP)->display_units->abbr); } } |
