deweese     2003/06/05 03:03:17

  Modified:    samples/extensions multi.svg
               sources/org/apache/batik/extension/svg
                        BatikMultiImageElementBridge.java
                        MultiResGraphicsNode.java
  Added:       samples  sydney.svg
               samples/extensions/opera opera-subImage.svg
                        opera-subImageRef.svg
               samples/tests/resources/images operaBridge.jpg
                        operaSteps.jpg operaWalk.jpg
  Removed:     samples/extensions/opera opera.svg
  Log:
  1) The 'multiImage' element now implements both subImage and subImageRef.
     So resolution selected content can be included inline (see
     samples/extensions/opera-subImage.svg for an example).
  2) New sample file: 'samples/sydney.svg' - layout images interactively.
  
  Revision  Changes    Path
  1.1                  xml-batik/samples/sydney.svg
  
  Index: sydney.svg
  ===================================================================
  <?xml version="1.0" standalone="no"?>
  <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN" 
    "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd";>
  <svg width="655" height="600" viewBox="0 0 655 600"
       xmlns="http://www.w3.org/2000/svg"; 
       xmlns:xlink="http://www.w3.org/1999/xlink"; >
  
  <script type="text/ecmascript">
  <![CDATA[
  var svgns   = "http://www.w3.org/2000/svg";;
  var xlinkns = "http://www.w3.org/1999/xlink";;
  
  var dragNode;
  var scaleNode;
  var scaleTgt;
  var dx;
  var dy;
  var imgGroup = document.getElementById("imgGroup")
  var filter = imgGroup.getAttribute("style");
  var dragged=false;
  
  function dragOn(evt) {
    dragNode = evt.target;
    var currX = parseFloat(dragNode.getAttribute("x"));
    var currY = parseFloat(dragNode.getAttribute("y"));
    dx = evt.getClientX()-currX;
    dy = evt.getClientY()-currY;
    dragged=false;
  }
  
  function scaleOn(evt) {
    scaleNode = scaleTgt;
    var cW = parseFloat(scaleNode.getAttribute("width"));
    var cH = parseFloat(scaleNode.getAttribute("height"));
    dx = evt.getClientX()-cW;
    dy = evt.getClientY()-cH;
    dragged=false;
  }
  
  function dragScaleOff() {
    if (dragged) 
       imgGroup.setAttribute("style",filter);
  
    if (dragNode != null) {
      if (dragNode != imgGroup.lastChild) {
         imgGroup.appendChild(dragNode);
      }
      dragNode = null;
    }
    if (scaleNode != null) {
      if (scaleNode != imgGroup.lastChild) {
         imgGroup.appendChild(scaleNode);
      }
      scaleNode = null;
    }
  }
  
  function dragScaleImgBg(evt) {
    if ((dragNode == null) && (scaleNode == null)) {
        hideOverlay();
        return;
    }
    dragScaleImg(evt);
  }
  
  function dragScaleImg(evt) {
    if ((dragNode == null) && (scaleNode == null))
      return;
  
    dragged = true;
    imgGroup.setAttribute("style","");
    if (dragNode != null) {
      if (dragNode != imgGroup.lastChild) 
         imgGroup.appendChild(dragNode);
      dragNode.setAttribute("x",""+(evt.getClientX()-dx));
      dragNode.setAttribute("y",""+(evt.getClientY()-dy));
      updateOverlay(dragNode);
    }
    if (scaleNode != null) {
      if (scaleNode != imgGroup.lastChild) 
         imgGroup.appendChild(scaleNode);
      var cW = parseFloat(scaleNode.getAttribute("width"));
      var cH = parseFloat(scaleNode.getAttribute("height"));
  
      var ar = cW/cH; 
      var nW = evt.getClientX()-dx;
      var nH = evt.getClientY()-dy;
  
      if (nW/nH < ar) {
         nW = ar*nH;
      } else {
         nH = nW/ar;
      }
  
      scaleNode.setAttribute("width", ""+nW);
      scaleNode.setAttribute("height",""+nH);
      updateOverlay(scaleNode);
    }
  }
  
  function updateOverlay(tgt) {
    var cX = parseFloat(tgt.getAttribute("x"));
    var cY = parseFloat(tgt.getAttribute("y"));
    var cW = parseFloat(tgt.getAttribute("width"));
    var cH = parseFloat(tgt.getAttribute("height"));
  
    var over = document.getElementById("overlay");
    over.setAttribute("transform","translate("+(cX+cW-1)+","+(cY+cH-1)+")");
    scaleTgt = tgt;
  }
  
  function showOverlay(evt) {
    if ((dragNode != null) || (scaleNode != null))
       return;
    var tgt = evt.target;
    updateOverlay(tgt);
    var over = document.getElementById("overlay");
    over.setAttribute("visibility","visible");
  }
  
  function hideOverlay() {
    if ((dragNode != null) || (scaleNode != null))
       return;
    var over = document.getElementById("overlay");
    over.setAttribute("visibility","hidden");
  }
  
  ]]></script>
  
     <filter id="merge"  filterUnits="objectBoundingBox" >
         <feMorphology operator="dilate" radius="10" in="SourceAlpha" />
         <feGaussianBlur stdDeviation="4" /> 
         <feOffset dx="3" dy="3"/>
         <feComponentTransfer result="shadow">
            <feFuncA type="linear" slope=".6" intercept="0" />
         </feComponentTransfer>
         <feComposite operator="over" in="SourceGraphic" in2="shadow"/>
     </filter>
  
     <rect fill="#88A" x="0%" y="0%" width="100%" height="100%"/>
     <text x="302" y="47" font-size="24" fill="#448"
          >Click and drag to move images</text>
     <text x="300" y="45" font-size="24" fill="white"
          >Click and drag to move images</text>
     <rect fill="none" x="0%" y="0%" width="100%" height="100%"
           pointer-events="fill"
           onmousedown="dragScaleOff()"
           onmouseup="dragScaleOff()"
           onmousemove="dragScaleImgBg(evt)"/>
  
     <g id="imgGroup" style="filter:url(#merge)" 
             onmousedown="dragOn(evt)"
             onmouseup="dragScaleOff()"
             onmousemove="dragScaleImg(evt)"
               onmouseover="showOverlay(evt)">
  
        <image x="25" y="315" width="360" height="240"
               xlink:href="tests/resources/images/operaSteps.jpg"/>
     
        <image x="50" y="40" width="200" height="300"
               xlink:href="tests/resources/images/operaWalk.jpg"/>
     
        <image x="270" y="200" width="360" height="240"
               xlink:href="tests/resources/images/operaBridge.jpg"/>
     </g>
  
     <g id="overlay" visibility="hidden" 
        onmousedown="scaleOn(evt)"
        onmouseup="dragScaleOff()"
        onmousemove="dragScaleImg(evt)">
        <path fill="darkgrey" stroke="white"
            d="M0,0 h-20 l20,-20 z M-12,-3 l9-9 z M-6,-3 l3-3z"/>
     </g>
  
  </svg>
  
  
  
  1.6       +13 -13    xml-batik/samples/extensions/multi.svg
  
  Index: multi.svg
  ===================================================================
  RCS file: /home/cvs/xml-batik/samples/extensions/multi.svg,v
  retrieving revision 1.5
  retrieving revision 1.6
  diff -u -r1.5 -r1.6
  --- multi.svg 28 May 2003 18:45:59 -0000      1.5
  +++ multi.svg 5 Jun 2003 10:03:16 -0000       1.6
  @@ -2,20 +2,20 @@
   <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN"
   "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd";>
   
  -<!-- ====================================================================== -->
  -<!-- Copyright (C) The Apache Software Foundation. All rights reserved.     -->
  -<!--                                                                        -->
  -<!-- This software is published under the terms of the Apache Software      -->
  -<!-- License version 1.1, a copy of which has been included with this       -->
  -<!-- distribution in  the LICENSE file.                                     -->
  -<!-- ====================================================================== -->
  +<!-- =================================================================== -->
  +<!-- Copyright (C) The Apache Software Foundation. All rights reserved.  -->
  +<!--                                                                     -->
  +<!-- This software is published under the terms of the Apache Software   -->
  +<!-- License version 1.1, a copy of which has been included with this    -->
  +<!-- distribution in  the LICENSE file.                                  -->
  +<!-- =================================================================== -->
   
  -<!-- ====================================================================== -->
  -<!-- Tests 'multiImage' element with just 'subImageRef' children.           -->
  -<!--                                                                        -->
  -<!-- @author [EMAIL PROTECTED]                                       -->
  +<!-- =================================================================== -->
  +<!-- Tests 'multiImage' element with just 'subImageRef' children.        -->
  +<!--                                                                     -->
  +<!-- @author [EMAIL PROTECTED]                                    -->
   <!-- @version $Id$ -->
  -<!-- ====================================================================== -->
  +<!-- =================================================================== -->
   
   <svg width="450" height="500" xml:space="preserve" 
        viewBox="0 0 450 500"
  
  
  
  1.1                  xml-batik/samples/extensions/opera/opera-subImage.svg
  
  Index: opera-subImage.svg
  ===================================================================
  <?xml version="1.0" standalone="no"?>
  <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN"
  "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd";>
  
  <!-- =================================================================== -->
  <!-- Copyright (C) The Apache Software Foundation. All rights reserved.  -->
  <!--                                                                     -->
  <!-- This software is published under the terms of the Apache Software   -->
  <!-- License version 1.1, a copy of which has been included with this    -->
  <!-- distribution in  the LICENSE file.                                  -->
  <!-- =================================================================== -->
  
  <!-- =================================================================== -->
  <!-- Tests 'multiImage' element with a combination of 'subImage' and     -->
  <!-- 'subImageRef' children.                                             -->
  <!--                                                                     -->
  <!-- @author [EMAIL PROTECTED]                                    -->
  <!-- @version $Id: opera-subImage.svg,v 1.1 2003/06/05 10:03:16 deweese Exp $ -->
  <!-- =================================================================== -->
  
  <svg width="640" height="480" viewBox="0 0 640 480" 
       xmlns="http://www.w3.org/2000/svg"; 
       xmlns:xlink="http://www.w3.org/1999/xlink";>
  
  <style type="text/css"><![CDATA[
          .overlay { fill:none; stroke-width:4; }
     ]]></style>
  
     <symbol id="opera" viewBox="0 0 90 135">
        <multiImage x="0" y="0" width="90" height="135"
                    xmlns="http://xml.apache.org/batik/ext";>
           <subImageRef xlink:href="multires/opera-3-0-0.jpg"
             min-pixel-size="1"/>
           <subImage max-pixel-size="1">
              <svg width="100%" height="100%" viewBox="0 0 180 270">
                 <multiImage x="0" y="0" width="180" height="180"
                             xmlns="http://xml.apache.org/batik/ext";>
                    <subImageRef xlink:href="multires/opera-2-0-0.jpg"
                      min-pixel-size="1"/>
                    <subImage max-pixel-size="1">
                       <svg width="100%" height="100%" viewBox="0 0 360 360">
                          <multiImage x="0" y="0" width="180" height="180"
                                      xmlns="http://xml.apache.org/batik/ext";>
                             <subImageRef xlink:href="multires/opera-1-0-0.jpg"
                               min-pixel-size="1"/>
                             <subImage max-pixel-size="1">
                                <svg width="100%" height="100%" 
                                     viewBox="0 0 360 360">
                                   <image x="0" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-0-0.jpg"/>
                                   <image x="180" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-1-0.jpg"/>
                                   <image x="0" y="180" width="180" height="180"
                                         xlink:href="multires/opera-0-0-1.jpg"/>
                                   <image x="180" y="180" 
                                         width="180" height="180"
                                         xlink:href="multires/opera-0-1-1.jpg"/>
  
                                   <rect class="overlay" stroke="#F00" 
                                         x="0" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="0" y="180" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="180" width="180" height="180"/>
                                </svg>
                             </subImage>
                          </multiImage>
                          <multiImage x="180" y="0" width="180" height="180"
                                      xmlns="http://xml.apache.org/batik/ext";>
                             <subImageRef xlink:href="multires/opera-1-1-0.jpg"
                               min-pixel-size="1"/>
                             <subImage max-pixel-size="1">
                                <svg width="100%" height="100%" 
                                     viewBox="0 0 360 360">
                                   <image x="0" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-2-0.jpg"/>
                                   <image x="180" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-3-0.jpg"/>
                                   <image x="0" y="180" width="180" height="180"
                                         xlink:href="multires/opera-0-2-1.jpg"/>
                                   <image x="180" y="180" 
                                         width="180" height="180"
                                         xlink:href="multires/opera-0-3-1.jpg"/>
  
                                   <rect class="overlay" stroke="#F00" 
                                         x="0" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="0" y="180" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="180" width="180" height="180"/>
                                </svg>
                             </subImage>
                          </multiImage>
                          <multiImage x="0" y="180" width="180" height="180"
                                      xmlns="http://xml.apache.org/batik/ext";>
                             <subImageRef xlink:href="multires/opera-1-0-1.jpg"
                               min-pixel-size="1"/>
                             <subImage max-pixel-size="1">
                                <svg width="100%" height="100%" 
                                     viewBox="0 0 360 360">
                                   <image x="0" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-0-2.jpg"/>
                                   <image x="180" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-1-2.jpg"/>
                                   <image x="0" y="180" width="180" height="180"
                                         xlink:href="multires/opera-0-0-3.jpg"/>
                                   <image x="180" y="180" 
                                         width="180" height="180"
                                         xlink:href="multires/opera-0-1-3.jpg"/>
  
                                   <rect class="overlay" stroke="#F00" 
                                         x="0" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="0" y="180" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="180" width="180" height="180"/>
                                </svg>
                             </subImage>
                          </multiImage>
                          <multiImage x="180" y="180" width="180" height="180"
                                      xmlns="http://xml.apache.org/batik/ext";>
                             <subImageRef xlink:href="multires/opera-1-1-1.jpg"
                               min-pixel-size="1"/>
                             <subImage max-pixel-size="1">
                                <svg width="100%" height="100%" 
                                     viewBox="0 0 360 360">
                                   <image x="0" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-2-2.jpg"/>
                                   <image x="180" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-3-2.jpg"/>
                                   <image x="0" y="180" width="180" height="180"
                                         xlink:href="multires/opera-0-2-3.jpg"/>
                                   <image x="180" y="180" 
                                         width="180" height="180"
                                         xlink:href="multires/opera-0-3-3.jpg"/>
  
                                   <rect class="overlay" stroke="#F00" 
                                         x="0" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="0" y="180" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="180" width="180" height="180"/>
                                </svg>
                             </subImage>
                          </multiImage>
  
                          <rect class="overlay" 
                                stroke="#FF0" 
                                x="0" y="0" width="180" height="180"/>
                          <rect class="overlay" 
                                stroke="#FF0" 
                                x="180" y="0" width="180" height="180"/>
                          <rect class="overlay" 
                                stroke="#FF0" 
                                x="0" y="180" width="180" height="180"/>
                          <rect class="overlay" 
                                stroke="#FF0" 
                                x="180" y="180" width="180" height="180"/>
                       </svg>
                    </subImage>
                 </multiImage>
  
                 <multiImage x="0" y="180" width="180" height="90"
                             xmlns="http://xml.apache.org/batik/ext";>
                    <subImageRef xlink:href="multires/opera-2-0-1.jpg"
                      min-pixel-size="1"/>
                    <subImage max-pixel-size="1">
                       <svg width="100%" height="100%" viewBox="0 0 360 180">
                          <multiImage x="0" y="0" width="180" height="180"
                                      xmlns="http://xml.apache.org/batik/ext";>
                             <subImageRef xlink:href="multires/opera-1-0-2.jpg"
                               min-pixel-size="1"/>
                             <subImage max-pixel-size="1">
                                <svg width="100%" height="100%" 
                                     viewBox="0 0 360 360">
                                   <image x="0" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-0-4.jpg"/>
                                   <image x="180" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-1-4.jpg"/>
                                   <image x="0" y="180" width="180" height="180"
                                         xlink:href="multires/opera-0-0-5.jpg"/>
                                   <image x="180" y="180" 
                                         width="180" height="180"
                                         xlink:href="multires/opera-0-1-5.jpg"/>
  
                                   <rect class="overlay" stroke="#F00" 
                                         x="0" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="0" y="180" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="180" width="180" height="180"/>
                                </svg>
                             </subImage>
                          </multiImage>
                          <multiImage x="180" y="0" width="180" height="180"
                                      xmlns="http://xml.apache.org/batik/ext";>
                             <subImageRef xlink:href="multires/opera-1-1-2.jpg"
                               min-pixel-size="1"/>
                             <subImage max-pixel-size="1">
                                <svg width="100%" height="100%" 
                                     viewBox="0 0 360 360">
                                   <image x="0" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-2-4.jpg"/>
                                   <image x="180" y="0" width="180" height="180"
                                         xlink:href="multires/opera-0-3-4.jpg"/>
                                   <image x="0" y="180" width="180" height="180"
                                         xlink:href="multires/opera-0-2-5.jpg"/>
                                   <image x="180" y="180" 
                                         width="180" height="180"
                                         xlink:href="multires/opera-0-3-5.jpg"/>
  
                                   <rect class="overlay" stroke="#F00" 
                                         x="0" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="0" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="0" y="180" width="180" height="180"/>
                                   <rect class="overlay" stroke="#F00" 
                                    x="180" y="180" width="180" height="180"/>
                                </svg>
                             </subImage>
                          </multiImage>
  
                          <rect class="overlay" 
                                stroke="#FF0" 
                                x="0" y="0" width="180" height="180"/>
                          <rect class="overlay" 
                                stroke="#FF0" 
                                x="180" y="0" width="180" height="180"/>
                       </svg>
                    </subImage>
                 </multiImage>
  
                 <rect class="overlay" 
                       stroke="#0F0" 
                       x="0" y="0" width="180" height="180"/>
                 <rect class="overlay" 
                       stroke="#0F0" 
                       x="0" y="180" width="180" height="90"/>
              </svg>
           </subImage>
        </multiImage>
        <rect class="overlay" stroke="#00F" 
              x="0" y="0" width="90" height="135"/>
     </symbol>>
  
     <use x="165" y="50" width="270" height="405" xlink:href="#opera"/>
  
     <use x="10" y="50" width="135" height="202.5" xlink:href="#opera"/>
  
     <use x="43.75" y="272.5" width="67.5" height="101.25" xlink:href="#opera"/>
  </svg>
  
  
  
  1.1                  xml-batik/samples/extensions/opera/opera-subImageRef.svg
  
  Index: opera-subImageRef.svg
  ===================================================================
  <?xml version="1.0" standalone="no"?>
  <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN"
  "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd";>
  <!-- =================================================================== -->
  <!-- Copyright (C) The Apache Software Foundation. All rights reserved.  -->
  <!--                                                                     -->
  <!-- This software is published under the terms of the Apache Software   -->
  <!-- License version 1.1, a copy of which has been included with this    -->
  <!-- distribution in  the LICENSE file.                                  -->
  <!-- =================================================================== -->
  
  <!-- =================================================================== -->
  <!-- Tests 'multiImage' element with 'subImageRef' children that         -->
  <!-- reference external SVG files.                                       -->
  <!--                                                                     -->
  <!-- @author [EMAIL PROTECTED]                                    -->
  <!-- @version $Id: opera-subImageRef.svg,v 1.1 2003/06/05 10:03:16 deweese Exp $ -->
  <!-- =================================================================== -->
  
  <svg width="640" height="480" viewBox="0 0 640 480" 
       xmlns="http://www.w3.org/2000/svg"; 
       xmlns:xlink="http://www.w3.org/1999/xlink";>
     <image x="165" y="50" width="270" height="405"
            xlink:href="opera-3-0-0.svg" />
  
     <image x="10" y="50" width="135" height="202.5"
            xlink:href="opera-3-0-0.svg" />
  
     <image x="43.75" y="272.5" width="67.5" height="101.25"
            xlink:href="opera-3-0-0.svg" />
      
  </svg>
  
  
  
  1.1                  xml-batik/samples/tests/resources/images/operaBridge.jpg
  
        <<Binary file>>
  
  
  1.1                  xml-batik/samples/tests/resources/images/operaSteps.jpg
  
        <<Binary file>>
  
  
  1.1                  xml-batik/samples/tests/resources/images/operaWalk.jpg
  
        <<Binary file>>
  
  
  1.10      +158 -32   
