Improve SvgImport to support styles that come from CSS style sheet rules.

This commit is contained in:
Jürg Lehni 2013-02-28 17:15:03 -08:00
parent 84f3f041e3
commit c29a7e38a0
2 changed files with 35 additions and 20 deletions

View file

@ -94,9 +94,12 @@ var DomElement = new function() {
return el; return el;
}, },
getStyles: function(el) {
return el.ownerDocument.defaultView.getComputedStyle(el, '');
},
getStyle: function(el, key) { getStyle: function(el, key) {
var style = el.ownerDocument.defaultView.getComputedStyle(el, ''); return el.style[key] || this.getStyles(el)[key] || null;
return el.style[key] || style && style[key] || null;
}, },
setStyle: function(el, key, value) { setStyle: function(el, key, value) {

View file

@ -422,7 +422,8 @@ new function() {
'clip-path': function(item, node, name, value) { 'clip-path': function(item, node, name, value) {
// http://www.w3.org/TR/SVG/masking.html#ClipPathProperty // http://www.w3.org/TR/SVG/masking.html#ClipPathProperty
return createClipGroup(item, getDefinition(value).clone().reduce()); var def = getDefinition(value);
return def && createClipGroup(item, def.clone().reduce());
}, },
gradientTransform: applyTransform, gradientTransform: applyTransform,
@ -441,11 +442,6 @@ new function() {
'font-size': applyTextAttribute, 'font-size': applyTextAttribute,
'text-anchor': applyTextAttribute, 'text-anchor': applyTextAttribute,
'stop-opacity': function(item, node, name, value) {
// http://www.w3.org/TR/SVG/pservers.html#StopOpacityProperty
item.color.setAlpha(parseFloat(value));
},
visibility: function(item, node, name, value) { visibility: function(item, node, name, value) {
item.setVisible(value === 'visible'); item.setVisible(value === 'visible');
}, },
@ -455,6 +451,13 @@ new function() {
item.setColor(value); item.setColor(value);
}, },
'stop-opacity': function(item, node, name, value) {
// http://www.w3.org/TR/SVG/pservers.html#StopOpacityProperty
// NOTE: It is important that this is applied after stop-color!
if (item._color)
item._color.setAlpha(parseFloat(value));
},
offset: function(item, node, name, value) { offset: function(item, node, name, value) {
// http://www.w3.org/TR/SVG/pservers.html#StopElementOffsetAttribute // http://www.w3.org/TR/SVG/pservers.html#StopElementOffsetAttribute
var percentage = value.match(/(.*)%$/); var percentage = value.match(/(.*)%$/);
@ -491,17 +494,24 @@ new function() {
function applyAttributes(item, node) { function applyAttributes(item, node) {
// SVG attributes can be set both as styles and direct node attributes, // SVG attributes can be set both as styles and direct node attributes,
// so we need to parse both // so we need to parse both
// TODO: Instead of looping through the styles, we need to loop through var styles = DomElement.getStyles(node),
// a list of styles relevant to SVG, and calculate the computed style, parentStyles = DomElement.getStyles(node.parentNode);
// to support style classes too. Base.each(attributes, function(apply, key) {
for (var i = 0, l = node.style.length; i < l; i++) { var attr = node.attributes[key];
var name = node.style[i]; if (attr) {
item = applyAttribute(item, node, name, node.style[Base.camelize(name)]); item = applyAttribute(item, node, attr.name, attr.value);
} } else {
for (var i = 0, l = node.attributes.length; i < l; i++) { // Fallback to using styles. See if there is a style, either set
var attr = node.attributes[i]; // directly on the object or applied to it through CSS rules.
item = applyAttribute(item, node, attr.name, attr.value); // We also need to filter out inheritance from their parents.
} var name = Base.camelize(key),
value = node.style[name];
if (!value && styles[name] !== parentStyles[name])
value = styles[name];
if (value && value != 'none')
item = applyAttribute(item, node, key, value);
}
});
return item; return item;
} }
@ -525,7 +535,9 @@ new function() {
var definitions = {}; var definitions = {};
function getDefinition(value) { function getDefinition(value) {
var match = value.match(/\(#([^)']+)/); // When url() comes from a style property, '#'' seems to be missing on
// WebKit, so let's make it optional here:
var match = value.match(/\((?:#|)([^)']+)/);
return match && definitions[match[1]]; return match && definitions[match[1]];
} }