Revamped BundledTileSetRepository to make it easier to add bundles on the

fly in the future; it also now provides efficient tileset name to tileset
id mappings which is exported via the TileSetRepository interface. Lastly,
TileManager now relies on TileSetRepository to efficiently provide tiles
by name or id and no longer maintains its own cache (because the
BundledTileSetRepository already maintains the same mappings).


git-svn-id: svn+ssh://src.earth.threerings.net/narya/trunk@2663 542714f4-19e9-0310-aa3c-eee0fc999fb1
This commit is contained in:
Michael Bayne
2003-06-18 05:48:45 +00:00
parent 572570de75
commit cbe229ccb7
3 changed files with 80 additions and 101 deletions
@@ -1,5 +1,5 @@
// //
// $Id: TileManager.java,v 1.33 2003/05/13 21:33:58 ray Exp $ // $Id: TileManager.java,v 1.34 2003/06/18 05:48:45 mdb Exp $
package com.threerings.media.tile; package com.threerings.media.tile;
@@ -130,16 +130,6 @@ public class TileManager
return _setrep; return _setrep;
} }
/**
* Adds a tileset to be recognized by the specified id. Note that this
* tileset registration will override any tileset in the repository
* with the same id. Be very careful!
*/
public void addTileSet (int tileSetId, TileSet set)
{
_setcache.put(tileSetId, set);
}
/** /**
* Returns the tileset with the specified id. Tilesets are fetched * Returns the tileset with the specified id. Tilesets are fetched
* from the tileset repository supplied via {@link * from the tileset repository supplied via {@link
@@ -160,13 +150,7 @@ public class TileManager
} }
try { try {
TileSet set = (TileSet)_setcache.get(tileSetId); return _setrep.getTileSet(tileSetId);
if (set == null) {
set = _setrep.getTileSet(tileSetId);
_setcache.put(tileSetId, set);
}
return set;
} catch (PersistenceException pe) { } catch (PersistenceException pe) {
Log.warning("Failure loading tileset [id=" + tileSetId + Log.warning("Failure loading tileset [id=" + tileSetId +
", error=" + pe + "]."); ", error=" + pe + "].");
@@ -189,16 +173,7 @@ public class TileManager
} }
try { try {
TileSet set = (TileSet)_byname.get(name); return _setrep.getTileSet(name);
if (set == null) {
set = _setrep.getTileSet(name);
if (set == null) {
throw new NoSuchTileSetException(name);
}
_byname.put(name, set);
}
return set;
} catch (PersistenceException pe) { } catch (PersistenceException pe) {
Log.warning("Failure loading tileset [name=" + name + Log.warning("Failure loading tileset [name=" + name +
", error=" + pe + "]."); ", error=" + pe + "].");
@@ -251,15 +226,9 @@ public class TileManager
/** The entity through which we decode and cache images. */ /** The entity through which we decode and cache images. */
protected ImageManager _imgr; protected ImageManager _imgr;
/** Cache of tilesets that have been requested thus far. */
protected HashIntMap _setcache = new HashIntMap();
/** A cache of tilesets that have been loaded by hand. */ /** A cache of tilesets that have been loaded by hand. */
protected HashMap _handcache = new HashMap(); protected HashMap _handcache = new HashMap();
/** A mapping from tileset name to tileset. */
protected HashMap _byname = new HashMap();
/** The tile set repository. */ /** The tile set repository. */
protected TileSetRepository _setrep; protected TileSetRepository _setrep;
@@ -1,5 +1,5 @@
// //
// $Id: TileSetRepository.java,v 1.4 2003/01/13 22:49:46 mdb Exp $ // $Id: TileSetRepository.java,v 1.5 2003/06/18 05:48:45 mdb Exp $
package com.threerings.media.tile; package com.threerings.media.tile;
@@ -42,6 +42,18 @@ public interface TileSetRepository
public TileSet getTileSet (int tileSetId) public TileSet getTileSet (int tileSetId)
throws NoSuchTileSetException, PersistenceException; throws NoSuchTileSetException, PersistenceException;
/**
* Returns the unique identifier of the {@link TileSet} with the
* specified tile set name.
*
* @exception NoSuchTileSetException thrown if no tileset exists with
* the specified name.
* @exception PersistenceException thrown if an error occurs
* communicating with the underlying persistence mechanism.
*/
public int getTileSetId (String setName)
throws NoSuchTileSetException, PersistenceException;
/** /**
* Returns the {@link TileSet} with the specified tile set name. The * Returns the {@link TileSet} with the specified tile set name. The
* repository is responsible for configuring the tile set with an * repository is responsible for configuring the tile set with an
@@ -1,16 +1,16 @@
// //
// $Id: BundledTileSetRepository.java,v 1.11 2003/04/01 19:33:07 mdb Exp $ // $Id: BundledTileSetRepository.java,v 1.12 2003/06/18 05:48:45 mdb Exp $
package com.threerings.media.tile.bundle; package com.threerings.media.tile.bundle;
import java.io.IOException; import java.io.IOException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator; import java.util.Iterator;
import com.samskivert.io.PersistenceException; import com.samskivert.io.PersistenceException;
import com.samskivert.util.CompoundIterator; import com.samskivert.util.HashIntMap;
import com.samskivert.util.CompoundIterator.IteratorProvider;
import com.threerings.resource.ResourceBundle; import com.threerings.resource.ResourceBundle;
import com.threerings.resource.ResourceManager; import com.threerings.resource.ResourceManager;
@@ -47,10 +47,12 @@ public class BundledTileSetRepository
final ImageManager imgr, final ImageManager imgr,
final String name) final String name)
{ {
_imgr = imgr;
// unpack our bundles in the background // unpack our bundles in the background
new Thread(new Runnable() { new Thread(new Runnable() {
public void run () { public void run () {
initBundles(rmgr, imgr, name); initBundles(rmgr, name);
} }
}).start(); }).start();
} }
@@ -58,8 +60,7 @@ public class BundledTileSetRepository
/** /**
* Initializes our bundles, * Initializes our bundles,
*/ */
protected void initBundles ( protected void initBundles (ResourceManager rmgr, String name)
ResourceManager rmgr, ImageManager imgr, String name)
{ {
// first we obtain the resource set from which we will load up our // first we obtain the resource set from which we will load up our
// tileset bundles // tileset bundles
@@ -70,10 +71,12 @@ public class BundledTileSetRepository
Log.warning("Unable to fetch tileset resource set " + Log.warning("Unable to fetch tileset resource set " +
"[name=" + name + "]. Perhaps it's not defined " + "[name=" + name + "]. Perhaps it's not defined " +
"in the resource manager config?"); "in the resource manager config?");
_bundles = new TileSetBundle[0];
return; return;
} }
HashIntMap idmap = new HashIntMap();
HashMap namemap = new HashMap();
// iterate over the resource bundles in the set, loading up the // iterate over the resource bundles in the set, loading up the
// tileset bundles in each resource bundle // tileset bundles in each resource bundle
ArrayList tbundles = new ArrayList(); ArrayList tbundles = new ArrayList();
@@ -83,7 +86,7 @@ public class BundledTileSetRepository
TileSetBundle tsb = BundleUtil.extractBundle(rbundles[i]); TileSetBundle tsb = BundleUtil.extractBundle(rbundles[i]);
// initialize it and add it to the list // initialize it and add it to the list
tsb.init(rbundles[i]); tsb.init(rbundles[i]);
tbundles.add(tsb); addBundle(idmap, namemap, tsb);
} catch (Exception e) { } catch (Exception e) {
Log.warning("Unable to load tileset bundle '" + Log.warning("Unable to load tileset bundle '" +
@@ -94,38 +97,40 @@ public class BundledTileSetRepository
} }
} }
// finally create one big fat array of all of the tileset bundles
TileSetBundle[] bundles = new TileSetBundle[tbundles.size()];
tbundles.toArray(bundles);
// create image providers for our bundles
_improvs = new IMImageProvider[bundles.length];
for (int ii = 0; ii < bundles.length; ii++) {
_improvs[ii] = new IMImageProvider(imgr, bundles[ii]);
}
// fill in our bundles array and wake up any waiters // fill in our bundles array and wake up any waiters
synchronized (this) { synchronized (this) {
_bundles = bundles; _idmap = idmap;
_namemap = namemap;
notifyAll(); notifyAll();
} }
} }
/**
* Adds the tilesets in the supplied bundle to our tileset mapping
* tables. Any tilesets with the same name or id will be overwritten.
*/
protected void addBundle (HashIntMap idmap, HashMap namemap,
TileSetBundle bundle)
{
IMImageProvider improv = new IMImageProvider(_imgr, bundle);
// map all of the tilesets in this bundle
for (Iterator iter = bundle.entrySet().iterator(); iter.hasNext(); ) {
HashIntMap.Entry entry = (HashIntMap.Entry)iter.next();
Integer tsid = (Integer)entry.getKey();
TileSet tset = (TileSet)entry.getValue();
tset.setImageProvider(improv);
idmap.put(tsid.intValue(), tset);
namemap.put(tset.getName(), tsid);
}
}
// documentation inherited from interface // documentation inherited from interface
public Iterator enumerateTileSetIds () public Iterator enumerateTileSetIds ()
throws PersistenceException throws PersistenceException
{ {
waitForBundles(); waitForBundles();
return new CompoundIterator(new IteratorProvider() { return _idmap.keySet().iterator();
public Iterator nextIterator () {
if (_bidx < _bundles.length) {
return _bundles[_bidx++].enumerateTileSetIds();
} else {
return null;
}
}
protected int _bidx = 0;
});
} }
// documentation inherited from interface // documentation inherited from interface
@@ -133,16 +138,7 @@ public class BundledTileSetRepository
throws PersistenceException throws PersistenceException
{ {
waitForBundles(); waitForBundles();
return new CompoundIterator(new IteratorProvider() { return _idmap.values().iterator();
public Iterator nextIterator () {
if (_bidx < _bundles.length) {
return _bundles[_bidx++].enumerateTileSets();
} else {
return null;
}
}
protected int _bidx = 0;
});
} }
// documentation inherited from interface // documentation inherited from interface
@@ -150,16 +146,23 @@ public class BundledTileSetRepository
throws NoSuchTileSetException, PersistenceException throws NoSuchTileSetException, PersistenceException
{ {
waitForBundles(); waitForBundles();
TileSet tset = null; TileSet tset = (TileSet)_idmap.get(tileSetId);
int blength = _bundles.length; if (tset == null) {
for (int i = 0; i < blength; i++) { throw new NoSuchTileSetException(tileSetId);
tset = _bundles[i].getTileSet(tileSetId);
if (tset != null) {
tset.setImageProvider(_improvs[i]);
return tset;
}
} }
throw new NoSuchTileSetException(tileSetId); return tset;
}
// documentation inherited from interface
public int getTileSetId (String setName)
throws NoSuchTileSetException, PersistenceException
{
waitForBundles();
Integer tsid = (Integer)_namemap.get(setName);
if (tsid != null) {
return tsid.intValue();
}
throw new NoSuchTileSetException(setName);
} }
// documentation inherited from interface // documentation inherited from interface
@@ -167,26 +170,18 @@ public class BundledTileSetRepository
throws NoSuchTileSetException, PersistenceException throws NoSuchTileSetException, PersistenceException
{ {
waitForBundles(); waitForBundles();
int bcount = _bundles.length; TileSet tset = null;
for (int ii = 0; ii < bcount; ii++) { Integer tsid = (Integer)_namemap.get(setName);
TileSetBundle tsb = _bundles[ii]; if (tsid != null) {
// search for the tileset in this bundle return getTileSet(tsid.intValue());
Iterator tsiter = tsb.enumerateTileSets();
while (tsiter.hasNext()) {
TileSet set = (TileSet)tsiter.next();
if (set.getName().equals(setName)) {
set.setImageProvider(_improvs[ii]);
return set;
}
}
} }
return null; throw new NoSuchTileSetException(setName);
} }
/** Used to allow bundle unpacking to proceed asynchronously. */ /** Used to allow bundle unpacking to proceed asynchronously. */
protected synchronized void waitForBundles () protected synchronized void waitForBundles ()
{ {
while (_bundles == null) { while (_idmap == null) {
try { try {
wait(); wait();
} catch (InterruptedException ie) { } catch (InterruptedException ie) {
@@ -195,9 +190,12 @@ public class BundledTileSetRepository
} }
} }
/** An array of tileset bundles from which we obtain tilesets. */ /** The image manager via which we load our images. */
protected TileSetBundle[] _bundles; protected ImageManager _imgr;
/** Image providers for each of our tile set bundles. */ /** A mapping from tileset id to tileset. */
protected IMImageProvider[] _improvs; protected HashIntMap _idmap;
/** A mapping from tileset name to tileset id. */
protected HashMap _namemap;
} }