One step back, two steps forward. Fixed the media manager so that once

again, things added on the current tick are ticked and painted on that
tick, but cleaned things up so that we don't choke if things are added or
removed from funny places.


git-svn-id: svn+ssh://src.earth.threerings.net/narya/trunk@2187 542714f4-19e9-0310-aa3c-eee0fc999fb1
This commit is contained in:
Michael Bayne
2003-01-18 20:14:03 +00:00
parent 99d66fe5c6
commit fe2364e01a
@@ -1,5 +1,5 @@
// //
// $Id: AbstractMediaManager.java,v 1.5 2003/01/18 03:14:29 mdb Exp $ // $Id: AbstractMediaManager.java,v 1.6 2003/01/18 20:14:03 mdb Exp $
package com.threerings.media; package com.threerings.media;
@@ -50,12 +50,8 @@ public abstract class AbstractMediaManager
*/ */
public void renderMedia (Graphics2D gfx, int layer, Shape clip) public void renderMedia (Graphics2D gfx, int layer, Shape clip)
{ {
for (int ii = 0, nn = _tickvec.length; ii < nn; ii++) { for (int ii = 0, nn = _media.size(); ii < nn; ii++) {
AbstractMedia media = _tickvec[ii]; AbstractMedia media = (AbstractMedia)_media.get(ii);
if (_tickvec[ii] == null) {
continue;
}
int order = media.getRenderOrder(); int order = media.getRenderOrder();
try { try {
if (((layer == ALL) || if (((layer == ALL) ||
@@ -94,6 +90,11 @@ public abstract class AbstractMediaManager
*/ */
public void fastForward (long timeDelta) public void fastForward (long timeDelta)
{ {
if (_tickStamp > 0) {
Log.warning("Egads! Asked to fastForward() during a tick.");
Thread.dumpStack();
}
for (int ii=0, nn=_media.size(); ii < nn; ii++) { for (int ii=0, nn=_media.size(); ii < nn; ii++) {
((AbstractMedia) _media.get(ii)).fastForward(timeDelta); ((AbstractMedia) _media.get(ii)).fastForward(timeDelta);
} }
@@ -106,19 +107,12 @@ public abstract class AbstractMediaManager
*/ */
protected void tickAllMedia (long tickStamp) protected void tickAllMedia (long tickStamp)
{ {
// we copy our media into an array to prevent additions and // we use _tickpos so that it can be adjusted if media is added or
// removals during tick from breaking things // removed during the tick dispatch
_tickvec = (AbstractMedia[])_media.toArray(_tickvec); for (_tickpos = 0; _tickpos < _media.size(); _tickpos++) {
((AbstractMedia) _media.get(_tickpos)).tick(tickStamp);
// clear out any leftover media
int mcount = _media.size();
if (mcount < _tickvec.length) {
Arrays.fill(_tickvec, mcount, _tickvec.length, null);
}
for (int ii = 0; ii < mcount; ii++) {
_tickvec[ii].tick(tickStamp);
} }
_tickpos = -1;
} }
/** /**
@@ -133,8 +127,16 @@ public abstract class AbstractMediaManager
return false; return false;
} }
_media.insertSorted(media, RENDER_ORDER);
media.init(this); media.init(this);
int ipos = _media.insertSorted(media, RENDER_ORDER);
// if we're ticking, we need to adjust _tickpos and also tick this
// media if it was inserted behind our current tick position
if (ipos <= _tickpos) {
_tickpos++;
media.tick(_tickStamp);
}
return true; return true;
} }
@@ -144,13 +146,15 @@ public abstract class AbstractMediaManager
*/ */
protected boolean removeMedia (AbstractMedia media) protected boolean removeMedia (AbstractMedia media)
{ {
if (_media.remove(media)) { int mpos = _media.indexOf(media);
if (mpos != -1) {
_media.remove(mpos);
media.invalidate(); media.invalidate();
media.shutdown(); media.shutdown();
if (_tickStamp > 0) { // if we're in the middle of ticking, we need to adjust the
// if we're in the middle of ticking, clear the removed // _tickpos if necessary
// media so that we don't paint it when the time comes if (mpos <= _tickpos) {
ListUtil.clear(_tickvec, media); _tickpos--;
} }
return true; return true;
} }
@@ -166,6 +170,11 @@ public abstract class AbstractMediaManager
*/ */
protected void clearMedia () protected void clearMedia ()
{ {
if (_tickStamp > 0) {
Log.warning("Egads! Requested to clearMedia() during a tick.");
Thread.dumpStack();
}
for (int ii=_media.size() - 1; ii >= 0; ii--) { for (int ii=_media.size() - 1; ii >= 0; ii--) {
AbstractMedia media = (AbstractMedia) _media.remove(ii); AbstractMedia media = (AbstractMedia) _media.remove(ii);
media.shutdown(); media.shutdown();
@@ -207,14 +216,14 @@ public abstract class AbstractMediaManager
/** Our render-order sorted list of media. */ /** Our render-order sorted list of media. */
protected SortableArrayList _media = new SortableArrayList(); protected SortableArrayList _media = new SortableArrayList();
/** The position in our media list that we're ticking in the middle of
* a call to {@link #tick} otherwise -1. */
protected int _tickpos = -1;
/** The tick stamp if the manager is in the midst of a call to {@link /** The tick stamp if the manager is in the midst of a call to {@link
* #tick}, else <code>0</code>. */ * #tick}, else <code>0</code>. */
protected long _tickStamp; protected long _tickStamp;
/** An array used to dispatch ticks and paint without worrying that
* additions and removals mess us up during the process. */
protected AbstractMedia[] _tickvec = new AbstractMedia[0];
/** Used to sort media by render order. */ /** Used to sort media by render order. */
protected static final Comparator RENDER_ORDER = new Comparator() { protected static final Comparator RENDER_ORDER = new Comparator() {
public int compare (Object o1, Object o2) { public int compare (Object o1, Object o2) {