001    /*
002     * PatternPaintContext.java
003     *
004     *
005     *  The Salamander Project - 2D and 3D graphics libraries in Java
006     *  Copyright (C) 2004 Mark McKay
007     *
008     *  This library is free software; you can redistribute it and/or
009     *  modify it under the terms of the GNU Lesser General Public
010     *  License as published by the Free Software Foundation; either
011     *  version 2.1 of the License, or (at your option) any later version.
012     *
013     *  This library is distributed in the hope that it will be useful,
014     *  but WITHOUT ANY WARRANTY; without even the implied warranty of
015     *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
016     *  Lesser General Public License for more details.
017     *
018     *  You should have received a copy of the GNU Lesser General Public
019     *  License along with this library; if not, write to the Free Software
020     *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
021     *
022     *  Mark McKay can be contacted at mark@kitfox.com.  Salamander and other
023     *  projects can be found at http://www.kitfox.com
024     *
025     * Created on April 1, 2004, 3:37 AM
026     */
027    
028    package com.kitfox.svg.pattern;
029    
030    import java.awt.*;
031    import java.awt.geom.*;
032    import java.awt.image.*;
033    
034    /**
035     * @author Mark McKay
036     * @author <a href="mailto:mark@kitfox.com">Mark McKay</a>
037     */
038    public class PatternPaintContext implements PaintContext
039    {
040        BufferedImage source;  //Image we're rendering from
041        Rectangle deviceBounds;  //int size of rectangle we're rendering to
042    //    AffineTransform userXform;  //xform from user space to device space
043    //    AffineTransform distortXform;  //distortion applied to this pattern
044    
045        AffineTransform xform;  //distortion applied to this pattern
046    
047        int sourceWidth;
048        int sourceHeight;
049    
050        //Raster we use to build tile
051        BufferedImage buf;
052    
053        /** Creates a new instance of PatternPaintContext */
054        public PatternPaintContext(BufferedImage source, Rectangle deviceBounds, AffineTransform userXform, AffineTransform distortXform)
055        {
056    //System.err.println("Bounds " + deviceBounds);
057            this.source = source;
058            this.deviceBounds = deviceBounds;
059            try {
060    //            this.distortXform = distortXform.createInverse();
061    //            this.userXform = userXform.createInverse();
062    
063    //            xform = userXform.createInverse();
064    //            xform.concatenate(distortXform.createInverse());
065                xform = distortXform.createInverse();
066                xform.concatenate(userXform.createInverse());
067            }
068            catch (Exception e) { e.printStackTrace(); }
069    
070            sourceWidth = source.getWidth();
071            sourceHeight = source.getHeight();
072        }
073    
074        public void dispose() {
075        }
076    
077        public ColorModel getColorModel() {
078            return source.getColorModel();
079        }
080    
081        public Raster getRaster(int x, int y, int w, int h)
082        {
083    //System.err.println("" + x + ", " + y + ", " + w + ", " + h);
084            if (buf == null || buf.getWidth() != w || buf.getHeight() != buf.getHeight())
085            {
086                buf = new BufferedImage(w, h, source.getType());
087            }
088    
089    //        Point2D.Float srcPt = new Point2D.Float(), srcPt2 = new Point2D.Float(), destPt = new Point2D.Float();
090            Point2D.Float srcPt = new Point2D.Float(), destPt = new Point2D.Float();
091            for (int j = 0; j < h; j++)
092            {
093                for (int i = 0; i < w; i++)
094                {
095                    destPt.setLocation(i + x, j + y);
096    
097                    xform.transform(destPt, srcPt);
098    
099    //                userXform.transform(destPt, srcPt2);
100    //                distortXform.transform(srcPt2, srcPt);
101    
102                    int ii = ((int)srcPt.x) % sourceWidth;
103                    if (ii < 0) ii += sourceWidth;
104                    int jj = ((int)srcPt.y) % sourceHeight;
105                    if (jj < 0) jj += sourceHeight;
106    
107                    buf.setRGB(i, j, source.getRGB(ii, jj));
108                }
109            }
110    
111            return buf.getData();
112        }
113    
114        public static void main(String[] argv)
115        {
116            int i = -4;
117            System.err.println("Hello " + (i % 4));
118        }
119    
120    }