/******************************************************************************* * Copyright (c) 2007, 2010 Association for Decentralized Information Management * in Industry THTH ry. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * VTT Technical Research Centre of Finland - initial API and implementation *******************************************************************************/ package org.simantics.diagram.elements; import java.awt.Point; import java.awt.Shape; import java.awt.geom.Rectangle2D; import java.util.EnumSet; import org.simantics.g2d.image.Image; import org.simantics.scenegraph.Node; import org.simantics.scenegraph.g2d.G2DParentNode; import org.simantics.utils.datastructures.cache.IFactory; import org.simantics.utils.datastructures.cache.ProvisionException; /** * This is a SVG implementation to the PaintableSymbol interface. */ public class AnimatedSVGImage implements Image { static EnumSet caps = EnumSet.of(Feature.Vector); private Rectangle2D bounds; private final String nodeIdentifier; private final String svgDocument; private final String svgScript; private Point targetSize; // public static AnimatedSVGImage loadFromURL(String nodeIdentifier, URL url) throws IOException { // InputStream in = url.openStream(); // try { // return new AnimatedSVGImage(nodeIdentifier, in); // } finally { // in.close(); // } // } public static IFactory createFactoryFromString(String nodeIdentifier, String svgDocument) { return createFactoryFromString(svgDocument, null); } public static IFactory createFactoryFromString(String nodeIdentifier, String svgDocument, String svgScript, Point targetSize) { return new AnimatedSVGFactory(nodeIdentifier, svgDocument, svgScript, targetSize); } static class AnimatedSVGFactory implements IFactory { String nodeIdentifier; String document; String script; Point targetSize; public AnimatedSVGFactory(String nodeIdentifier, String document, String script, Point referenceSize) { if (nodeIdentifier == null) throw new NullPointerException("nodeIdentifier is null"); if (document == null) throw new NullPointerException("document is null"); if (script == null) throw new NullPointerException("script is null"); this.nodeIdentifier = nodeIdentifier; this.document = document; this.script = script; this.targetSize = referenceSize; } public Image get() throws ProvisionException { return new AnimatedSVGImage(nodeIdentifier, document, script, targetSize); } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (!obj.getClass().equals(getClass())) return false; AnimatedSVGFactory other = (AnimatedSVGFactory)obj; if (!nodeIdentifier.equals(other.nodeIdentifier)) return false; if (targetSize != null) { if (!targetSize.equals(other.targetSize)) return false; } else { if (other.targetSize != null) return false; } return document.equals(other.document); } @Override public int hashCode() { return nodeIdentifier.hashCode() * 31 + document.hashCode() + 123; } } // public AnimatedSVGImage(String nodeIdentifier, String svgDocument) // { // this(nodeIdentifier, svgDocument, null); // } public AnimatedSVGImage(String nodeIdentifier, String svgDocument, String svgScript, Point targetSize) { if (nodeIdentifier == null) throw new NullPointerException("nodeIdentifier is null"); if (svgDocument == null) throw new NullPointerException("svgDocument is null"); if (svgScript == null) throw new NullPointerException("svgScript is null"); this.nodeIdentifier = nodeIdentifier; this.svgDocument = svgDocument; this.svgScript = svgScript; this.targetSize = targetSize; //this.bounds = SVGNode.getBounds(svgDocument); } // public AnimatedSVGImage(String nodeIdentifier, InputStream svgInput) // { // if (nodeIdentifier == null) // throw new NullPointerException("nodeIdentifier is null"); // // String data = ""; // try { // BufferedReader reader = new BufferedReader(new InputStreamReader(svgInput)); // String line = ""; // while((line = reader.readLine()) != null) { // data += line+"\n"; // } // } catch(IOException e) { // } // // this.nodeIdentifier = nodeIdentifier; // this.bounds = SVGNode.getBounds(data); // this.svgDocument = data; // } @Override public Node init(G2DParentNode parent) { // FIXME: mipmaps enabled here by default, since some apps just don't work without them. // Figure out a way to pass the mipmap argument from above AnimatedSVGNode node = parent.getOrCreateNode(nodeIdentifier, AnimatedSVGNode.class); node.setData(svgDocument); node.setScript(svgScript); node.setTargetSize(targetSize); // If this is set to false, rendered graphics will pixelate and disppear during rotation. See #2396. node.useMipMap(true); return node; } @Override public Rectangle2D getBounds() { if(bounds == null) bounds = SVGNode.getBounds(svgDocument); return bounds; } @Override public Shape getOutline() { return getBounds(); } @Override public void addImageListener(ImageListener listener) { } @Override public EnumSet getFeatures() { return caps; } @Override public void removeImageListener(ImageListener listener) { } }