A whole lot of widening, refactoring, thinking, rethinking and fiddling around

for what ultimately boils down adding this method to BundledComponentRepository:

    @Override // from IMImageProvider
    public Mirage getTileImage (String path, Rectangle bounds, Colorization[] zations)
    {
        // we don't need our images prepared for screen rendering
        BufferedImage src = _imgr.getImage(getImageKey(path), zations);
        if (bounds != null) {
            src = src.getSubimage(bounds.x, bounds.y, bounds.width, bounds.height);
        }
        return new BufferedMirage(src);
    }

So much fun to revisit code I wrote six years ago.


git-svn-id: svn+ssh://src.earth.threerings.net/nenya/trunk@283 ed5b42cb-e716-0410-a449-f6a68f950b19
This commit is contained in:
Michael Bayne
2007-08-03 22:04:04 +00:00
parent bbd5dd284e
commit 069fe85c70
11 changed files with 390 additions and 486 deletions
+88 -113
View File
@@ -40,20 +40,17 @@ import com.threerings.media.util.MultiFrameImage;
import com.threerings.media.util.MultiFrameImageImpl;
/**
* A tileset stores information on a single logical set of tiles. It
* provides a clean interface for the {@link TileManager} or other
* entities to retrieve individual tiles from the tile set and
* encapsulates the potentially sophisticated process of extracting the
* tile image from a composite tileset image.
* A tileset stores information on a single logical set of tiles. It provides a clean interface for
* the {@link TileManager} or other entities to retrieve individual tiles from the tile set and
* encapsulates the potentially sophisticated process of extracting the tile image from a composite
* tileset image.
*
* <p> Tiles are referenced by their tile id. The tile id is essentially
* the tile number, assuming the tile at the top-left of the image is tile
* id zero and tiles are numbered, in ascending order, left to right, top
* to bottom.
* <p> Tiles are referenced by their tile id. The tile id is essentially the tile number, assuming
* the tile at the top-left of the image is tile id zero and tiles are numbered, in ascending
* order, left to right, top to bottom.
*
* <p> This class is serializable and will be serialized, so derived
* classes should be sure to mark non-persistent fields as
* <code>transient</code>.
* <p> This class is serializable and will be serialized, so derived classes should be sure to mark
* non-persistent fields as <code>transient</code>.
*/
public abstract class TileSet
implements Cloneable, Serializable
@@ -62,19 +59,17 @@ public abstract class TileSet
public static interface Colorizer
{
/**
* Returns the colorization to be used for the specified named
* colorization class.
* Returns the colorization to be used for the specified named colorization class.
*
* @param index the index of the colorization being requested in
* the tileset's colorization list.
* @param index the index of the colorization being requested in the tileset's colorization
* list.
*/
public Colorization getColorization (int index, String zation);
}
/**
* Configures this tileset with an image provider that it can use to
* load its tileset image. This will be called automatically when the
* tileset is fetched via the {@link TileManager}.
* Configures this tileset with an image provider that it can use to load its tileset image.
* This will be called automatically when the tileset is fetched via the {@link TileManager}.
*/
public void setImageProvider (ImageProvider improv)
{
@@ -98,8 +93,8 @@ public abstract class TileSet
}
/**
* Sets the path to the image that will be used by this tileset. This
* must be called before the first call to {@link #getTile}.
* Sets the path to the image that will be used by this tileset. This must be called before the
* first call to {@link #getTile}.
*/
public void setImagePath (String imagePath)
{
@@ -120,8 +115,8 @@ public abstract class TileSet
public abstract int getTileCount ();
/**
* Creates a copy of this tileset which will apply the supplied
* colorizations to its tileset image when creating tiles.
* Creates a copy of this tileset which will apply the supplied colorizations to its tileset
* image when creating tiles.
*/
public TileSet clone (Colorization[] zations)
{
@@ -131,19 +126,16 @@ public abstract class TileSet
return tset;
} catch (CloneNotSupportedException cnse) {
Log.warning("Unable to clone tileset prior to colorization " +
"[tset=" + this +
", zations=" + StringUtil.toString(zations) +
", error=" + cnse + "].");
Log.warning("Unable to clone tileset prior to colorization [tset=" + this +
", zations=" + StringUtil.toString(zations) + ", error=" + cnse + "].");
return null;
}
}
/**
* Returns a new tileset that is a clone of this tileset with the
* image path updated to reference the given path. Useful for
* configuring a single tileset and then generating additional
* tilesets with new images with the same configuration.
* Returns a new tileset that is a clone of this tileset with the image path updated to
* reference the given path. Useful for configuring a single tileset and then generating
* additional tilesets with new images with the same configuration.
*/
public TileSet clone (String imagePath)
throws CloneNotSupportedException
@@ -154,8 +146,20 @@ public abstract class TileSet
}
/**
* Equivalent to {@link #getTile(int,Colorizer)} with a null
* <code>Colorizer</code> argument.
* Computes and fills in the bounds for the specified tile based on the mechanism used by the
* derived class to do such things. The width and height of the bounds should be the size of
* the tile image and the x and y offset should be the offset in the tileset image for the
* image data of the specified tile.
*
* @param tileIndex the index of the tile whose bounds are to be computed.
* @param bounds the rectangle object into which to fill the bounds.
*
* @return the rectangle passed into the bounds parameter.
*/
public abstract Rectangle computeTileBounds (int tileIndex, Rectangle bounds);
/**
* Equivalent to {@link #getTile(int,Colorizer)} with a null <code>Colorizer</code> argument.
*/
public Tile getTile (int tileIndex)
{
@@ -163,17 +167,15 @@ public abstract class TileSet
}
/**
* Creates a {@link Tile} object from this tileset corresponding to
* the specified tile id and returns that tile. A null tile will never
* be returned, but one with an error image may be returned if a
* problem occurs loading the underlying tileset image.
* Creates a {@link Tile} object from this tileset corresponding to the specified tile id and
* returns that tile. A null tile will never be returned, but one with an error image may be
* returned if a problem occurs loading the underlying tileset image.
*
* @param tileIndex the index of the tile in the tileset. Tile indexes
* start with zero as the upper left tile and increase by one as the
* tiles move left to right and top to bottom over the source image.
* @param rizer an entity that will be used to obtain colorizations
* for tilesets that are recolorizable. Passing null if the tileset is
* known not to be recolorizable is valid.
* @param tileIndex the index of the tile in the tileset. Tile indexes start with zero as the
* upper left tile and increase by one as the tiles move left to right and top to bottom over
* the source image.
* @param rizer an entity that will be used to obtain colorizations for tilesets that are
* recolorizable. Passing null if the tileset is known not to be recolorizable is valid.
*
* @return the tile object.
*/
@@ -183,16 +185,15 @@ public abstract class TileSet
}
/**
* Creates a {@link Tile} object from this tileset corresponding to
* the specified tile id and returns that tile. A null tile will never
* be returned, but one with an error image may be returned if a
* problem occurs loading the underlying tileset image.
* Creates a {@link Tile} object from this tileset corresponding to the specified tile id and
* returns that tile. A null tile will never be returned, but one with an error image may be
* returned if a problem occurs loading the underlying tileset image.
*
* @param tileIndex the index of the tile in the tileset. Tile indexes
* start with zero as the upper left tile and increase by one as the
* tiles move left to right and top to bottom over the source image.
* @param zations colorizations to be applied to the tile image prior
* to returning it. These may be null for uncolorized images.
* @param tileIndex the index of the tile in the tileset. Tile indexes start with zero as the
* upper left tile and increase by one as the tiles move left to right and top to bottom over
* the source image.
* @param zations colorizations to be applied to the tile image prior to returning it. These
* may be null for uncolorized images.
*
* @return the tile object.
*/
@@ -200,8 +201,8 @@ public abstract class TileSet
{
Tile tile = null;
// first look in the active set; if it's in use by anyone or in
// the cache, it will be in the active set
// first look in the active set; if it's in use by anyone or in the cache, it will be in
// the active set
synchronized (_atiles) {
_key.tileSet = this;
_key.tileIndex = tileIndex;
@@ -229,10 +230,9 @@ public abstract class TileSet
}
/**
* Returns a prepared version of the image that would be used by the
* tile at the specified index. Because tilesets are often used simply
* to provide access to a collection of uniform images, this method is
* provided to bypass the creation of a {@link Tile} object when all
* Returns a prepared version of the image that would be used by the tile at the specified
* index. Because tilesets are often used simply to provide access to a collection of uniform
* images, this method is provided to bypass the creation of a {@link Tile} object when all
* that is desired is access to the underlying image.
*/
public Mirage getTileMirage (int tileIndex)
@@ -241,36 +241,32 @@ public abstract class TileSet
}
/**
* Returns a prepared version of the image that would be used by the
* tile at the specified index. Because tilesets are often used simply
* to provide access to a collection of uniform images, this method is
* provided to bypass the creation of a {@link Tile} object when all
* Returns a prepared version of the image that would be used by the tile at the specified
* index. Because tilesets are often used simply to provide access to a collection of uniform
* images, this method is provided to bypass the creation of a {@link Tile} object when all
* that is desired is access to the underlying image.
*/
public Mirage getTileMirage (int tileIndex, Colorization[] zations)
{
Rectangle bounds = computeTileBounds(tileIndex);
Rectangle bounds = computeTileBounds(tileIndex, new Rectangle());
Mirage mirage = null;
if (checkTileIndex(tileIndex)) {
if (_improv == null) {
Log.warning("Aiya! Tile set missing image provider " +
"[path=" + _imagePath + "].");
Log.warning("Aiya! Tile set missing image provider [path=" + _imagePath + "].");
} else {
mirage = _improv.getTileImage(_imagePath, bounds, zations);
}
}
if (mirage == null) {
mirage = new BufferedMirage(
ImageUtil.createErrorImage(bounds.width, bounds.height));
mirage = new BufferedMirage(ImageUtil.createErrorImage(bounds.width, bounds.height));
}
return mirage;
}
/**
* Returns the entire, raw, uncut, unprepared tileset source image.
* Don't use this method unless you know what you're doing! This image
* should not be rendered directly to the screen, you should obtain a
* tile ({@link #getTile}), or a tile mirage ({@link #getTileMirage}).
* Returns the entire, raw, uncut, unprepared tileset source image. Don't use this method
* unless you know what you're doing! This image should not be rendered directly to the screen,
* you should obtain a tile ({@link #getTile}), or a tile mirage ({@link #getTileMirage}).
*/
public BufferedImage getRawTileSetImage ()
{
@@ -278,22 +274,20 @@ public abstract class TileSet
}
/**
* Returns the raw (unprepared) image that would be used by the tile
* at the specified index. Don't use this method unless you know what
* you're doing! If you're going to be painting this image onto the
* screen directly, use {@link #getTileMirage} because that prepares
* the image for display. Only use this if you're going to do further
* processing and prepare the subsequent image for display onscreen.
* Returns the raw (unprepared) image that would be used by the tile at the specified
* index. Don't use this method unless you know what you're doing! If you're going to be
* painting this image onto the screen directly, use {@link #getTileMirage} because that
* prepares the image for display. Only use this if you're going to do further processing and
* prepare the subsequent image for display onscreen.
*/
public BufferedImage getRawTileImage (int tileIndex)
{
Rectangle bounds = computeTileBounds(tileIndex);
Rectangle bounds = computeTileBounds(tileIndex, new Rectangle());
BufferedImage img = null;
if (checkTileIndex(tileIndex)) {
BufferedImage timg = getRawTileSetImage();
if (timg != null) {
img = timg.getSubimage(bounds.x, bounds.y,
bounds.width, bounds.height);
img = timg.getSubimage(bounds.x, bounds.y, bounds.width, bounds.height);
} else {
Log.warning("Missing source image " + this);
}
@@ -305,11 +299,10 @@ public abstract class TileSet
}
/**
* Returns colorizations for the specified tile image. The default is
* to return any colorizations associated with the tileset via a call
* to {@link #clone(Colorization[])}, however derived classes may have
* dynamic colorization policies that look up colorization assignments
* from the supplied colorizer.
* Returns colorizations for the specified tile image. The default is to return any
* colorizations associated with the tileset via a call to {@link #clone(Colorization[])},
* however derived classes may have dynamic colorization policies that look up colorization
* assignments from the supplied colorizer.
*/
protected Colorization[] getColorizations (int tileIndex, Colorizer rizer)
{
@@ -325,30 +318,16 @@ public abstract class TileSet
if (tileIndex >= 0 && tileIndex < tcount) {
return true;
} else {
Log.warning("Requested invalid tile [tset=" + this +
", index=" + tileIndex + "].");
Log.warning("Requested invalid tile [tset=" + this + ", index=" + tileIndex + "].");
Thread.dumpStack();
return false;
}
}
/**
* Computes and returns the bounds for the specified tile based on the
* mechanism used by the derived class to do such things. The width
* and height of the bounds should be the size of the tile image and
* the x and y offset should be the offset in the tileset image for
* the image data of the specified tile.
*
* @param tileIndex the index of the tile whose bounds are to be
* computed.
*/
protected abstract Rectangle computeTileBounds (int tileIndex);
/**
* Creates a blank tile of the appropriate type for this tileset.
*
* @return a blank tile ready to be populated with its image and
* metadata.
* @return a blank tile ready to be populated with its image and metadata.
*/
protected Tile createTile ()
{
@@ -356,14 +335,12 @@ public abstract class TileSet
}
/**
* Initializes the supplied tile. Derived classes can override this
* method to add in their own tile information, but should be sure to
* call <code>super.initTile()</code>.
* Initializes the supplied tile. Derived classes can override this method to add in their own
* tile information, but should be sure to call <code>super.initTile()</code>.
*
* @param tile the tile to initialize.
* @param tileIndex the index of the tile.
* @param zations the colorizations to be used when generating the
* tile image.
* @param zations the colorizations to be used when generating the tile image.
*/
protected void initTile (Tile tile, int tileIndex, Colorization[] zations)
{
@@ -383,8 +360,8 @@ public abstract class TileSet
}
/**
* Reports statistics detailing the image manager cache performance
* and the current size of the cached images.
* Reports statistics detailing the image manager cache performance and the current size of the
* cached images.
*/
protected void reportCachePerformance ()
{
@@ -415,9 +392,8 @@ public abstract class TileSet
}
/**
* Derived classes can override this, calling
* <code>super.toString(buf)</code> and then appending additional
* information to the buffer.
* Derived classes can override this, calling <code>super.toString(buf)</code> and then
* appending additional information to the buffer.
*/
protected void toString (StringBuilder buf)
{
@@ -445,8 +421,7 @@ public abstract class TileSet
/** A map containing weak references to all "active" tiles. */
protected static HashMap _atiles = new HashMap();
/** A key used to look things up in the cache without creating
* craploads of keys unduly. */
/** A key used to look things up in the cache without creating craploads of keys unduly. */
protected static Tile.Key _key = new Tile.Key(null, 0, null);
/** Throttle our cache status logging to once every 300 seconds. */