
com.threerings.media.image.TransformedMirage Maven / Gradle / Ivy
//
// Nenya library - tools for developing networked games
// Copyright (C) 2002-2012 Three Rings Design, Inc., All Rights Reserved
// https://github.com/threerings/nenya
//
// This library is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published
// by the Free Software Foundation; either version 2.1 of the License, or
// (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
package com.threerings.media.image;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.geom.AffineTransform;
import java.awt.geom.NoninvertibleTransformException;
import java.awt.image.BufferedImage;
/**
* Draws a mirage combined with an arbitrary AffineTransform.
*/
public class TransformedMirage
implements Mirage
{
/**
* Constructor for backwards compatibility that automatically repositions the transformed
* mirage so its new upper-left corner is still at the origin.
*/
public TransformedMirage (Mirage base, AffineTransform transform)
{
this(base, transform, true);
}
/**
* Constructor.
*/
public TransformedMirage (Mirage base, AffineTransform transform, boolean reposition)
{
_base = base;
// clone the transform so that it doesn't get changed on us.
_transform = (AffineTransform) transform.clone();
computeTransformedBounds();
if (reposition) {
_transform.preConcatenate(
AffineTransform.getTranslateInstance(-_bounds.x, -_bounds.y));
}
}
// documentation inherited from interface Mirage
public void paint (Graphics2D gfx, int x, int y)
{
AffineTransform otrans = gfx.getTransform();
gfx.translate(x, y);
gfx.transform(_transform);
_base.paint(gfx, 0, 0);
gfx.setTransform(otrans);
}
// documentation inherited from interface Mirage
public int getWidth ()
{
return _bounds.width;
}
// documentation inherited from interface Mirage
public int getHeight ()
{
return _bounds.height;
}
// documentation inherited from interface Mirage
public boolean hitTest (int x, int y)
{
Point p = new Point(x, y);
try {
_transform.createInverse().transform(p, p);
return _base.hitTest(p.x, p.y);
} catch (NoninvertibleTransformException nte) {
// grumble, grumble
// TODO: log something?
return ImageUtil.hitTest(getSnapshot(), x, y);
}
}
// documentation inherited from interface Mirage
public BufferedImage getSnapshot ()
{
BufferedImage baseSnap = _base.getSnapshot();
BufferedImage img = new BufferedImage(_bounds.width, _bounds.height,
baseSnap.getType());
Graphics2D gfx = (Graphics2D) img.getGraphics();
try {
gfx.transform(_transform);
gfx.drawImage(baseSnap, 0, 0, null);
} finally {
gfx.dispose();
}
return img;
}
// documentation inherited from interface Mirage
public long getEstimatedMemoryUsage ()
{
return _base.getEstimatedMemoryUsage();
}
/**
* Compute the bounds of the base Mirage after it has been transformed.
*/
protected void computeTransformedBounds ()
{
int w = _base.getWidth();
int h = _base.getHeight();
Point[] points = new Point[] {
new Point(0, 0), new Point(w, 0), new Point(0, h), new Point(w, h) };
_transform.transform(points, 0, points, 0, 4);
int minX, minY, maxX, maxY;
minX = minY = Integer.MAX_VALUE;
maxX = maxY = Integer.MIN_VALUE;
for (int ii=0; ii < 4; ii++) {
minX = Math.min(minX, points[ii].x);
maxX = Math.max(maxX, points[ii].x);
minY = Math.min(minY, points[ii].y);
maxY = Math.max(maxY, points[ii].y);
}
_bounds = new Rectangle(minX, minY, maxX - minX, maxY - minY);
}
/** The base mirage. */
protected Mirage _base;
/** Our transformed bounds. */
protected Rectangle _bounds;
/** The transform we apply when painting the base mirage. */
protected AffineTransform _transform;
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy