Rather than loading all the base tiles at once (or really, all the ones in an arbitrary region), we'll load only the ones on-screen. And then if we scroll around, we'll load the others we need.

git-svn-id: svn+ssh://src.earth.threerings.net/nenya/trunk@941 ed5b42cb-e716-0410-a449-f6a68f950b19
This commit is contained in:
Mike Thomas
2010-07-09 00:18:06 +00:00
parent 78f64d2c66
commit 64bbf9f9d8
@@ -48,6 +48,12 @@ import com.threerings.crowd.client.PlaceView;
import com.threerings.crowd.data.PlaceObject;
import com.threerings.util.DelayUtil;
import com.threerings.util.Log;
import com.threerings.util.Map;
import com.threerings.util.Maps;
import com.threerings.util.MathUtil;
import com.threerings.util.Set;
import com.threerings.util.Sets;
import com.threerings.util.StringUtil;
import com.threerings.media.tile.Colorizer;
import com.threerings.media.tile.NoSuchTileSetError;
import com.threerings.media.tile.TileSet;
@@ -114,6 +120,7 @@ public class MisoScenePanel extends Sprite
var viewPt :Point = _isoView.globalToLocal(new Point(event.stageX, event.stageY));
_isoView.centerOnPt(new Pt(viewPt.x - _isoView.width / 2 + _isoView.currentX,
viewPt.y - _isoView.height / 2 + _isoView.currentY), false);
refreshBaseBlockScenes();
}
public function setSceneModel (model :MisoSceneModel) :void
@@ -136,21 +143,76 @@ public class MisoScenePanel extends Sprite
{
}
protected function refreshScene () :void
protected function getBaseBlocks () :Set
{
// Clear it out...
_isoView.removeAllScenes();
var blocks :Set = Sets.newSetOf(int);
var scene :IsoScene = new IsoScene();
scene.layoutRenderer = new ClassFactory(PrioritizedSceneLayoutRenderer);
var time :int = getTimer();
var baseArr :Array = [];
var size :Point = _isoView.size;
var topLeft :Point = _isoView.localToIso(new Point(0, 0));
var topRight :Point = _isoView.localToIso(new Point(size.x, 0));
var btmLeft :Point = _isoView.localToIso(new Point(0, size.y));
var btmRight :Point = _isoView.localToIso(new Point(size.x, size.y));
for (var yy :int = topRight.y - 1; yy <= btmLeft.y + 1; yy++) {
for (var xx :int = topLeft.x - 1; xx <= btmRight.x + 1; xx++) {
// Toss out any that aren't actually in our view.
var blkTop :Point = _isoView.isoToLocal(new Pt(xx, yy, 0));
var blkRight :Point = _isoView.isoToLocal(new Pt(xx + BLOCK_SIZE, yy, 0));
var blkLeft :Point = _isoView.isoToLocal(new Pt(xx, yy + BLOCK_SIZE, 0));
var blkBtm :Point =
_isoView.isoToLocal(new Pt(xx + BLOCK_SIZE, yy + BLOCK_SIZE, 0));
if (blkTop.y < size.y &&
blkBtm.y > 0 &&
blkLeft.x < size.x &&
blkRight.x > 0) {
blocks.add(getBlockKey(xx, yy));
}
}
}
return blocks;
}
protected function getBlockKey (x :int, y :int) :int
{
return (MathUtil.floorDiv(x, BLOCK_SIZE) << 16 |
(MathUtil.floorDiv(y, BLOCK_SIZE) & 0xFFFF));
}
protected function getBlockX (key :int) :int
{
return (key >> 16) * BLOCK_SIZE;
}
protected function getBlockY (key :int) :int
{
// We really do mean to do this crazy shift left then back right thing to get our sign
// back from before we encoded.
return (((key & 0xFFFF) * BLOCK_SIZE) << 16) >> 16;
}
protected function refreshBaseBlockScenes () :void
{
var blocks :Set = getBaseBlocks();
// Take out any scenes no longer in our valid blocks.
for each (var baseKey :int in _baseScenes.keys()) {
if (!blocks.contains(baseKey)) {
// It's not valid anymore, so toss it.
_isoView.removeScene(_baseScenes.remove(baseKey));
}
}
blocks.forEach(function(blockKey :int) :void {
if (!_baseScenes.containsKey(blockKey)) {
// Not already in there, let's create and add it.
var x :int = getBlockX(blockKey);
var y :int = getBlockY(blockKey);
for (var si :int = -2; si < 4; si++) {
for (var sj :int = -1; sj < 3; sj++) {
var baseScene :IsoScene = new IsoScene();
for (var ii :int = 10*si; ii < 10*si + 10; ii++) {
for (var jj :int = 10*sj; jj < 10*sj + 10; jj++) {
for (var ii :int = x; ii < x + BLOCK_SIZE; ii++) {
for (var jj :int = y; jj < y + BLOCK_SIZE; jj++) {
var tileId :int = _model.getBaseTileId(ii, jj);
if (tileId <= 0) {
var defSet :TileSet;
@@ -186,14 +248,27 @@ public class MisoScenePanel extends Sprite
}
}
baseScene.render();
_isoView.addScene(baseScene);
_isoView.addSceneAt(baseScene, 0);
_baseScenes.put(blockKey, baseScene);
}
}
});
}
protected function refreshScene () :void
{
// Clear it out...
_isoView.removeAllScenes();
var scene :IsoScene = new IsoScene();
scene.layoutRenderer = new ClassFactory(PrioritizedSceneLayoutRenderer);
var time :int = getTimer();
refreshBaseBlockScenes();
var set :ObjectSet = new ObjectSet();
_model.getObjects(new Rectangle(-100, -100, 200, 200), set);
time = getTimer();
for (ii = 0; ii < set.size(); ii++) {
for (var ii :int = 0; ii < set.size(); ii++) {
var objInfo :ObjectInfo = set.get(ii);
var objTileId :int = objInfo.tileId;
var objTileSet :TileSet;
@@ -246,7 +321,11 @@ public class MisoScenePanel extends Sprite
/** If we should do something when we hear about progress updates, this is it. */
protected var _loadingProgressFunc :Function;
protected var _baseScenes :Map = Maps.newMapOf(int);
protected const DEF_WIDTH :int = 985;
protected const DEF_HEIGHT :int = 560;
protected const BLOCK_SIZE :int = 4;
}
}