001/*
002 * SVG Salamander
003 * Copyright (c) 2004, Mark McKay
004 * All rights reserved.
005 *
006 * Redistribution and use in source and binary forms, with or 
007 * without modification, are permitted provided that the following
008 * conditions are met:
009 *
010 *   - Redistributions of source code must retain the above 
011 *     copyright notice, this list of conditions and the following
012 *     disclaimer.
013 *   - Redistributions in binary form must reproduce the above
014 *     copyright notice, this list of conditions and the following
015 *     disclaimer in the documentation and/or other materials 
016 *     provided with the distribution.
017 *
018 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
019 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
020 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
021 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
022 * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
023 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
024 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
025 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
026 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
027 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
028 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
029 * OF THE POSSIBILITY OF SUCH DAMAGE. 
030 * 
031 * Mark McKay can be contacted at mark@kitfox.com.  Salamander and other
032 * projects can be found at http://www.kitfox.com
033 *
034 * Created on March 18, 2004, 6:52 AM
035 */
036package com.kitfox.svg;
037
038import com.kitfox.svg.xml.StyleAttribute;
039import java.awt.geom.Point2D;
040import java.net.URI;
041import java.net.URL;
042import java.util.ArrayList;
043
044/**
045 * @author Mark McKay
046 * @author <a href="mailto:mark@kitfox.com">Mark McKay</a>
047 */
048public class Filter extends SVGElement
049{
050
051    public static final String TAG_NAME = "filter";
052    public static final int FU_OBJECT_BOUNDING_BOX = 0;
053    public static final int FU_USER_SPACE_ON_USE = 1;
054    protected int filterUnits = FU_OBJECT_BOUNDING_BOX;
055    public static final int PU_OBJECT_BOUNDING_BOX = 0;
056    public static final int PU_USER_SPACE_ON_USE = 1;
057    protected int primitiveUnits = PU_OBJECT_BOUNDING_BOX;
058    float x = 0f;
059    float y = 0f;
060    float width = 1f;
061    float height = 1f;
062    Point2D filterRes = new Point2D.Double();
063    URL href = null;
064    final ArrayList filterEffects = new ArrayList();
065
066    /**
067     * Creates a new instance of FillElement
068     */
069    public Filter()
070    {
071    }
072
073    public String getTagName()
074    {
075        return TAG_NAME;
076    }
077
078    /**
079     * Called after the start element but before the end element to indicate
080     * each child tag that has been processed
081     */
082    public void loaderAddChild(SVGLoaderHelper helper, SVGElement child) throws SVGElementException
083    {
084        super.loaderAddChild(helper, child);
085
086        if (child instanceof FilterEffects)
087        {
088            filterEffects.add(child);
089        }
090    }
091
092    protected void build() throws SVGException
093    {
094        super.build();
095
096        StyleAttribute sty = new StyleAttribute();
097        String strn;
098
099        if (getPres(sty.setName("filterUnits")))
100        {
101            strn = sty.getStringValue().toLowerCase();
102            if (strn.equals("userspaceonuse"))
103            {
104                filterUnits = FU_USER_SPACE_ON_USE;
105            } else
106            {
107                filterUnits = FU_OBJECT_BOUNDING_BOX;
108            }
109        }
110
111        if (getPres(sty.setName("primitiveUnits")))
112        {
113            strn = sty.getStringValue().toLowerCase();
114            if (strn.equals("userspaceonuse"))
115            {
116                primitiveUnits = PU_USER_SPACE_ON_USE;
117            } else
118            {
119                primitiveUnits = PU_OBJECT_BOUNDING_BOX;
120            }
121        }
122
123        if (getPres(sty.setName("x")))
124        {
125            x = sty.getFloatValueWithUnits();
126        }
127
128        if (getPres(sty.setName("y")))
129        {
130            y = sty.getFloatValueWithUnits();
131        }
132
133        if (getPres(sty.setName("width")))
134        {
135            width = sty.getFloatValueWithUnits();
136        }
137
138        if (getPres(sty.setName("height")))
139        {
140            height = sty.getFloatValueWithUnits();
141        }
142
143        try
144        {
145            if (getPres(sty.setName("xlink:href")))
146            {
147                URI src = sty.getURIValue(getXMLBase());
148                href = src.toURL();
149            }
150        } catch (Exception e)
151        {
152            throw new SVGException(e);
153        }
154
155    }
156
157    public float getX()
158    {
159        return x;
160    }
161
162    public float getY()
163    {
164        return y;
165    }
166
167    public float getWidth()
168    {
169        return width;
170    }
171
172    public float getHeight()
173    {
174        return height;
175    }
176
177    public boolean updateTime(double curTime) throws SVGException
178    {
179//        if (trackManager.getNumTracks() == 0) return false;
180
181        //Get current values for parameters
182        StyleAttribute sty = new StyleAttribute();
183        boolean stateChange = false;
184
185        if (getPres(sty.setName("x")))
186        {
187            float newVal = sty.getFloatValueWithUnits();
188            if (newVal != x)
189            {
190                x = newVal;
191                stateChange = true;
192            }
193        }
194
195        if (getPres(sty.setName("y")))
196        {
197            float newVal = sty.getFloatValueWithUnits();
198            if (newVal != y)
199            {
200                y = newVal;
201                stateChange = true;
202            }
203        }
204
205        if (getPres(sty.setName("width")))
206        {
207            float newVal = sty.getFloatValueWithUnits();
208            if (newVal != width)
209            {
210                width = newVal;
211                stateChange = true;
212            }
213        }
214
215        if (getPres(sty.setName("height")))
216        {
217            float newVal = sty.getFloatValueWithUnits();
218            if (newVal != height)
219            {
220                height = newVal;
221                stateChange = true;
222            }
223        }
224
225        try
226        {
227            if (getPres(sty.setName("xlink:href")))
228            {
229                URI src = sty.getURIValue(getXMLBase());
230                URL newVal = src.toURL();
231
232                if (!newVal.equals(href))
233                {
234                    href = newVal;
235                    stateChange = true;
236                }
237            }
238        } catch (Exception e)
239        {
240            throw new SVGException(e);
241        }
242
243        if (getPres(sty.setName("filterUnits")))
244        {
245            int newVal;
246            String strn = sty.getStringValue().toLowerCase();
247            if (strn.equals("userspaceonuse"))
248            {
249                newVal = FU_USER_SPACE_ON_USE;
250            } else
251            {
252                newVal = FU_OBJECT_BOUNDING_BOX;
253            }
254            if (newVal != filterUnits)
255            {
256                filterUnits = newVal;
257                stateChange = true;
258            }
259        }
260
261        if (getPres(sty.setName("primitiveUnits")))
262        {
263            int newVal;
264            String strn = sty.getStringValue().toLowerCase();
265            if (strn.equals("userspaceonuse"))
266            {
267                newVal = PU_USER_SPACE_ON_USE;
268            } else
269            {
270                newVal = PU_OBJECT_BOUNDING_BOX;
271            }
272            if (newVal != filterUnits)
273            {
274                primitiveUnits = newVal;
275                stateChange = true;
276            }
277        }
278
279
280
281        return stateChange;
282    }
283}