xml-batik/sources/org/apache/batik/extension/svg/BatikMultiImageElementBridge.java
  
  Index: BatikMultiImageElementBridge.java
  ===================================================================
  RCS file: 
/home/cvs/xml-batik/sources/org/apache/batik/extension/svg/BatikMultiImageElementBridge.java,v
  retrieving revision 1.9
  retrieving revision 1.10
  diff -u -r1.9 -r1.10
  --- BatikMultiImageElementBridge.java 28 May 2003 14:40:57 -0000      1.9
  +++ BatikMultiImageElementBridge.java 5 Jun 2003 10:03:16 -0000       1.10
  @@ -9,25 +9,32 @@
   package org.apache.batik.extension.svg;
   
   import java.awt.Dimension;
  +import java.awt.geom.AffineTransform;
   import java.awt.geom.Rectangle2D;
   import java.util.Collection;
   import java.util.Iterator;
   import java.util.LinkedList;
   import java.util.List;
   
  +import org.apache.batik.ext.awt.image.renderable.ClipRable8Bit;
  +import org.apache.batik.ext.awt.image.renderable.Filter;
   import org.apache.batik.bridge.Bridge;
   import org.apache.batik.bridge.BridgeContext;
   import org.apache.batik.bridge.BridgeException;
   import org.apache.batik.bridge.CSSUtilities;
   import org.apache.batik.bridge.SVGImageElementBridge;
   import org.apache.batik.bridge.SVGUtilities;
  +import org.apache.batik.bridge.Viewport;
   import org.apache.batik.dom.svg.SVGOMElement;
   import org.apache.batik.dom.svg.XMLBaseSupport;
   import org.apache.batik.dom.util.XLinkSupport;
   import org.apache.batik.gvt.GraphicsNode;
   import org.apache.batik.gvt.ImageNode;
   import org.apache.batik.util.ParsedURL;
  +import org.w3c.dom.Attr;
  +import org.w3c.dom.Document;
   import org.w3c.dom.Element;
  +import org.w3c.dom.NamedNodeMap;
   import org.w3c.dom.Node;
   
   /**
  @@ -99,7 +106,35 @@
   
           Rectangle2D b = getImageBounds(ctx, e);
   
  -        List uris   = new LinkedList();
  +        // 'transform'
  +        AffineTransform at = null;
  +        String s = e.getAttribute(SVG_TRANSFORM_ATTRIBUTE);
  +        if (s.length() != 0)
  +            at = SVGUtilities.convertTransform(e, SVG_TRANSFORM_ATTRIBUTE, s);
  +        else
  +            at = new AffineTransform();
  +
  +        at.translate(b.getX(), b.getY());
  +        imgNode.setTransform(at);
  +        
  +        // 'visibility'
  +        imgNode.setVisible(CSSUtilities.convertVisibility(e));
  +
  +        Rectangle2D clip;
  +        clip = new Rectangle2D.Double(0,0,b.getWidth(), b.getHeight());
  +        Filter filter = imgNode.getGraphicsNodeRable(true);
  +        imgNode.setClip(new ClipRable8Bit(filter, clip));
  +
  +        // 'enable-background'
  +        Rectangle2D r = CSSUtilities.convertEnableBackground(e);
  +        if (r != null) {
  +            imgNode.setBackgroundEnable(r);
  +        }
  +        ctx.openViewport(e, new MultiImageElementViewport
  +                         ((float)b.getWidth(), (float)b.getHeight()));
  +
  +
  +        List elems  = new LinkedList();
           List minDim = new LinkedList();
           List maxDim = new LinkedList();
   
  @@ -108,19 +143,22 @@
                   continue;
               
               Element se = (Element)n;
  -            if (!(se.getNamespaceURI().equals(BATIK_EXT_NAMESPACE_URI)) ||
  -                !(se.getLocalName().equals(BATIK_EXT_SUB_IMAGE_REF_TAG)))
  +            if (!se.getNamespaceURI().equals(BATIK_EXT_NAMESPACE_URI))
                   continue;
  -
  -            addInfo(se, uris, minDim, maxDim, b);
  +            if (se.getLocalName().equals(BATIK_EXT_SUB_IMAGE_TAG)) {
  +                addInfo(se, elems, minDim, maxDim, b);
  +            }
  +            if (se.getLocalName().equals(BATIK_EXT_SUB_IMAGE_REF_TAG)) {
  +                addRefInfo(se, elems, minDim, maxDim, b);
  +            }
           }
   
  -        Dimension [] mindary = new Dimension[uris.size()];
  -        Dimension [] maxdary = new Dimension[uris.size()];
  -        ParsedURL [] uary = new ParsedURL[uris.size()];
  +        Dimension [] mindary = new Dimension[elems.size()];
  +        Dimension [] maxdary = new Dimension[elems.size()];
  +        Element   [] elemary = new Element  [elems.size()];
           Iterator mindi = minDim.iterator();
           Iterator maxdi = maxDim.iterator();
  -        Iterator ui = uris.iterator();
  +        Iterator ei = elems.iterator();
           int n=0;
           while (mindi.hasNext()) {
               Dimension minD = (Dimension)mindi.next();
  @@ -135,33 +173,20 @@
                   }
               }
               for (int j=n; j>i; j--) {
  -                uary[j]    = uary[j-1];
  +                elemary[j] = elemary[j-1];
                   mindary[j] = mindary[j-1];
                   maxdary[j] = maxdary[j-1];
               }
               
  -            uary   [i] = (ParsedURL)ui.next();
  +            elemary[i] = (Element)ei.next();
               mindary[i] = minD;
               maxdary[i] = maxD;
               n++;
           }
   
  -        // System.out.println("Bounds: " + bounds);
  -        // System.out.println("ImgB: " + imgBounds);
  -        
  -
  -        GraphicsNode node = new MultiResGraphicsNode(e, b, uary, 
  -                                                     mindary, maxdary);
  -
  -        // 'transform'
  -        String s = e.getAttributeNS(null, SVG_TRANSFORM_ATTRIBUTE);
  -        if (s.length() != 0) {
  -            node.setTransform
  -                (SVGUtilities.convertTransform(e, SVG_TRANSFORM_ATTRIBUTE, s));
  -        }
  -        // 'visibility'
  -        imgNode.setVisible(CSSUtilities.convertVisibility(e));
  -
  +        GraphicsNode node = new MultiResGraphicsNode(e, clip, elemary, 
  +                                                     mindary, maxdary,
  +                                                     ctx);
           imgNode.setImage(node);
   
           return imgNode;
  @@ -174,6 +199,18 @@
           return false;
       }
   
  +    public void buildGraphicsNode(BridgeContext ctx,
  +                                  Element e,
  +                                  GraphicsNode node) {
  +        if (ctx.isDynamic()) {
  +            initializeDynamicSupport(ctx, e, node);
  +        }
  +        // Handle children elements such as <title>
  +        //SVGUtilities.bridgeChildren(ctx, e);
  +        //super.buildGraphicsNode(ctx, e, node);
  +        ctx.closeViewport(e);
  +    }
  +
       /**
        * This method is invoked during the build phase if the document
        * is dynamic. The responsability of this method is to ensure that
  @@ -192,22 +229,78 @@
           ((SVGOMElement)e).setSVGContext(this);
       }
   
  -    protected void addInfo(Element e, Collection uris, 
  +    /**
  +     * Disposes this BridgeUpdateHandler and releases all resources.
  +     */
  +    public void dispose() {
  +        ctx.removeViewport(e);
  +        super.dispose();
  +    }
  +
  +    protected void addInfo(Element e, Collection elems, 
                              Collection minDim, Collection maxDim,
                              Rectangle2D bounds) {
  +        Document doc   = e.getOwnerDocument();
  +        Element  gElem = doc.createElementNS(SVG_NAMESPACE_URI, 
  +                                              SVG_G_TAG);
  +        NamedNodeMap attrs = e.getAttributes();
  +        int len = attrs.getLength();
  +        for (int i = 0; i < len; i++) {
  +            Attr attr = (Attr)attrs.item(i);
  +            gElem.setAttributeNS(attr.getNamespaceURI(),
  +                                 attr.getName(),
  +                                 attr.getValue());
  +        }
  +        // move the children from <subImage> to the <g> element
  +        for (Node n = e.getFirstChild();
  +             n != null;
  +             n = e.getFirstChild()) {
  +            gElem.appendChild(n);
  +        }
  +        e.appendChild(gElem);
  +        elems.add(gElem);
  +        minDim.add(getElementMinPixel(e, bounds));
  +        maxDim.add(getElementMaxPixel(e, bounds));
  +    }
  +
  +    protected void addRefInfo(Element e, Collection elems, 
  +                              Collection minDim, Collection maxDim,
  +                              Rectangle2D bounds) {
           String uriStr = XLinkSupport.getXLinkHref(e);
           if (uriStr.length() == 0) {
               throw new BridgeException(e, ERR_ATTRIBUTE_MISSING,
                                         new Object[] {"xlink:href"});
           }
  -
           String baseURI = XMLBaseSupport.getCascadedXMLBase(e);
           ParsedURL purl;
           if (baseURI == null) purl = new ParsedURL(uriStr);
           else                 purl = new ParsedURL(baseURI, uriStr);
  -        uris.add(purl);
  +        Document doc = e.getOwnerDocument();
  +        Element imgElem = doc.createElementNS(SVG_NAMESPACE_URI, 
  +                                              SVG_IMAGE_TAG);
  +        imgElem.setAttributeNS(XLinkSupport.XLINK_NAMESPACE_URI, 
  +                               "href", purl.toString());
  +        // move the attributes from <subImageRef> to the <image> element
  +        NamedNodeMap attrs = e.getAttributes();
  +        int len = attrs.getLength();
  +        for (int i = 0; i < len; i++) {
  +            Attr attr = (Attr)attrs.item(i);
  +            imgElem.setAttributeNS(attr.getNamespaceURI(),
  +                                   attr.getName(),
  +                                   attr.getValue());
  +        }
  +        String s;
  +        s = e.getAttribute("x");
  +        if (s.length() == 0) imgElem.setAttribute("x", "0");
  +        s = e.getAttribute("y");
  +        if (s.length() == 0) imgElem.setAttribute("y", "0");
  +        s = e.getAttribute("width");
  +        if (s.length() == 0) imgElem.setAttribute("width", "100%");
  +        s = e.getAttribute("height");
  +        if (s.length() == 0) imgElem.setAttribute("height", "100%");
  +        e.appendChild(imgElem);
  +        elems.add(imgElem);
   
  -        
           minDim.add(getElementMinPixel(e, bounds));
           maxDim.add(getElementMaxPixel(e, bounds));
       }
  @@ -240,5 +333,38 @@
           
           return new Dimension((int)(bounds.getWidth()/xPixSz+0.5), 
                                (int)(bounds.getHeight()/yPixSz+0.5)); 
  +    }
  +
  +    /**
  +     * A viewport defined an &lt;svg> element.
  +     */
  +    public static class MultiImageElementViewport implements Viewport {
  +        private float width;
  +        private float height;
  +
  +        /**
  +         * Constructs a new viewport with the specified <tt>SVGSVGElement</tt>.
  +         * @param e the SVGSVGElement that defines this viewport
  +         * @param w the width of the viewport
  +         * @param h the height of the viewport
  +         */
  +        public MultiImageElementViewport(float w, float h) {
  +            this.width = w;
  +            this.height = h;
  +        }
  +
  +        /**
  +         * Returns the width of this viewport.
  +         */
  +        public float getWidth(){
  +            return width;
  +        }
  +
  +        /**
  +         * Returns the height of this viewport.
  +         */
  +        public float getHeight(){
  +            return height;
  +        }
       }
   }
  
  
  
  1.7       +59 -188   
