diff options
| author | Tavmjong Bah <tavmjong@free.fr> | 2011-11-29 11:27:10 +0000 |
|---|---|---|
| committer | tavmjong-free <tavmjong@free.fr> | 2011-11-29 11:27:10 +0000 |
| commit | 771029025214cffd0bc9783656c29e08ad208743 (patch) | |
| tree | f8571540680f4aa0138798f87222263df20c278a /src/xml | |
| parent | preferences read out: when no unit is specified, assume it is in the requeste... (diff) | |
| download | inkscape-771029025214cffd0bc9783656c29e08ad208743.tar.gz inkscape-771029025214cffd0bc9783656c29e08ad208743.zip | |
Add possibility to check validity of attributes and usefulness of properties.
This code adds the ability to check for every elment in an SVG document if its
attributes are valid and the styling properties are useful. Options under the
SVG Output section of the Inkscape Preferences dialog control what should
be checked when, and what actions should be taken if invalid attributes
or non-useful properties are found.
(bzr r10753)
Diffstat (limited to 'src/xml')
| -rw-r--r-- | src/xml/repr-io.cpp | 23 | ||||
| -rw-r--r-- | src/xml/simple-node.cpp | 60 |
2 files changed, 76 insertions, 7 deletions
diff --git a/src/xml/repr-io.cpp b/src/xml/repr-io.cpp index 365415488..39eb2637a 100644 --- a/src/xml/repr-io.cpp +++ b/src/xml/repr-io.cpp @@ -33,6 +33,8 @@ #include "extension/extension.h" +#include "attribute-rel-util.h" + #include "preferences.h" using Inkscape::IO::Writer; @@ -256,6 +258,7 @@ int XmlSource::close() Document * sp_repr_read_file (const gchar * filename, const gchar *default_ns) { + // g_warning( "Reading file: %s", filename ); xmlDocPtr doc = 0; Document * rdoc = 0; @@ -446,6 +449,18 @@ sp_repr_do_read (xmlDocPtr doc, const gchar *default_ns) promote_to_namespace(root, INKSCAPE_EXTENSION_NS_NC); } } + + + // Clean unnecessary attributes and style properties from SVG documents. (Controlled by + // preferences.) Note: internal Inkscape svg files will also be cleaned (filters.svg, + // icons.svg). How can one tell if a file is internal? + if ( !strcmp(root->name(), "svg:svg" ) ) { + Inkscape::Preferences *prefs = Inkscape::Preferences::get(); + bool clean = prefs->getBool("/options/svgoutput/check_on_reading"); + if( clean ) { + sp_attribute_clean_tree( root ); + } + } } g_hash_table_destroy (prefix_map); @@ -806,6 +821,12 @@ sp_repr_write_stream_root_element(Node *repr, Writer &out, using Inkscape::Util::ptr_shared; g_assert(repr != NULL); + + // Clean unnecessary attributes and stype properties. (Controlled by preferences.) + Inkscape::Preferences *prefs = Inkscape::Preferences::get(); + bool clean = prefs->getBool("/options/svgoutput/check_on_writing"); + if (clean) sp_attribute_clean_tree( repr ); + Glib::QueryQuark xml_prefix=g_quark_from_static_string("xml"); NSMap ns_map; @@ -928,7 +949,7 @@ void sp_repr_write_stream_element( Node * repr, Writer & out, add_whitespace = false; } - + // THIS DOESN'T APPEAR TO DO ANYTHING. Can it be commented out or deleted? { GQuark const href_key = g_quark_from_static_string("xlink:href"); GQuark const absref_key = g_quark_from_static_string("sodipodi:absref"); diff --git a/src/xml/simple-node.cpp b/src/xml/simple-node.cpp index 792706a18..44ddba237 100644 --- a/src/xml/simple-node.cpp +++ b/src/xml/simple-node.cpp @@ -1,6 +1,5 @@ -/** - * @file - * Garbage collected XML node implementation. +/** @file + * @brief Garbage collected XML node implementation */ /* Copyright 2003-2005 MenTaLguY <mental@rydia.net> * Copyright 2003 Nathan Hurst @@ -17,8 +16,11 @@ #include <cstring> #include <string> + #include <glib/gstrfuncs.h> +#include "preferences.h" + #include "xml/node.h" #include "xml/simple-node.h" #include "xml/node-event-vector.h" @@ -29,6 +31,8 @@ #include "util/share.h" #include "util/format.h" +#include "attribute-rel-util.h" + namespace Inkscape { namespace XML { @@ -312,6 +316,47 @@ SimpleNode::setAttribute(gchar const *name, gchar const *value, bool const /*is_ { g_return_if_fail(name && *name); + // Check usefulness of attributes on elements in the svg namespace, optionally don't add them to tree. + Glib::ustring element = g_quark_to_string(_name); + //g_warning("setAttribute: %s: %s: %s", element.c_str(), name, value); + + gchar* cleaned_value = g_strdup( value ); + + // Only check elements in SVG name space and don't block setting attribute to NULL. + if( element.substr(0,4) == "svg:" && value != NULL) { + + Inkscape::Preferences *prefs = Inkscape::Preferences::get(); + if( prefs->getBool("/options/svgoutput/check_on_editing") ) { + + gchar const *id_char = attribute("id"); + Glib::ustring id = (id_char == NULL ? "" : id_char ); + unsigned int flags = sp_attribute_clean_get_prefs(); + bool attr_warn = flags & SP_ATTR_CLEAN_ATTR_WARN; + bool attr_remove = flags & SP_ATTR_CLEAN_ATTR_REMOVE; + + // Check attributes + if( (attr_warn || attr_remove) && value != NULL ) { + bool is_useful = sp_attribute_check_attribute( element, id, name, attr_warn ); + if( !is_useful && attr_remove ) { + g_free( cleaned_value ); + return; // Don't add to tree. + } + } + + // Check style properties -- Note: if element is not yet inserted into + // tree (and thus has no parent), default values will not be tested. + if( !strcmp( name, "style" ) && (flags >= SP_ATTR_CLEAN_STYLE_WARN) ) { + g_free( cleaned_value ); + cleaned_value = sp_attribute_clean_style( this, value, flags ); + // if( g_strcmp0( value, cleaned_value ) ) { + // g_warning( "SimpleNode::setAttribute: %s", id.c_str() ); + // g_warning( " original: %s", value); + // g_warning( " cleaned: %s", cleaned_value); + // } + } + } + } + GQuark const key = g_quark_from_string(name); MutableList<AttributeRecord> ref; @@ -322,14 +367,13 @@ SimpleNode::setAttribute(gchar const *name, gchar const *value, bool const /*is_ } ref = existing; } - Debug::EventTracker<> tracker; ptr_shared<char> old_value=( existing ? existing->value : ptr_shared<char>() ); ptr_shared<char> new_value=ptr_shared<char>(); - if (value) { - new_value = share_string(value); + if (cleaned_value) { + new_value = share_string(cleaned_value); tracker.set<DebugSetAttribute>(*this, key, new_value); if (!existing) { if (ref) { @@ -355,7 +399,11 @@ SimpleNode::setAttribute(gchar const *name, gchar const *value, bool const /*is_ if ( new_value != old_value && (!old_value || !new_value || strcmp(old_value, new_value))) { _document->logger()->notifyAttributeChanged(*this, key, old_value, new_value); _observers.notifyAttributeChanged(*this, key, old_value, new_value); + //g_warning( "setAttribute notified: %s: %s: %s: %s", name, element.c_str(), old_value, new_value ); } + + g_free( cleaned_value ); + } void SimpleNode::addChild(Node *generic_child, Node *generic_ref) { |
