Files
narya/src/java/com/threerings/miso/client/IsoSceneViewModel.java
T
Walter Korman c7d26cea8e Fixed scene rendering issues and improved performance.
git-svn-id: svn+ssh://src.earth.threerings.net/narya/trunk@517 542714f4-19e9-0310-aa3c-eee0fc999fb1
2001-10-22 18:21:42 +00:00

302 lines
9.3 KiB
Java

//
// $Id: IsoSceneViewModel.java,v 1.16 2001/10/22 18:21:41 shaper Exp $
package com.threerings.miso.scene;
import java.awt.Rectangle;
import java.awt.Point;
import java.util.ArrayList;
import com.samskivert.util.Config;
import com.threerings.miso.Log;
import com.threerings.miso.scene.util.IsoUtil;
import com.threerings.miso.util.MisoUtil;
/**
* The iso scene view model provides a holding place for the myriad
* parameters and bits of data that describe the details of an
* isometric view of a scene.
*
* <p> The member data are public to facilitate speedy referencing by
* the {@link IsoSceneView} class. The model should only be modified
* through the constructor's passed-in {@link
* com.samskivert.util.Config} object and the accessor methods.
*/
public class IsoSceneViewModel
{
/** Tile dimensions and half-dimensions in the view. */
public int tilewid, tilehei, tilehwid, tilehhei;
/** Fine coordinate dimensions. */
public int finehwid, finehhei;
/** Number of fine coordinates on each axis within a tile. */
public int finegran;
/** Scene dimensions in tile count. */
public int scenewid, scenehei;
/** The bounds of the view in screen pixel coordinates. */
public Rectangle bounds;
/** The position in pixels at which tile (0, 0) is drawn. */
public Point origin;
/** The total number of tile rows to render the full view. */
public int tilerows;
/** The length of a tile edge in pixels. */
public float tilelen;
/** The y-intercept of the x-axis line. */
public int bX;
/** The slope of the x- and y-axis lines. */
public float slopeX, slopeY;
/** The x-axis line. */
public Point lineX[];
/** The length between fine coordinates in pixels. */
public float finelen;
/** The y-intercept of the x-axis line within a tile. */
public float fineBX;
/** The slope of the x- and y-axis lines within a tile. */
public float fineSlopeX, fineSlopeY;
/** Whether tile coordinates should be drawn. */
public boolean showCoords;
/** Whether locations in the scene should be drawn. */
public boolean showLocs;
/** Whether sprite paths should be drawn. */
public boolean showPaths;
/**
* Construct an iso scene view model with view parameters as
* specified in the given config object.
*
* @param config the config object.
*/
public IsoSceneViewModel (Config config)
{
// set the scene tile dimensions
scenewid = config.getValue(SCENE_WIDTH_KEY, DEF_SCENE_WIDTH);
scenehei = config.getValue(SCENE_HEIGHT_KEY, DEF_SCENE_HEIGHT);
// get the tile dimensions
tilewid = config.getValue(TILE_WIDTH_KEY, DEF_TILE_WIDTH);
tilehei = config.getValue(TILE_HEIGHT_KEY, DEF_TILE_HEIGHT);
// set the fine coordinate granularity
finegran = config.getValue(FINE_GRAN_KEY, DEF_FINE_GRAN);
// set the desired scene view bounds
int svwid = config.getValue(SCENE_VWIDTH_KEY, DEF_SCENE_VWIDTH);
int svhei = config.getValue(SCENE_VHEIGHT_KEY, DEF_SCENE_VHEIGHT);
bounds = new Rectangle(0, 0, svwid * tilewid, svhei * tilehei);
// set the scene display origin
int offy = config.getValue(SCENE_OFFSET_Y_KEY, DEF_OFFSET_Y);
origin = new Point((bounds.width / 2), (offy * tilehei));
// set our various flags
showCoords = config.getValue(SHOW_COORDS_KEY, DEF_SHOW_COORDS);
showLocs = config.getValue(SHOW_COORDS_KEY, DEF_SHOW_COORDS);
showPaths = config.getValue(SHOW_PATHS_KEY, DEF_SHOW_PATHS);
}
/**
* Add an iso scene view model listener.
*
* @param l the listener.
*/
public void addListener (IsoSceneViewModelListener l)
{
if (!_listeners.contains(l)) {
_listeners.add(l);
}
}
/**
* Notify all model listeners that the iso scene view model has
* changed.
*/
protected void notifyListeners (int event)
{
int size = _listeners.size();
for (int ii = 0; ii < size; ii++) {
((IsoSceneViewModelListener)_listeners.get(ii)).
viewChanged(event);
}
}
/**
* Returns whether the given tile coordinate is a valid coordinate
* within the scene.
*/
public boolean isCoordinateValid (int x, int y)
{
return (x >= 0 && x < scenewid &&
y >= 0 && y < scenehei);
}
/**
* Returns whether the given full coordinate is a valid coordinate
* within the scene.
*/
public boolean isFullCoordinateValid (int x, int y)
{
int tx = IsoUtil.fullToTile(x), ty = IsoUtil.fullToTile(y);
int fx = IsoUtil.fullToFine(x), fy = IsoUtil.fullToFine(y);
return (isCoordinateValid(tx, ty) &&
fx >= 0 && fx < finegran &&
fy >= 0 && fy < finegran);
}
/**
* Toggle whether locations in the scene should be drawn.
*/
public void toggleShowLocations ()
{
showLocs = !showLocs;
notifyListeners(IsoSceneViewModelListener.SHOW_LOCATIONS_CHANGED);
}
/**
* Toggle whether coordinates should be drawn for each tile.
*/
public void toggleShowCoordinates ()
{
showCoords = !showCoords;
notifyListeners(IsoSceneViewModelListener.SHOW_COORDINATES_CHANGED);
}
/**
* Pre-calculate various member data that are commonly used in
* working with an isometric view.
*/
public void precalculate ()
{
// pre-calculate tile-related data
precalculateTiles();
// calculate scene-based x-axis line for conversion from
// screen to tile coordinates
// create the x- and y-axis lines
lineX = new Point[2];
for (int ii = 0; ii < 2; ii++) {
lineX[ii] = new Point();
}
// determine the starting point
lineX[0].setLocation(origin.x, origin.y);
bX = (int)-(slopeX * origin.x);
// determine the ending point
lineX[1].x = lineX[0].x + (tilehwid * scenewid);
lineX[1].y = lineX[0].y + (int)((slopeX * lineX[1].x) + bX);
// calculate tile-based x-axis line for conversion from
// tile-based pixel to fine coordinates
// calculate the edge length separating each fine coordinate
finelen = tilelen / (float)finegran;
// calculate the fine-coordinate x-axis line
fineSlopeX = (float)tilehei / (float)tilewid;
fineBX = -(fineSlopeX * (float)tilehwid);
fineSlopeY = -fineSlopeX;
// calculate the fine coordinate dimensions
finehwid = (int)((float)tilehwid / (float)finegran);
finehhei = (int)((float)tilehhei / (float)finegran);
}
/**
* Pre-calculate various tile-related member data.
*/
protected void precalculateTiles ()
{
// halve the dimensions
tilehwid = (tilewid / 2);
tilehhei = (tilehei / 2);
// calculate the length of a tile edge in pixels
tilelen = (float) Math.sqrt(
(tilehwid * tilehwid) + (tilehhei * tilehhei));
// calculate the number of tile rows to render
tilerows = (scenewid * scenehei) - 1;
// calculate the slope of the x- and y-axis lines
slopeX = (float)tilehei / (float)tilewid;
slopeY = -slopeX;
}
/** The config key for tile width in pixels. */
protected static final String TILE_WIDTH_KEY =
MisoUtil.CONFIG_KEY + ".tile_width";
/** The config key for tile height in pixels. */
protected static final String TILE_HEIGHT_KEY =
MisoUtil.CONFIG_KEY + ".tile_height";
/** The config key for tile fine coordinate granularity. */
protected static final String FINE_GRAN_KEY =
MisoUtil.CONFIG_KEY + ".fine_granularity";
/** The config key for scene view width in tile count. */
protected static final String SCENE_VWIDTH_KEY =
MisoUtil.CONFIG_KEY + ".scene_view_width";
/** The config key for scene view height in tile count. */
protected static final String SCENE_VHEIGHT_KEY =
MisoUtil.CONFIG_KEY + ".scene_view_height";
/** The config key for scene width in tile count. */
protected static final String SCENE_WIDTH_KEY =
MisoUtil.CONFIG_KEY + ".scene_width";
/** The config key for scene height in tile count. */
protected static final String SCENE_HEIGHT_KEY =
MisoUtil.CONFIG_KEY + ".scene_height";
/** The config key for scene origin vertical offset in tile count. */
protected static final String SCENE_OFFSET_Y_KEY =
MisoUtil.CONFIG_KEY + ".scene_offset_y";
/** The config key for whether to show tile coordinates. */
protected static final String SHOW_COORDS_KEY =
MisoUtil.CONFIG_KEY + ".show_coords";
/** The config key for whether to show locations. */
protected static final String SHOW_LOCS_KEY =
MisoUtil.CONFIG_KEY + ".show_locs";
/** The config key for whether to show sprite paths. */
protected static final String SHOW_PATHS_KEY =
MisoUtil.CONFIG_KEY + ".show_paths";
/** Default scene view parameters. */
protected static final int DEF_TILE_WIDTH = 64;
protected static final int DEF_TILE_HEIGHT = 48;
protected static final int DEF_FINE_GRAN = 4;
protected static final int DEF_SCENE_VWIDTH = 10;
protected static final int DEF_SCENE_VHEIGHT = 12;
protected static final int DEF_SCENE_WIDTH = 22;
protected static final int DEF_SCENE_HEIGHT = 22;
protected static final int DEF_OFFSET_Y = -5;
protected static final boolean DEF_SHOW_COORDS = false;
protected static final boolean DEF_SHOW_LOCS = false;
protected static final boolean DEF_SHOW_PATHS = false;
/** The model listeners. */
protected ArrayList _listeners = new ArrayList();
}