xml-batik/sources/org/apache/batik/extension/svg/MultiResGraphicsNode.java
  
  Index: MultiResGraphicsNode.java
  ===================================================================
  RCS file: 
/home/cvs/xml-batik/sources/org/apache/batik/extension/svg/MultiResGraphicsNode.java,v
  retrieving revision 1.6
  retrieving revision 1.7
  diff -u -r1.6 -r1.7
  --- MultiResGraphicsNode.java 30 May 2003 01:07:15 -0000      1.6
  +++ MultiResGraphicsNode.java 5 Jun 2003 10:03:16 -0000       1.7
  @@ -47,46 +47,36 @@
       extends AbstractGraphicsNode implements SVGConstants {
   
       SoftReference [] srcs;
  -    ParsedURL     [] srcURLs;
  +    Element       [] srcElems;
       Dimension     [] minSz;
       Dimension     [] maxSz;
       Rectangle2D      bounds;
   
  -    UserAgent      userAgent;
  -    DocumentLoader loader;
       BridgeContext  ctx;
   
       Element multiImgElem;
   
  -    /**
  -     * The error code when a required attribute is missing.
  -     * {0} = the name of the attribute
  -     */
  -    public static final String ERR_ATTRIBUTE_MISSING
  -        = "attribute.missing";
  -
  -
       public MultiResGraphicsNode(Element multiImgElem,
                                   Rectangle2D  bounds,
  -                                ParsedURL [] srcURLs,
  +                                Element   [] srcElems,
                                   Dimension [] minSz,
  -                                Dimension [] maxSz) {
  +                                Dimension [] maxSz,
  +                                BridgeContext ctx) {
  +
           this.multiImgElem = multiImgElem;
  -        this.srcURLs     = new ParsedURL[srcURLs.length];
  -        this.minSz       = new Dimension[srcURLs.length];
  -        this.maxSz       = new Dimension[srcURLs.length];
  -
  -        for (int i=0; i<srcURLs.length; i++) {
  -            this.srcURLs[i] = srcURLs[i];
  -            this.minSz[i]   = minSz[i];
  -            this.maxSz[i]   = maxSz[i];
  +        this.srcElems     = new Element  [srcElems.length];
  +        this.minSz        = new Dimension[srcElems.length];
  +        this.maxSz        = new Dimension[srcElems.length];
  +        this.ctx          = ctx;
  +
  +        for (int i=0; i<srcElems.length; i++) {
  +            this.srcElems[i] = srcElems[i];
  +            this.minSz[i]    = minSz[i];
  +            this.maxSz[i]    = maxSz[i];
           }
   
  -        this.srcs = new SoftReference[srcURLs.length];
  +        this.srcs = new SoftReference[srcElems.length];
           this.bounds = bounds;
  -        userAgent = new UserAgentAdapter();
  -        loader    = new DocumentLoader(userAgent);
  -        ctx       = new BridgeContext(userAgent, loader);
       }
   
       /**
  @@ -95,12 +85,13 @@
        * @param g2d the Graphics2D to use
        */
       public void primitivePaint(Graphics2D g2d) {
  -        // System.err.println("PrimPaint: " + this);
           // get the current affine transform
           AffineTransform at = g2d.getTransform();
   
  -        double scx = Math.sqrt(at.getShearX()*at.getShearX()+
  +        double scx = Math.sqrt(at.getShearY()*at.getShearY()+
                                  at.getScaleX()*at.getScaleX());
  +        double scy = Math.sqrt(at.getShearX()*at.getShearX()+
  +                               at.getScaleY()*at.getScaleY());
   
           GraphicsNode gn = null;
           int idx =-1;
  @@ -133,7 +124,43 @@
   
           if (gn == null) return;
   
  -        // Rectangle2D gnBounds = gn.getBounds();
  +        // This makes sure that the image 'pushes out' to it's pixel
  +        // bounderies.
  +        Rectangle2D gnBounds = gn.getBounds();
  +        double gnDevW = gnBounds.getWidth()*scx;
  +        double gnDevH = gnBounds.getHeight()*scy;
  +        double gnDevX = gnBounds.getX()*scx;
  +        double gnDevY = gnBounds.getY()*scy;
  +        double gnDevX0, gnDevX1, gnDevY0, gnDevY1;
  +        if (gnDevW < 0) {
  +            gnDevX0 = gnDevX+gnDevW;
  +            gnDevX1 = gnDevX;
  +        } else {
  +            gnDevX0 = gnDevX;
  +            gnDevX1 = gnDevX+gnDevW;
  +        }
  +        if (gnDevH < 0) {
  +            gnDevY0 = gnDevY+gnDevH;
  +            gnDevY1 = gnDevY;
  +        } else {
  +            gnDevY0 = gnDevY;
  +            gnDevY1 = gnDevY+gnDevH;
  +        }
  +        // This calculate the width/height in pixels given 'worst
  +        // case' assessment.
  +        gnDevW = (int)(Math.ceil(gnDevX1)-Math.floor(gnDevX0));
  +        gnDevH = (int)(Math.ceil(gnDevY1)-Math.floor(gnDevY0));
  +        scx = (gnDevW/gnBounds.getWidth())/scx;
  +        scy = (gnDevH/gnBounds.getHeight())/scy;
  +
  +        // This scales things up slightly so our edges fall on device
  +        // pixel boundries.
  +        AffineTransform nat = g2d.getTransform();
  +        nat = new AffineTransform(nat.getScaleX()*scx, nat.getShearY()*scx,
  +                                 nat.getShearX()*scy, nat.getScaleY()*scy,
  +                                 nat.getTranslateX(), nat.getTranslateY());
  +        g2d.setTransform(nat);
  +
           // double sx = bounds.getWidth()/sizes[idx].getWidth();
           // double sy = bounds.getHeight()/sizes[idx].getHeight();
           // System.err.println("Scale: [" + sx + ", " + sy + "]");
  @@ -199,170 +226,14 @@
           }
           
           try {
  -            SVGDocument svgDoc = (SVGDocument)loader.loadDocument
  -                (srcURLs[idx].toString());
  -
  -            GraphicsNode gn;
  -            gn = createSVGImageNode(ctx, multiImgElem, 
  -                                    bounds, svgDoc);
  -            srcs[idx] = new SoftReference(gn);
  -            return gn;
  -        } catch (Exception ex) { /* ex.printStackTrace(); */ }
  -
  -        try {
  +            GVTBuilder builder = ctx.getGVTBuilder();
               GraphicsNode gn;
  -            gn = createRasterImageNode(ctx, multiImgElem, 
  -                                       bounds, srcURLs[idx]);
  +            gn = builder.build(ctx, srcElems[idx]);
               srcs[idx] = new SoftReference(gn);
               return gn;
  -        } catch (Exception ex) { /* ex.printStackTrace(); */ }
  +        } catch (Exception ex) { ex.printStackTrace();  }
   
           return null;
  -    }
  -
  -
  -    /**
  -     * Returns a GraphicsNode that represents an raster image in JPEG or PNG
  -     * format.
  -     *
  -     * @param ctx the bridge context
  -     * @param e the image element
  -     * @param uriStr the uri of the image
  -     */
  -    protected static GraphicsNode createRasterImageNode(BridgeContext ctx,
  -                                                        Element e,
  -                                                        Rectangle2D bounds,
  -                                                        ParsedURL     purl) {
  -
  -        RasterImageNode node = new RasterImageNode();
  -
  -        ImageTagRegistry reg = ImageTagRegistry.getRegistry();
  -        Filter           img = reg.readURL(purl);
  -        Object           obj = img.getProperty
  -            (SVGBrokenLinkProvider.SVG_BROKEN_LINK_DOCUMENT_PROPERTY);
  -        if ((obj != null) && (obj instanceof SVGDocument)) {
  -            // Ok so we are dealing with a broken link.
  -            return createSVGImageNode(ctx, e, bounds, (SVGDocument)obj);
  -        }
  -        node.setImage(img);
  -        Rectangle2D imgBounds = img.getBounds2D();
  -
  -        // create the implicit viewBox for the raster image. The viewBox for a
  -        // raster image is the size of the image
  -        float [] vb = new float[4];
  -        vb[0] = 0; // x
  -        vb[1] = 0; // y
  -        vb[2] = (float)imgBounds.getWidth(); // width
  -        vb[3] = (float)imgBounds.getHeight(); // height
  -
  -        // System.err.println("Bounds: " + bounds);
  -        // System.err.println("ImgB: " + imgBounds);
  -        // handles the 'preserveAspectRatio', 'overflow' and 'clip' and 
  -        // sets the appropriate AffineTransform to the image node
  -        initializeViewport(e, node, vb, bounds);
  -
  -        return node;
  -    }
  -
  -    /**
  -     * Returns a GraphicsNode that represents a svg document as an image.
  -     *
  -     * @param ctx the bridge context
  -     * @param e the image element
  -     * @param bounds the bounds for this graphicsNode
  -     * @param imgDocument the SVG document that represents the image
  -     */
  -    protected static GraphicsNode createSVGImageNode(BridgeContext ctx,
  -                                                     Element e,
  -                                                     Rectangle2D bounds,
  -                                                     SVGDocument imgDocument) {
  -
  -        CompositeGraphicsNode result = new CompositeGraphicsNode();
  -
  -        Rectangle2D r = CSSUtilities.convertEnableBackground(e);
  -        if (r != null) {
  -            result.setBackgroundEnable(r);
  -        }
  -
  -        SVGSVGElement svgElement = imgDocument.getRootElement();
  -        GVTBuilder builder = new GVTBuilder();
  -        GraphicsNode node = builder.build(ctx, imgDocument);
  -        // HACK: remove the clip set by the SVGSVGElement as the overflow
  -        // and clip properties must be ignored. The clip will be set later
  -        // using the overflow and clip of the <image> element.
  -        node.setClip(null);
  -        result.getChildren().add(node);
  -
  -        // create the implicit viewBox for the SVG image. The viewBox
  -        // for a SVG image is the viewBox of the outermost SVG element
  -        // of the SVG file
  -        String viewBox =
  -            svgElement.getAttributeNS(null, SVG_VIEW_BOX_ATTRIBUTE);
  -        float [] vb = ViewBox.parseViewBoxAttribute(e, viewBox);
  -        
  -        // handles the 'preserveAspectRatio', 'overflow' and 'clip' and sets 
  -        // the appropriate AffineTransform to the image node
  -
  -        // System.err.println("Bounds: " + bounds);
  -        // System.err.println("ViewBox: " + viewBox);
  -        initializeViewport(e, result, vb, bounds);
  -
  -        return result;
  -    }
  -
  -    /**
  -     * Initializes according to the specified element, the specified graphics
  -     * node with the specified bounds. This method takes into account the
  -     * 'viewBox', 'preserveAspectRatio', and 'clip' properties. According to
  -     * those properties, a AffineTransform and a clip is set.
  -     *
  -     * @param e the image element that defines the properties
  -     * @param node the graphics node
  -     * @param vb the implicit viewBox definition
  -     * @param bounds the bounds of the image element
  -     */
  -    protected static void initializeViewport(Element e,
  -                                             GraphicsNode node,
  -                                             float [] vb,
  -                                             Rectangle2D bounds) {
  -
  -        float x = (float)bounds.getX();
  -        float y = (float)bounds.getY();
  -        float w = (float)bounds.getWidth();
  -        float h = (float)bounds.getHeight();
  -
  -        AffineTransform at
  -            = ViewBox.getPreserveAspectRatioTransform(e, vb, w, h);
  -        // System.err.println("VP Affine: " + at);
  -        at.preConcatenate(AffineTransform.getTranslateInstance(x, y));
  -        node.setTransform(at);
  -
  -        // 'overflow' and 'clip'
  -        Shape clip = null;
  -        if (CSSUtilities.convertOverflow(e)) { // overflow:hidden
  -            float [] offsets = CSSUtilities.convertClip(e);
  -            if (offsets == null) { // clip:auto
  -                clip = new Rectangle2D.Float(x, y, w, h);
  -            } else { // clip:rect(<x> <y> <w> <h>)
  -                // offsets[0] = top
  -                // offsets[1] = right
  -                // offsets[2] = bottom
  -                // offsets[3] = left
  -                clip = new Rectangle2D.Float(x+offsets[3],
  -                                             y+offsets[0],
  -                                             w-offsets[1]-offsets[3],
  -                                             h-offsets[2]-offsets[0]);
  -            }
  -        }
  -
  -        if (clip != null) {
  -            try {
  -                at = at.createInverse(); // clip in user space
  -                Filter filter = node.getGraphicsNodeRable(true);
  -                clip = at.createTransformedShape(clip);
  -                node.setClip(new ClipRable8Bit(filter, clip));
  -            } catch (java.awt.geom.NoninvertibleTransformException ex) {}
  -        }
       }
   }    
   
  
  
  

---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to