aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorChien Yang <[email protected]>2004-08-13 03:15:32 +0000
committerChien Yang <[email protected]>2004-08-13 03:15:32 +0000
commit3069025614f7b03f6ccd148a72dcb564ea8ebdd1 (patch)
tree8c5da4cfdde9fcab8d691225f38a2b6a3aa80992 /src
parent3f3187ab805a0173fb5a3e1e7466688d52314c64 (diff)
Issue number: 18
Fixed Issue 18 : Moved the execution of destroyOffScreenBuffer and createOffScreenBuffer to the renderer thread. git-svn-id: https://svn.java.net/svn/j3d-core~svn/trunk@33 ba19aa83-45c5-6ac9-afd3-db810772062c
Diffstat (limited to 'src')
-rw-r--r--src/classes/share/javax/media/j3d/Canvas3D.java64
-rw-r--r--src/classes/share/javax/media/j3d/J3dMessage.java1
-rw-r--r--src/classes/share/javax/media/j3d/Renderer.java49
3 files changed, 83 insertions, 31 deletions
diff --git a/src/classes/share/javax/media/j3d/Canvas3D.java b/src/classes/share/javax/media/j3d/Canvas3D.java
index ba6016c..2135a9c 100644
--- a/src/classes/share/javax/media/j3d/Canvas3D.java
+++ b/src/classes/share/javax/media/j3d/Canvas3D.java
@@ -1753,21 +1753,13 @@ public class Canvas3D extends Canvas {
}
// TODO: illegalSharing
-
+
if ((offScreenCanvasSize.width != bufferRetained.width) ||
- (offScreenCanvasSize.height != bufferRetained.height)) {
-
- // NOTE: the setOffScreenBuffer method really shouldn't
- // make any GLX calls (which the native create/destroy
- // OffScreenBuffer methods do). It should send a message
- // to the Renderer thread and have it done there, although
- // that would be problematic if called from a
- // Behavior. As it is, there is a small, but non-zero
- // chance of a similar bug cropping up for a system with
- // multiple views and multiple on-screen canvases.
-
+ (offScreenCanvasSize.height != bufferRetained.height)) {
+
if (window != 0) {
- destroyOffScreenBuffer(ctx, screen.display, window);
+ // Fix for Issue 18.
+ // Will do destroyOffScreenBuffer in the Renderer thread.
removeCtx(true);
window = 0;
}
@@ -1777,13 +1769,12 @@ public class Canvas3D extends Canvas {
bufferRetained.height);
this.setSize(offScreenCanvasSize);
- // create off screen buffer
- window = createOffScreenBuffer(ctx, screen.display, vid,
- offScreenCanvasSize.width, offScreenCanvasSize.height);
- ctx = 0;
+ sendCreateOffScreenBuffer();
+
+ ctx = 0;
}
if (ctx != 0) {
- removeCtx(true);
+ removeCtx(false);
}
offScreenBuffer = buffer;
@@ -1846,6 +1837,7 @@ public class Canvas3D extends Canvas {
*/
public void renderOffScreenBuffer() {
+
if (!offScreen)
throw new IllegalStateException(J3dI18N.getString("Canvas3D1"));
@@ -1917,7 +1909,9 @@ public class Canvas3D extends Canvas {
offScreenRendering = true;
if (view.inCanvasCallback) {
+
if (screen.renderer == null) {
+
// It is possible that screen.renderer = null when this View
// is shared by another onScreen Canvas and this callback
// is from that Canvas. In this case it need one more
@@ -1933,6 +1927,7 @@ public class Canvas3D extends Canvas {
// the renderer message queue, and call renderer doWork
// to do the offscreen rendering now
if (Thread.currentThread() == screen.renderer) {
+
J3dMessage createMessage = VirtualUniverse.mc.getMessage();
createMessage.threads = J3dThread.RENDER_THREAD;
createMessage.type = J3dMessage.RENDER_OFFSCREEN;
@@ -1956,6 +1951,7 @@ public class Canvas3D extends Canvas {
// the renderer thread
screen.renderer.doWork(0);
} else {
+
// TODO:
// Now we are in trouble, this will cause deadlock if
// waitForOffScreenRendering() is invoked
@@ -1970,6 +1966,7 @@ public class Canvas3D extends Canvas {
}
} else if (Thread.currentThread() instanceof BehaviorScheduler) {
+
// If called from behavior scheduler, send a message directly to
// the renderer message queue.
// Note that we didn't use
@@ -1986,6 +1983,7 @@ public class Canvas3D extends Canvas {
VirtualUniverse.mc.setWorkForRequestRenderer();
} else {
+
// send a message to renderBin
J3dMessage createMessage = VirtualUniverse.mc.getMessage();
createMessage.threads = J3dThread.UPDATE_RENDER;
@@ -2221,6 +2219,7 @@ public class Canvas3D extends Canvas {
}
void doSwap() {
+
if (firstPaintCalled && useDoubleBuffer) {
try {
if (validCtx && (ctx != 0) && (view != null)) {
@@ -3947,16 +3946,37 @@ public class Canvas3D extends Canvas {
final void endScene() {
endScene(ctx);
}
+
- void removeCtx(boolean offscreen) {
+ // Fix for Issue 18
+ // Pass CreateOffScreenBuffer to the Renderer thread for execution.
+ private void sendCreateOffScreenBuffer() {
+
+ J3dMessage createMessage = VirtualUniverse.mc.getMessage();
+ createMessage.threads = J3dThread.RENDER_THREAD;
+ createMessage.type = J3dMessage.CREATE_OFFSCREENBUFFER;
+ createMessage.universe = this.view.universe;
+ createMessage.view = this.view;
+ createMessage.args[0] = this;
+ screen.renderer.rendererStructure.addMessage(createMessage);
+ VirtualUniverse.mc.setWorkForRequestRenderer();
+
+ }
+
+ private void removeCtx(boolean destroyOffscreen) {
if ((screen != null) &&
(screen.renderer != null) &&
(ctx != 0)) {
+
+ // Fix for Issue 18
+ // Pass destroyOffscreen boolean Renderer thread to perform destroyOffScreenBuffer.
VirtualUniverse.mc.postRequest(MasterControl.FREE_CONTEXT,
new Object[]{this,
- new Long(screen.display),
- new Integer(window),
- new Long(ctx)});
+ new Long(screen.display),
+ new Integer(window),
+ new Long(ctx),
+ new Boolean(destroyOffscreen)});
+
// Fix for Issue 19
// Wait for the context to be freed unless called from
// a Behavior or from a Rendering thread
diff --git a/src/classes/share/javax/media/j3d/J3dMessage.java b/src/classes/share/javax/media/j3d/J3dMessage.java
index 586c23a..5c6a6ef 100644
--- a/src/classes/share/javax/media/j3d/J3dMessage.java
+++ b/src/classes/share/javax/media/j3d/J3dMessage.java
@@ -83,6 +83,7 @@ class J3dMessage extends Object {
static final int VIEWSPECIFICGROUP_CLEAR = 58;
static final int ORDERED_GROUP_TABLE_CHANGED = 59;
static final int BEHAVIOR_REEVALUATE = 60;
+ static final int CREATE_OFFSCREENBUFFER = 61;
/**
* This is the time snapshot at which this change occured
diff --git a/src/classes/share/javax/media/j3d/Renderer.java b/src/classes/share/javax/media/j3d/Renderer.java
index eabfa6e..df39882 100644
--- a/src/classes/share/javax/media/j3d/Renderer.java
+++ b/src/classes/share/javax/media/j3d/Renderer.java
@@ -326,7 +326,7 @@ class Renderer extends J3dThread {
// from MasterControl freeContext(View v)
cv = (Canvas3D) args[1];
removeCtx(cv, cv.screen.display, cv.window, cv.ctx,
- true, true);
+ true, true, false);
} else if (mtype == MasterControl.RESETCANVAS_CLEANUP) {
// from MasterControl RESET_CANVAS postRequest
cv = (Canvas3D) args[1];
@@ -342,10 +342,14 @@ class Renderer extends J3dThread {
((Long) obj[1]).longValue(),
((Integer) obj[2]).intValue(),
((Long) obj[3]).longValue(),
- false, !c.offScreen);
+ false, !c.offScreen,
+ ((Boolean)obj[4]).booleanValue());
+
}
return;
} else { // RENDER || REQUESTRENDER
+
+
int renderType;
nmesg = 0;
int totalMessages = 0;
@@ -447,6 +451,19 @@ class Renderer extends J3dThread {
continue;
}
+
+ if (renderType == J3dMessage.CREATE_OFFSCREENBUFFER) {
+ // Fix for issue 18.
+ canvas.window =
+ canvas.createOffScreenBuffer(canvas.ctx,
+ canvas.screen.display,
+ canvas.vid,
+ canvas.offScreenCanvasSize.width,
+ canvas.offScreenCanvasSize.height);
+ m[nmesg++].decRefcount();
+ continue;
+ }
+
if (!canvas.validCanvas &&
(renderType != J3dMessage.RENDER_OFFSCREEN)) {
m[nmesg++].decRefcount();
@@ -600,22 +617,24 @@ class Renderer extends J3dThread {
}
m[nmesg++].decRefcount();
} else { // retained mode rendering
+
m[nmesg++].decRefcount();
ImageComponent2DRetained offBufRetained = null;
- if (renderType == J3dMessage.RENDER_OFFSCREEN) {
+ if (renderType == J3dMessage.RENDER_OFFSCREEN) {
+
if (canvas.window == 0 || !canvas.active) {
canvas.offScreenRendering = false;
continue;
} else {
offBufRetained = (ImageComponent2DRetained)
- canvas.offScreenBuffer.retained;
-
+ canvas.offScreenBuffer.retained;
+
if (offBufRetained.isByReference()) {
offBufRetained.geomLock.getLock();
offBufRetained.evaluateExtensions(
- canvas.extensionsSupported);
+ canvas.extensionsSupported);
}
}
} else if (!canvas.active) {
@@ -632,6 +651,7 @@ class Renderer extends J3dThread {
// gets yanked from us during a remove.
if (canvas.useSharedCtx) {
+
if (sharedCtx == 0) {
display = canvas.screen.display;
@@ -669,8 +689,9 @@ class Renderer extends J3dThread {
canvas.drawingSurfaceObject.unLock();
}
}
- if (canvas.ctx == 0) {
+ if (canvas.ctx == 0) {
+
display = canvas.screen.display;
// Always lock for context create
@@ -766,6 +787,7 @@ class Renderer extends J3dThread {
}
canvas.drawingSurfaceObject.unLock();
} else {
+
if (canvas.isRunning) {
canvas.makeCtxCurrent();
}
@@ -1454,10 +1476,19 @@ class Renderer extends J3dThread {
// Canvas3D postRequest() offScreen rendering since the
// user thread will not wait for it. Also we can just
// reuse it as Canvas3D did not destroy.
- void removeCtx(Canvas3D cv, long display, int window, long ctx,
- boolean resetCtx, boolean freeBackground) {
+ private void removeCtx(Canvas3D cv, long display, int window, long ctx,
+ boolean resetCtx, boolean freeBackground,
+ boolean destroyOffScreenBuffer) {
+
synchronized (VirtualUniverse.mc.contextCreationLock) {
+ // Fix for issue 18.
+ // Since we are now the renderer thread,
+ // we can safely execute destroyOffScreenBuffer.
+ if(destroyOffScreenBuffer) {
+ cv.makeCtxCurrent();
+ cv.destroyOffScreenBuffer(ctx, display, window);
+ }
if (ctx != 0) {
int idx = listOfCtxs.indexOf(new Long(ctx));
if (idx >= 0) {