Permalink
Browse files

extracted new processors API and some implementations to configure th…

…e absolute transform of elements to the svg.processors package
  • Loading branch information...
1 parent 09b65ef commit 9bc1a5e74d53f7981b5bd4a3ac26266cffa1b308 @acoppes acoppes committed Feb 13, 2012
@@ -6,12 +6,12 @@
public class GemserkNamespace {
- public static final String Name = "gemserk";
+ public static final String namespace = "gemserk";
public static final String attributeAbsoluteTransform = "absoluteTransform";
public static Matrix3f getAbsoluteTransform(Element element) {
- String transformAttributeValue = element.getAttribute(attributeAbsoluteTransform);
+ String transformAttributeValue = element.getAttributeNS(namespace, attributeAbsoluteTransform);
Matrix3f m = new Matrix3f();
m.setIdentity();
return SvgInkscapeUtils.parseTransformAttribute(transformAttributeValue, m);
@@ -1,7 +1,5 @@
package com.gemserk.commons.svg.inkscape;
-import java.util.StringTokenizer;
-
import org.w3c.dom.Element;
import com.gemserk.vecmath.Matrix3f;
@@ -64,70 +62,22 @@ public static Matrix3f getTransform(Element element, Matrix3f m) {
}
/**
- * Parses a SVG Element transform attribute and applies each transform to the specified matrix.
- *
- * @param transformAttribute
- * The SVG Element transform attribute.
- * @param m
- * The matrix to be modified.
- * @return The matrix with all transforms applied.
+ * @deprecated Use SvgTransformUtils instead.
*/
public static Matrix3f parseTransformAttribute(String transformAttribute, Matrix3f m) {
-
- transformAttribute = transformAttribute.replace(" ", "");
-
- if (transformAttribute.startsWith("scale")) {
- transformAttribute = transformAttribute.substring(0, transformAttribute.length() - 1);
- transformAttribute = transformAttribute.substring("scale(".length());
- StringTokenizer tokens = new StringTokenizer(transformAttribute, ", ");
-
- float sx = Float.parseFloat(tokens.nextToken());
- float sy = sx;
-
- if (tokens.hasMoreTokens())
- sy = Float.parseFloat(tokens.nextToken());
-
- m.setM00(sx);
- m.setM11(sy);
- } else if (transformAttribute.startsWith("matrix")) {
-
- transformAttribute = transformAttribute.substring(0, transformAttribute.length() - 1);
- transformAttribute = transformAttribute.substring("matrix(".length());
-
- StringTokenizer tokens = new StringTokenizer(transformAttribute, ", ");
-
- float[] tr = new float[6];
-
- for (int j = 0; j < tr.length; j++) {
- tr[j] = Float.parseFloat(tokens.nextToken());
- }
-
- m.setM00(tr[0]);
- m.setM10(tr[1]);
-
- m.setM01(tr[2]);
- m.setM11(tr[3]);
-
- m.setM02(tr[4]);
- m.setM12(tr[5]);
- } else if (transformAttribute.startsWith("translate")) {
- transformAttribute = transformAttribute.substring(0, transformAttribute.length() - 1);
- transformAttribute = transformAttribute.substring("translate(".length());
- StringTokenizer tokens = new StringTokenizer(transformAttribute, ", ");
-
- float tx = Float.parseFloat(tokens.nextToken());
- float ty = Float.parseFloat(tokens.nextToken());
-
- m.setM02(tx);
- m.setM12(ty);
- }
- return m;
+ return SvgTransformUtils.parseTransform(transformAttribute, m);
}
-
+
+ /**
+ * @deprecated Use SvgTransformUtils instead.
+ */
public static String transformToAttribute(Matrix3f m) {
- return "matrix(" + m.m00 + "," + m.m10 + "," + m.m01 + "," + m.m11 + "," + m.m02 + "," + m.m12 + ")";
+ return SvgTransformUtils.serializeTransform(m);
}
+ /**
+ * @deprecated Use SvgTransformUtils isntead.
+ */
public static boolean isFlipped(Matrix3f matrix) {
return matrix.getM00() != matrix.getM11();
}
@@ -0,0 +1,81 @@
+package com.gemserk.commons.svg.inkscape;
+
+import java.util.StringTokenizer;
+
+import com.gemserk.vecmath.Matrix3f;
+
+public class SvgTransformUtils {
+
+ /**
+ * Parses a SVG Element transform attribute and applies each transform to the specified matrix.
+ *
+ * @param transform
+ * The SVG Element transform attribute.
+ * @param matrix
+ * The matrix to be modified.
+ * @return The matrix with all transforms applied.
+ */
+ public static Matrix3f parseTransform(String transform, Matrix3f matrix) {
+
+ transform = transform.replace(" ", "");
+
+ if (transform.startsWith("scale")) {
+ transform = transform.substring(0, transform.length() - 1);
+ transform = transform.substring("scale(".length());
+ StringTokenizer tokens = new StringTokenizer(transform, ", ");
+
+ float sx = Float.parseFloat(tokens.nextToken());
+ float sy = sx;
+
+ if (tokens.hasMoreTokens())
+ sy = Float.parseFloat(tokens.nextToken());
+
+ matrix.setM00(sx);
+ matrix.setM11(sy);
+ } else if (transform.startsWith("matrix")) {
+
+ transform = transform.substring(0, transform.length() - 1);
+ transform = transform.substring("matrix(".length());
+
+ StringTokenizer tokens = new StringTokenizer(transform, ", ");
+
+ float[] tr = new float[6];
+
+ for (int j = 0; j < tr.length; j++) {
+ tr[j] = Float.parseFloat(tokens.nextToken());
+ }
+
+ matrix.setM00(tr[0]);
+ matrix.setM10(tr[1]);
+
+ matrix.setM01(tr[2]);
+ matrix.setM11(tr[3]);
+
+ matrix.setM02(tr[4]);
+ matrix.setM12(tr[5]);
+ } else if (transform.startsWith("translate")) {
+ transform = transform.substring(0, transform.length() - 1);
+ transform = transform.substring("translate(".length());
+ StringTokenizer tokens = new StringTokenizer(transform, ", ");
+
+ float tx = Float.parseFloat(tokens.nextToken());
+ float ty = Float.parseFloat(tokens.nextToken());
+
+ matrix.setM02(tx);
+ matrix.setM12(ty);
+ }
+ return matrix;
+ }
+
+ /**
+ * Serializes the matrix to be in SVG transform format.
+ */
+ public static String serializeTransform(Matrix3f matrix) {
+ return "matrix(" + matrix.m00 + "," + matrix.m10 + "," + matrix.m01 + "," + matrix.m11 + "," + matrix.m02 + "," + matrix.m12 + ")";
+ }
+
+ public static boolean isFlipped(Matrix3f matrix) {
+ return matrix.getM00() != matrix.getM11();
+ }
+
+}
@@ -0,0 +1,17 @@
+package com.gemserk.commons.svg.processors;
+
+import org.w3c.dom.Element;
+
+import com.gemserk.commons.svg.inkscape.SvgNamespace;
+
+public class SvgConfigureIdProcessor extends SvgElementProcessor {
+
+ @Override
+ public boolean processElement(Element element) {
+ if ("".equals(element.getAttribute(SvgNamespace.attributeId)))
+ return true;
+ element.setIdAttribute(SvgNamespace.attributeId, true);
+ return true;
+ }
+
+}
@@ -0,0 +1,32 @@
+package com.gemserk.commons.svg.processors;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.NodeList;
+
+public class SvgDocumentProcessor {
+
+ SvgElementProcessor handler;
+
+ public void process(Document document, SvgElementProcessor handler) {
+ this.handler = handler;
+ this.handler.setDocument(document);
+ Element root = document.getDocumentElement();
+ internalProcessElement(root);
+ }
+
+ void internalProcessElement(Element element) {
+ NodeList list = element.getChildNodes();
+ for (int i = 0; i < list.getLength(); i++) {
+ if (list.item(i) instanceof Element) {
+ Element childElement = (Element) list.item(i);
+
+ handler.preProcess(childElement);
+ if (handler.processElement(childElement))
+ internalProcessElement(childElement);
+ handler.postProcessElement(childElement);
+ }
+ }
+ }
+
+}
@@ -0,0 +1,29 @@
+package com.gemserk.commons.svg.processors;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+
+public class SvgElementProcessor {
+
+ protected Document document;
+
+ public void setDocument(Document document) {
+ this.document = document;
+ }
+
+ public void preProcess(Element element) {
+
+ }
+
+ public void postProcessElement(Element element) {
+
+ }
+
+ /**
+ * Returns true if you want to continue parsing children elements of this node.
+ */
+ public boolean processElement(Element element) {
+ return true;
+ }
+
+}
@@ -0,0 +1,41 @@
+package com.gemserk.commons.svg.processors;
+
+import java.util.Stack;
+
+import org.w3c.dom.Element;
+
+import com.gemserk.commons.svg.inkscape.GemserkNamespace;
+import com.gemserk.commons.svg.inkscape.SvgNamespace;
+import com.gemserk.commons.svg.inkscape.SvgTransformUtils;
+import com.gemserk.vecmath.Matrix3f;
+
+public class SvgTransformProcessor extends SvgElementProcessor {
+
+ protected Stack<Matrix3f> transformStack;
+
+ public SvgTransformProcessor() {
+ transformStack = new Stack<Matrix3f>();
+ Matrix3f matrix = new Matrix3f();
+ matrix.setIdentity();
+ transformStack.push(matrix);
+ }
+
+ @Override
+ public void postProcessElement(Element element) {
+ transformStack.pop();
+ }
+
+ @Override
+ public boolean processElement(Element element) {
+ Matrix3f transform = SvgNamespace.getTransform(element);
+ Matrix3f parentTransform = transformStack.peek();
+
+ transform.mul(parentTransform);
+
+ transformStack.push(transform);
+
+ element.setAttributeNS(GemserkNamespace.namespace, GemserkNamespace.attributeAbsoluteTransform, SvgTransformUtils.serializeTransform(transform));
+ return true;
+ }
+
+}
@@ -0,0 +1,54 @@
+package com.gemserk.commons.svg.processors;
+
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+
+import com.gemserk.commons.svg.inkscape.GemserkNamespace;
+import com.gemserk.commons.svg.inkscape.SvgNamespace;
+import com.gemserk.commons.svg.inkscape.SvgTransformUtils;
+import com.gemserk.vecmath.Matrix3f;
+
+public class SvgUseProcessor extends SvgElementProcessor {
+
+ @Override
+ public boolean processElement(Element element) {
+
+ if (!SvgNamespace.isUse(element))
+ return true;
+
+ // for now, using only one level of indirection...
+
+ String sourceElementId = SvgNamespace.getXlinkHref(element);
+
+ if (sourceElementId.startsWith("#")) {
+ sourceElementId = sourceElementId.substring(1);
+
+ Element sourceElement = document.getElementById(sourceElementId);
+
+ if (sourceElement == null)
+ throw new RuntimeException("There is no element with id=" + sourceElementId);
+
+ Element clonedSourceElement = (Element) sourceElement.cloneNode(true);
+
+ clonedSourceElement.setAttribute(SvgNamespace.attributeId, SvgNamespace.getId(element));
+
+ // Matrix3f clonedElementTransform = GemserkNamespace.getAbsoluteTransform(clonedSourceElement);
+ Matrix3f useAbsoluteTransform = GemserkNamespace.getAbsoluteTransform(element);
+
+ clonedSourceElement.setAttribute(SvgNamespace.attributeTransform, SvgTransformUtils.serializeTransform(useAbsoluteTransform));
+
+ // clonedElementTransform.mul(useTransform);
+ // clonedSourceElement.setAttribute(GemserkNamespace.attributeAbsoluteTransform, SvgInkscapeUtils.transformToAttribute(clonedElementTransform));
+
+ Node parentNode = element.getParentNode();
+ parentNode.removeChild(element);
+ parentNode.appendChild(clonedSourceElement);
+
+ return false;
+ } else {
+ throw new RuntimeException("Not implemented, xlink:href=" + sourceElementId);
+ }
+
+ }
+
+}
Oops, something went wrong.

0 comments on commit 9bc1a5e

Please sign in to comment.