aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorrhatcher <[email protected]>2012-12-06 11:48:05 -0600
committerrhatcher <[email protected]>2012-12-06 11:48:05 -0600
commit603609c54139ccb1791b10bef5672f22f030d6a4 (patch)
treeb0c68726a4e6ecf45e1623c7f275b382725c567c /src
parent811e3791b98fea0dfa3b7d301cb532c54df8dc82 (diff)
parent7a6f6b7a5b028e918a843de9fe16c38da75edba9 (diff)
Merge branch 'master' of https://github.com/sgothel/jogl
Diffstat (limited to 'src')
-rw-r--r--src/jogl/classes/com/jogamp/opengl/swt/GLCanvas.java381
-rw-r--r--src/jogl/classes/jogamp/opengl/GLDrawableHelper.java53
-rw-r--r--src/nativewindow/classes/com/jogamp/nativewindow/swt/SWTAccessor.java427
-rw-r--r--src/nativewindow/classes/jogamp/nativewindow/x11/X11DummyUpstreamSurfaceHook.java4
-rw-r--r--src/nativewindow/native/x11/Xmisc.c123
-rw-r--r--src/newt/classes/com/jogamp/newt/Display.java12
-rw-r--r--src/newt/classes/com/jogamp/newt/swt/NewtCanvasSWT.java95
-rw-r--r--src/newt/classes/com/jogamp/newt/util/EDTUtil.java5
-rw-r--r--src/newt/classes/jogamp/newt/DefaultEDTUtil.java119
-rw-r--r--src/newt/classes/jogamp/newt/DisplayImpl.java33
-rw-r--r--src/newt/classes/jogamp/newt/WindowImpl.java81
-rw-r--r--src/newt/classes/jogamp/newt/driver/awt/AWTEDTUtil.java37
-rw-r--r--src/newt/classes/jogamp/newt/driver/windows/WindowDriver.java14
-rw-r--r--src/newt/classes/jogamp/newt/swt/SWTEDTUtil.java (renamed from src/newt/classes/com/jogamp/newt/swt/SWTEDTUtil.java)41
-rw-r--r--src/newt/classes/jogamp/newt/swt/event/SWTNewtEventFactory.java249
-rw-r--r--src/newt/native/WindowsWindow.c19
-rw-r--r--src/test/com/jogamp/opengl/test/junit/jogl/demos/es2/GearsES2.java8
-rw-r--r--src/test/com/jogamp/opengl/test/junit/jogl/swt/TestNewtCanvasSWTBug628ResizeDeadlock.java23
-rw-r--r--src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTBug643AsyncExec.java343
-rw-r--r--src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTJOGLGLCanvas01GLn.java45
-rw-r--r--src/test/com/jogamp/opengl/test/junit/newt/TestDisplayLifecycle01NEWT.java4
21 files changed, 1632 insertions, 484 deletions
diff --git a/src/jogl/classes/com/jogamp/opengl/swt/GLCanvas.java b/src/jogl/classes/com/jogamp/opengl/swt/GLCanvas.java
index e80079c20..0320c63ae 100644
--- a/src/jogl/classes/com/jogamp/opengl/swt/GLCanvas.java
+++ b/src/jogl/classes/com/jogamp/opengl/swt/GLCanvas.java
@@ -29,10 +29,16 @@ package com.jogamp.opengl.swt;
import java.util.List;
+import javax.media.nativewindow.AbstractGraphicsConfiguration;
import javax.media.nativewindow.AbstractGraphicsDevice;
+import javax.media.nativewindow.AbstractGraphicsScreen;
+import javax.media.nativewindow.GraphicsConfigurationFactory;
import javax.media.nativewindow.NativeSurface;
+import javax.media.nativewindow.NativeWindowException;
import javax.media.nativewindow.ProxySurface;
import javax.media.nativewindow.UpstreamSurfaceHook;
+import javax.media.nativewindow.VisualIDHolder;
+import javax.media.nativewindow.VisualIDHolder.VIDType;
import javax.media.opengl.GL;
import javax.media.opengl.GLAnimatorControl;
import javax.media.opengl.GLAutoDrawable;
@@ -48,21 +54,20 @@ import javax.media.opengl.GLProfile;
import javax.media.opengl.GLRunnable;
import javax.media.opengl.Threading;
+import jogamp.nativewindow.x11.X11Util;
import jogamp.opengl.Debug;
import jogamp.opengl.GLContextImpl;
import jogamp.opengl.GLDrawableHelper;
import jogamp.opengl.GLDrawableImpl;
import org.eclipse.swt.SWT;
-import org.eclipse.swt.events.ControlAdapter;
-import org.eclipse.swt.events.ControlEvent;
-import org.eclipse.swt.events.PaintEvent;
-import org.eclipse.swt.events.PaintListener;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.widgets.Canvas;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Display;
+import org.eclipse.swt.widgets.Event;
+import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Shell;
import com.jogamp.common.GlueGenVersion;
@@ -71,13 +76,14 @@ import com.jogamp.common.util.VersionUtil;
import com.jogamp.common.util.locks.LockFactory;
import com.jogamp.common.util.locks.RecursiveLock;
import com.jogamp.nativewindow.swt.SWTAccessor;
+import com.jogamp.nativewindow.x11.X11GraphicsDevice;
import com.jogamp.opengl.JoglVersion;
/**
* Native SWT Canvas implementing GLAutoDrawable
- *
- * <p>Note: To employ custom GLCapabilities, NewtCanvasSWT shall be used instead.</p>
- *
+ * <p>
+ * Implementation allows use of custom {@link GLCapabilities}.
+ * </p>
*/
public class GLCanvas extends Canvas implements GLAutoDrawable {
private static final boolean DEBUG = Debug.debug("GLCanvas");
@@ -101,11 +107,15 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
private final GLCapabilitiesImmutable capsRequested;
private final GLCapabilitiesChooser capsChooser;
+ private volatile Rectangle clientArea;
private volatile GLDrawableImpl drawable; // volatile: avoid locking for read-only access
- private GLContextImpl context;
+ private volatile GLContextImpl context;
/* Native window surface */
- private AbstractGraphicsDevice device;
+ private final boolean useX11GTK;
+ private volatile long gdkWindow; // either GDK child window ..
+ private volatile long x11Window; // .. or X11 child window (for GL rendering)
+ private final AbstractGraphicsScreen screen;
/* Construction parameters stored for GLAutoDrawable accessor methods */
private int additionalCtxCreationFlags = 0;
@@ -133,7 +143,7 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
@Override
public void run() {
if (sendReshape) {
- helper.reshape(GLCanvas.this, 0, 0, getWidth(), getHeight());
+ helper.reshape(GLCanvas.this, 0, 0, clientArea.width, clientArea.height);
sendReshape = false;
}
helper.display(GLCanvas.this);
@@ -141,13 +151,15 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
};
/* Action to make specified context current prior to running displayAction */
- private final Runnable makeCurrentAndDisplayOnEDTAction = new Runnable() {
+ private final Runnable makeCurrentAndDisplayOnGLAction = new Runnable() {
@Override
public void run() {
final RecursiveLock _lock = lock;
_lock.lock();
- try {
- helper.invokeGL(drawable, context, displayAction, initAction);
+ try {
+ if( !GLCanvas.this.isDisposed() ) {
+ helper.invokeGL(drawable, context, displayAction, initAction);
+ }
} finally {
_lock.unlock();
}
@@ -155,13 +167,14 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
};
/* Swaps buffers, assuming the GLContext is current */
- private final Runnable swapBuffersOnEDTAction = new Runnable() {
+ private final Runnable swapBuffersOnGLAction = new Runnable() {
@Override
public void run() {
final RecursiveLock _lock = lock;
_lock.lock();
try {
- if(null != drawable) {
+ final boolean drawableOK = null != drawable && drawable.isRealized();
+ if( drawableOK && !GLCanvas.this.isDisposed() ) {
drawable.swapBuffers();
}
} finally {
@@ -193,7 +206,11 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
// Catch dispose GLExceptions by GLEventListener, just 'print' them
// so we can continue with the destruction.
try {
- helper.disposeGL(GLCanvas.this, context);
+ if( !GLCanvas.this.isDisposed() ) {
+ helper.disposeGL(GLCanvas.this, context);
+ } else {
+ context.destroy();
+ }
} catch (GLException gle) {
gle.printStackTrace();
}
@@ -204,13 +221,14 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
drawable.setRealized(false);
drawable = null;
}
- // SWT is owner of the device handle, not us.
- // Hence close() operation is a NOP.
- if (null != device) {
- device.close();
- device = null;
+ if( 0 != x11Window) {
+ SWTAccessor.destroyX11Window(screen.getDevice(), x11Window);
+ x11Window = 0;
+ } else if( 0 != gdkWindow) {
+ SWTAccessor.destroyGDKWindow(gdkWindow);
+ gdkWindow = 0;
}
- SWTAccessor.setRealized(GLCanvas.this, false); // unrealize ..
+ screen.getDevice().close();
if (animatorPaused) {
animator.resume();
@@ -235,18 +253,15 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
final RecursiveLock _lock = lock;
_lock.lock();
try {
- listener = helper.disposeGLEventListener(GLCanvas.this, drawable, context, listener, remove);
+ if( !GLCanvas.this.isDisposed() ) {
+ listener = helper.disposeGLEventListener(GLCanvas.this, drawable, context, listener, remove);
+ }
} finally {
_lock.unlock();
}
}
};
- /**
- * Storage for the client area rectangle so that it may be accessed from outside of the SWT thread.
- */
- private volatile Rectangle clientArea;
-
/**
* Creates an instance using {@link #GLCanvas(Composite, int, GLCapabilitiesImmutable, GLCapabilitiesChooser, GLContext)}
* on the SWT thread.
@@ -286,61 +301,80 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
* @param style
* Optional SWT style bit-field. The {@link SWT#NO_BACKGROUND} bit is set before passing this up to the
* Canvas constructor, so OpenGL handles the background.
- * @param caps
+ * @param capsReqUser
* Optional GLCapabilities. If not provided, the default capabilities for the default GLProfile for the
* graphics device determined by the parent Composite are used. Note that the GLCapabilities that are
* actually used may differ based on the capabilities of the graphics device.
- * @param chooser
+ * @param capsChooser
* Optional GLCapabilitiesChooser to customize the selection of the used GLCapabilities based on the
* requested GLCapabilities, and the available capabilities of the graphics device.
* @param shareWith
* Optional GLContext to share state (textures, vbos, shaders, etc.) with.
*/
- public GLCanvas(final Composite parent, final int style, GLCapabilitiesImmutable caps,
- final GLCapabilitiesChooser chooser, final GLContext shareWith) {
+ public GLCanvas(final Composite parent, final int style, GLCapabilitiesImmutable capsReqUser,
+ final GLCapabilitiesChooser capsChooser, final GLContext shareWith) {
/* NO_BACKGROUND required to avoid clearing bg in native SWT widget (we do this in the GL display) */
super(parent, style | SWT.NO_BACKGROUND);
GLProfile.initSingleton(); // ensure JOGL is completly initialized
SWTAccessor.setRealized(this, true);
-
+
clientArea = GLCanvas.this.getClientArea();
/* Get the nativewindow-Graphics Device associated with this control (which is determined by the parent Composite).
* Note: SWT is owner of the native handle, hence closing operation will be a NOP. */
- device = SWTAccessor.getDevice(this);
+ final AbstractGraphicsDevice swtDevice = SWTAccessor.getDevice(this);
+
+ useX11GTK = SWTAccessor.useX11GTK();
+ if(useX11GTK) {
+ // Decoupled X11 Device/Screen allowing X11 display lock-free off-thread rendering
+ final long x11DeviceHandle = X11Util.openDisplay(swtDevice.getConnection());
+ if( 0 == x11DeviceHandle ) {
+ throw new RuntimeException("Error creating display(EDT): "+swtDevice.getConnection());
+ }
+ final AbstractGraphicsDevice x11Device = new X11GraphicsDevice(x11DeviceHandle, AbstractGraphicsDevice.DEFAULT_UNIT, true /* owner */);
+ screen = SWTAccessor.getScreen(x11Device, -1 /* default */);
+ } else {
+ screen = SWTAccessor.getScreen(swtDevice, -1 /* default */);
+ }
/* Select default GLCapabilities if none was provided, otherwise clone provided caps to ensure safety */
- if(null == caps) {
- caps = new GLCapabilities(GLProfile.getDefault(device));
+ if(null == capsReqUser) {
+ capsReqUser = new GLCapabilities(GLProfile.getDefault(screen.getDevice()));
}
- this.capsRequested = caps;
- this.capsChooser = chooser;
+
+ this.capsRequested = capsReqUser;
+ this.capsChooser = capsChooser;
this.shareWith = shareWith;
// post create .. when ready
+ gdkWindow = 0;
+ x11Window = 0;
drawable = null;
context = null;
- /* Register SWT listeners (e.g. PaintListener) to render/resize GL surface. */
- /* TODO: verify that these do not need to be manually de-registered when destroying the SWT component */
- addPaintListener(new PaintListener() {
- @Override
- public void paintControl(final PaintEvent arg0) {
- if ( !helper.isAnimatorAnimatingOnOtherThread() ) {
- display(); // checks: null != drawable
- }
- }
- });
-
- addControlListener(new ControlAdapter() {
- @Override
- public void controlResized(final ControlEvent arg0) {
- updateSizeCheck();
- }
- });
+ final Listener listener = new Listener () {
+ @Override
+ public void handleEvent (Event event) {
+ switch (event.type) {
+ case SWT.Paint:
+ displayIfNoAnimatorNoCheck();
+ break;
+ case SWT.Resize:
+ updateSizeCheck();
+ break;
+ case SWT.Dispose:
+ GLCanvas.this.dispose();
+ break;
+ }
+ }
+ };
+ addListener (SWT.Resize, listener);
+ addListener (SWT.Paint, listener);
+ addListener (SWT.Dispose, listener);
}
+
private final UpstreamSurfaceHook swtCanvasUpStreamHook = new UpstreamSurfaceHook() {
@Override
public final void create(ProxySurface s) { /* nop */ }
@@ -372,11 +406,13 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
) {
clientArea = nClientArea; // write back new value
- GLDrawableImpl _drawable = drawable;
- if( null != _drawable ) {
- if(DEBUG) {
- System.err.println("GLCanvas.sizeChanged: ("+Thread.currentThread().getName()+"): "+nClientArea.width+"x"+nClientArea.height+" - surfaceHandle 0x"+Long.toHexString(getNativeSurface().getSurfaceHandle()));
- }
+ final GLDrawableImpl _drawable = drawable;
+ final boolean drawableOK = null != _drawable && _drawable.isRealized();
+ if(DEBUG) {
+ final long dh = drawableOK ? _drawable.getHandle() : 0;
+ System.err.println("GLCanvas.sizeChanged: ("+Thread.currentThread().getName()+"): "+nClientArea.x+"/"+nClientArea.y+" "+nClientArea.width+"x"+nClientArea.height+" - drawableHandle 0x"+Long.toHexString(dh));
+ }
+ if( drawableOK ) {
if( ! _drawable.getChosenGLCapabilities().isOnscreen() ) {
final RecursiveLock _lock = lock;
_lock.lock();
@@ -389,66 +425,154 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
} finally {
_lock.unlock();
}
- sendReshape = true; // async if display() doesn't get called below, but avoiding deadlock
- }
- }
+ }
+ }
+ if(0 != x11Window) {
+ SWTAccessor.resizeX11Window(screen.getDevice(), clientArea, x11Window);
+ } else if(0 != gdkWindow) {
+ SWTAccessor.resizeGDKWindow(clientArea, gdkWindow);
+ }
+ sendReshape = true; // async if display() doesn't get called below, but avoiding deadlock
}
}
- @Override
- public void display() {
- if( null != drawable || validateDrawableAndContext() ) {
- runInGLThread(makeCurrentAndDisplayOnEDTAction);
- }
+ private boolean isValidAndVisibleOnEDTActionResult;
+ private final Runnable isValidAndVisibleOnEDTAction = new Runnable() {
+ @Override
+ public void run() {
+ isValidAndVisibleOnEDTActionResult = !GLCanvas.this.isDisposed() && GLCanvas.this.isVisible();
+ } };
+
+ private final boolean isValidAndVisibleOnEDT() {
+ synchronized(isValidAndVisibleOnEDTAction) {
+ runOnEDTIfAvail(true, isValidAndVisibleOnEDTAction);
+ return isValidAndVisibleOnEDTActionResult;
+ }
}
-
- /** assumes drawable == null ! */
- protected final boolean validateDrawableAndContext() {
- if( GLCanvas.this.isDisposed() ) {
+ /** assumes drawable == null || !drawable.isRealized() ! Checks of !isDispose() and isVisible() */
+ protected final boolean validateDrawableAndContextWithCheck() {
+ if( !isValidAndVisibleOnEDT() ) {
return false;
}
+ return validateDrawableAndContextPostCheck();
+ }
+
+ /** assumes drawable == null || !drawable.isRealized() ! No check of !isDispose() and isVisible() */
+ protected final boolean validateDrawableAndContextPostCheck() {
final Rectangle nClientArea = clientArea;
if(0 >= nClientArea.width || 0 >= nClientArea.height) {
return false;
}
+ final boolean res;
final RecursiveLock _lock = lock;
_lock.lock();
try {
- final GLDrawableFactory glFactory = GLDrawableFactory.getFactory(capsRequested.getGLProfile());
-
- /* Native handle for the control, used to associate with GLContext */
- final long nativeWindowHandle = SWTAccessor.getWindowHandle(this);
-
- /* Create a NativeWindow proxy for the SWT canvas */
- ProxySurface proxySurface = null;
- try {
- proxySurface = glFactory.createProxySurface(device, 0 /* screenIdx */, nativeWindowHandle,
- capsRequested, capsChooser, swtCanvasUpStreamHook);
- } catch (GLException gle) {
- // not ready yet ..
- if(DEBUG) { System.err.println(gle.getMessage()); }
+ if(null == drawable) {
+ createDrawableAndContext();
}
-
- if(null != proxySurface) {
- /* Associate a GL surface with the proxy */
- drawable = (GLDrawableImpl) glFactory.createGLDrawable(proxySurface);
+ if(null != drawable) {
drawable.setRealized(true);
-
- context = (GLContextImpl) drawable.createContext(shareWith);
+ res = drawable.isRealized();
+ } else {
+ res = false;
}
} finally {
_lock.unlock();
+ }
+
+ if(res) {
+ sendReshape = true;
+ if(DEBUG) {
+ System.err.println("SWT GLCanvas realized! "+this+", "+drawable);
+ // Thread.dumpStack();
+ }
}
- final boolean res = null != drawable;
- if(DEBUG && res) {
- System.err.println("SWT GLCanvas realized! "+this+", "+drawable);
- Thread.dumpStack();
- }
- return res;
+ return res;
}
+ private final void createDrawableAndContext() {
+ final AbstractGraphicsDevice device = screen.getDevice();
+ device.open();
+
+ final long nativeWindowHandle;
+ if( useX11GTK ) {
+ final GraphicsConfigurationFactory factory = GraphicsConfigurationFactory.getFactory(device, capsRequested);
+ final AbstractGraphicsConfiguration cfg = factory.chooseGraphicsConfiguration(
+ capsRequested, capsRequested, capsChooser, screen, VisualIDHolder.VID_UNDEFINED);
+ if(DEBUG) {
+ System.err.println("SWT.GLCanvas.X11 factory: "+factory+", chosen config: "+cfg);
+ }
+ if (null == cfg) {
+ throw new NativeWindowException("Error choosing GraphicsConfiguration creating window: "+this);
+ }
+ final int visualID = cfg.getVisualID(VIDType.NATIVE);
+ if( VisualIDHolder.VID_UNDEFINED != visualID ) {
+ // gdkWindow = SWTAccessor.createCompatibleGDKChildWindow(this, visualID, clientArea.width, clientArea.height);
+ // nativeWindowHandle = SWTAccessor.gdk_window_get_xwindow(gdkWindow);
+ x11Window = SWTAccessor.createCompatibleX11ChildWindow(screen, this, visualID, clientArea.width, clientArea.height);
+ nativeWindowHandle = x11Window;
+ } else {
+ throw new GLException("Could not choose valid visualID: 0x"+Integer.toHexString(visualID)+", "+this);
+ }
+ } else {
+ nativeWindowHandle = SWTAccessor.getWindowHandle(this);
+ }
+ final GLDrawableFactory glFactory = GLDrawableFactory.getFactory(capsRequested.getGLProfile());
+
+ // Create a NativeWindow proxy for the SWT canvas
+ ProxySurface proxySurface = glFactory.createProxySurface(device, screen.getIndex(), nativeWindowHandle,
+ capsRequested, capsChooser, swtCanvasUpStreamHook);
+ // Associate a GL surface with the proxy
+ drawable = (GLDrawableImpl) glFactory.createGLDrawable(proxySurface);
+ context = (GLContextImpl) drawable.createContext(shareWith);
+ context.setContextCreationFlags(additionalCtxCreationFlags);
+ }
+
+ @Override
+ public void update() {
+ // don't paint background etc .. nop avoids flickering
+ // super.update();
+ }
+
+ /**
+ @Override
+ public boolean forceFocus() {
+ final boolean r = super.forceFocus();
+ if(r && 0 != gdkWindow) {
+ SWTGTKUtil.focusGDKWindow(gdkWindow);
+ }
+ return r;
+ } */
+
+ @Override
+ public void dispose() {
+ runInGLThread(disposeOnEDTGLAction);
+ super.dispose();
+ }
+
+ private final void displayIfNoAnimatorNoCheck() {
+ if ( !helper.isAnimatorAnimatingOnOtherThread() ) {
+ final boolean drawableOK = null != drawable && drawable.isRealized();
+ if( drawableOK || validateDrawableAndContextPostCheck() ) {
+ runInGLThread(makeCurrentAndDisplayOnGLAction);
+ }
+ }
+ }
+
+ //
+ // GL[Auto]Drawable
+ //
+
+ @Override
+ public void display() {
+ final boolean drawableOK = null != drawable && drawable.isRealized();
+ if( drawableOK || validateDrawableAndContextWithCheck() ) {
+ runInGLThread(makeCurrentAndDisplayOnGLAction);
+ }
+ }
+
@Override
public final Object getUpstreamWidget() {
return this;
@@ -674,18 +798,7 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
@Override
public void swapBuffers() throws GLException {
- runInGLThread(swapBuffersOnEDTAction);
- }
-
- @Override
- public void update() {
- // don't paint background etc .. nop avoids flickering
- }
-
- @Override
- public void dispose() {
- runInGLThread(disposeOnEDTGLAction);
- super.dispose();
+ runInGLThread(swapBuffersOnGLAction);
}
/**
@@ -694,24 +807,66 @@ public class GLCanvas extends Canvas implements GLAutoDrawable {
* <li>Mac OSX
* <ul>
* <!--li>AWT EDT: In case AWT is available, the AWT EDT is the OSX UI main thread</li-->
- * <li><i>Main Thread</i>: Run on OSX UI main thread.</li>
+ * <!--li><i>Main Thread</i>: Run on OSX UI main thread.</li-->
+ * <li>Current thread</li>
* </ul></li>
* <li>Linux, Windows, ..
* <ul>
- * <li>Use {@link Threading#invokeOnOpenGLThread(boolean, Runnable)}</li>
+ * <!--li>Use {@link Threading#invokeOnOpenGLThread(boolean, Runnable)}</li-->
+ * <li>Current thread</li>
* </ul></li>
* </ul>
+ * The current thread seems to be valid for all platforms,
+ * since no SWT lifecycle tasks are being performed w/ this call.
+ * Only GL task, which are independent from the SWT threading model.
+ *
* @see Platform#AWT_AVAILABLE
* @see Platform#getOSType()
*/
- private static void runInGLThread(final Runnable action) {
+ private void runInGLThread(final Runnable action) {
+ /**
if(Platform.OSType.MACOS == Platform.OS_TYPE) {
SWTAccessor.invoke(true, action);
} else {
Threading.invokeOnOpenGLThread(true, action);
- }
+ } */
+ /**
+ if( !isDisposed() ) {
+ final Display d = getDisplay();
+ if( d.getThread() == Thread.currentThread() ) {
+ action.run();
+ } else {
+ d.syncExec(action);
+ }
+ } */
+ action.run();
+ }
+
+ private void runOnEDTIfAvail(boolean wait, final Runnable action) {
+ final Display d = isDisposed() ? null : getDisplay();
+ if( null == d || d.isDisposed() || d.getThread() == Thread.currentThread() ) {
+ action.run();
+ } else if(wait) {
+ d.syncExec(action);
+ } else {
+ d.asyncExec(action);
+ }
}
+ @Override
+ public String toString() {
+ final GLDrawable _drawable = drawable;
+ final int dw = (null!=_drawable) ? _drawable.getWidth() : -1;
+ final int dh = (null!=_drawable) ? _drawable.getHeight() : -1;
+
+ return "SWT-GLCanvas[Realized "+isRealized()+
+ ",\n\t"+((null!=_drawable)?_drawable.getClass().getName():"null-drawable")+
+ ",\n\tFactory "+getFactory()+
+ ",\n\thandle 0x"+Long.toHexString(getHandle())+
+ ",\n\tDrawable size "+dw+"x"+dh+
+ ",\n\tSWT size "+getWidth()+"x"+getHeight()+"]";
+ }
+
public static void main(final String[] args) {
System.err.println(VersionUtil.getPlatformInfo());
System.err.println(GlueGenVersion.getInstance());
diff --git a/src/jogl/classes/jogamp/opengl/GLDrawableHelper.java b/src/jogl/classes/jogamp/opengl/GLDrawableHelper.java
index 1a18b3432..0f8b6b816 100644
--- a/src/jogl/classes/jogamp/opengl/GLDrawableHelper.java
+++ b/src/jogl/classes/jogamp/opengl/GLDrawableHelper.java
@@ -890,35 +890,38 @@ public class GLDrawableHelper {
}
}
int res = GLContext.CONTEXT_NOT_CURRENT;
-
+
try {
- res = context.makeCurrent();
- if (GLContext.CONTEXT_NOT_CURRENT != res) {
- perThreadInitAction.set(initAction);
- if (GLContext.CONTEXT_CURRENT_NEW == res) {
- if (DEBUG) {
- System.err.println("GLDrawableHelper " + this + ".invokeGL(): Running initAction");
- }
- initAction.run();
- }
- runnable.run();
- if ( autoSwapBufferMode ) {
- drawable.swapBuffers();
+ res = context.makeCurrent();
+ if (GLContext.CONTEXT_NOT_CURRENT != res) {
+ try {
+ perThreadInitAction.set(initAction);
+ if (GLContext.CONTEXT_CURRENT_NEW == res) {
+ if (DEBUG) {
+ System.err.println("GLDrawableHelper " + this + ".invokeGL(): Running initAction");
+ }
+ initAction.run();
+ }
+ runnable.run();
+ if ( autoSwapBufferMode ) {
+ drawable.swapBuffers();
+ }
+ } finally {
+ try {
+ context.release();
+ } catch (Exception e) {
+ System.err.println("Catched: "+e.getMessage());
+ e.printStackTrace();
+ }
+ }
}
- }
} finally {
- try {
- context.release();
- } catch (Exception e) {
- System.err.println("Catched: "+e.getMessage());
- e.printStackTrace();
- }
- if (lastContext != null) {
- final int res2 = lastContext.makeCurrent();
- if (null != lastInitAction && res2 == GLContext.CONTEXT_CURRENT_NEW) {
- lastInitAction.run();
+ if (lastContext != null) {
+ final int res2 = lastContext.makeCurrent();
+ if (null != lastInitAction && res2 == GLContext.CONTEXT_CURRENT_NEW) {
+ lastInitAction.run();
+ }
}
- }
}
}
diff --git a/src/nativewindow/classes/com/jogamp/nativewindow/swt/SWTAccessor.java b/src/nativewindow/classes/com/jogamp/nativewindow/swt/SWTAccessor.java
index fca132f3f..eba26c7d3 100644
--- a/src/nativewindow/classes/com/jogamp/nativewindow/swt/SWTAccessor.java
+++ b/src/nativewindow/classes/com/jogamp/nativewindow/swt/SWTAccessor.java
@@ -34,6 +34,7 @@ import java.security.AccessController;
import java.security.PrivilegedAction;
import org.eclipse.swt.graphics.GCData;
+import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Control;
import javax.media.nativewindow.AbstractGraphicsScreen;
@@ -44,6 +45,7 @@ import javax.media.nativewindow.NativeWindowFactory;
import javax.media.nativewindow.VisualIDHolder;
import com.jogamp.common.util.ReflectionUtil;
+import com.jogamp.common.util.VersionNumber;
import com.jogamp.nativewindow.macosx.MacOSXGraphicsDevice;
import com.jogamp.nativewindow.windows.WindowsGraphicsDevice;
import com.jogamp.nativewindow.x11.X11GraphicsDevice;
@@ -53,53 +55,93 @@ import jogamp.nativewindow.macosx.OSXUtil;
import jogamp.nativewindow.x11.X11Lib;
public class SWTAccessor {
- static final Field swt_control_handle;
- static final boolean swt_uses_long_handles;
+ private static final boolean DEBUG = true;
+
+ private static final Field swt_control_handle;
+ private static final boolean swt_uses_long_handles;
+
+ private static Object swt_osx_init = new Object();
+ private static Field swt_osx_control_view = null;
+ private static Field swt_osx_view_id = null;
+
+ private static final String nwt;
+ private static final boolean isOSX;
+ private static final boolean isWindows;
+ private static final boolean isX11;
+ private static final boolean isX11GTK;
// X11/GTK, Windows/GDI, ..
- static final String str_handle = "handle";
+ private static final String str_handle = "handle";
// OSX/Cocoa
- static final String str_view = "view"; // OSX
- static final String str_id = "id"; // OSX
+ private static final String str_osx_view = "view"; // OSX
+ private static final String str_osx_id = "id"; // OSX
// static final String str_NSView = "org.eclipse.swt.internal.cocoa.NSView";
- static final Method swt_control_internal_new_GC;
- static final Method swt_control_internal_dispose_GC;
- static final String str_internal_new_GC = "internal_new_GC";
- static final String str_internal_dispose_GC = "internal_dispose_GC";
+ private static final Method swt_control_internal_new_GC;
+ private static final Method swt_control_internal_dispose_GC;
+ private static final String str_internal_new_GC = "internal_new_GC";
+ private static final String str_internal_dispose_GC = "internal_dispose_GC";
- static final String str_OS_gtk_class = "org.eclipse.swt.internal.gtk.OS";
- static final Class<?> OS_gtk_class;
- static final Method OS_gtk_widget_realize;
- static final Method OS_gtk_widget_unrealize; // optional (removed in SWT 4.3)
- static final Method OS_GTK_WIDGET_WINDOW;
- static final Method OS_gdk_x11_drawable_get_xdisplay;
- static final Method OS_gdk_x11_drawable_get_xid;
- static final String str_gtk_widget_realize = "gtk_widget_realize";
- static final String str_gtk_widget_unrealize = "gtk_widget_unrealize";
- static final String str_GTK_WIDGET_WINDOW = "GTK_WIDGET_WINDOW";
- static final String str_gdk_x11_drawable_get_xdisplay = "gdk_x11_drawable_get_xdisplay";
- static final String str_gdk_x11_drawable_get_xid = "gdk_x11_drawable_get_xid";
+ private static final String str_OS_gtk_class = "org.eclipse.swt.internal.gtk.OS";
+ public static final Class<?> OS_gtk_class;
+ private static final String str_OS_gtk_version = "GTK_VERSION";
+ public static final VersionNumber OS_gtk_version;
+
+ private static final Method OS_gtk_widget_realize;
+ private static final Method OS_gtk_widget_unrealize; // optional (removed in SWT 4.3)
+ private static final Method OS_GTK_WIDGET_WINDOW;
+ private static final Method OS_gtk_widget_get_window;
+ private static final Method OS_gdk_x11_drawable_get_xdisplay;
+ private static final Method OS_gdk_x11_display_get_xdisplay;
+ private static final Method OS_gdk_window_get_display;
+ private static final Method OS_gdk_x11_drawable_get_xid;
+ private static final Method OS_gdk_x11_window_get_xid;
+ private static final Method OS_gdk_window_set_back_pixmap;
+
+ private static final String str_gtk_widget_realize = "gtk_widget_realize";
+ private static final String str_gtk_widget_unrealize = "gtk_widget_unrealize";
+ private static final String str_GTK_WIDGET_WINDOW = "GTK_WIDGET_WINDOW";
+ private static final String str_gtk_widget_get_window = "gtk_widget_get_window";
+ private static final String str_gdk_x11_drawable_get_xdisplay = "gdk_x11_drawable_get_xdisplay";
+ private static final String str_gdk_x11_display_get_xdisplay = "gdk_x11_display_get_xdisplay";
+ private static final String str_gdk_window_get_display = "gdk_window_get_display";
+ private static final String str_gdk_x11_drawable_get_xid = "gdk_x11_drawable_get_xid";
+ private static final String str_gdk_x11_window_get_xid = "gdk_x11_window_get_xid";
+ private static final String str_gdk_window_set_back_pixmap = "gdk_window_set_back_pixmap";
+
+ private static final VersionNumber GTK_VERSION_2_14_0 = new VersionNumber(2, 14, 0);
+ private static final VersionNumber GTK_VERSION_2_24_0 = new VersionNumber(2, 24, 0);
+ private static final VersionNumber GTK_VERSION_3_0_0 = new VersionNumber(3, 0, 0);
+
+ private static VersionNumber GTK_VERSION(int version) {
+ // return (major << 16) + (minor << 8) + micro;
+ final int micro = ( version ) & 0x0f;
+ final int minor = ( version >> 8 ) & 0x0f;
+ final int major = ( version >> 16 ) & 0x0f;
+ return new VersionNumber(major, minor, micro);
+ }
static {
- Field f = null;
-
AccessController.doPrivileged(new PrivilegedAction<Object>() {
public Object run() {
NativeWindowFactory.initSingleton(); // last resort ..
return null;
} } );
- final String nwt = NativeWindowFactory.getNativeWindowType(false);
-
- if(NativeWindowFactory.TYPE_MACOSX != nwt ) {
+ nwt = NativeWindowFactory.getNativeWindowType(false);
+ isOSX = NativeWindowFactory.TYPE_MACOSX == nwt;
+ isWindows = NativeWindowFactory.TYPE_WINDOWS == nwt;
+ isX11 = NativeWindowFactory.TYPE_X11 == nwt;
+
+ Field f = null;
+ if( !isOSX ) {
try {
f = Control.class.getField(str_handle);
} catch (Exception ex) {
throw new NativeWindowException(ex);
}
- }
+ }
swt_control_handle = f; // maybe null !
boolean ulh;
@@ -131,17 +173,34 @@ public class SWTAccessor {
}
swt_control_internal_dispose_GC = m;
- Class<?> c=null;
- Method m1=null, m2=null, m3=null, m4=null, m5=null;
- Class<?> handleType = swt_uses_long_handles ? long.class : int.class ;
- if( NativeWindowFactory.TYPE_X11 == nwt ) {
+ Class<?> c=null;
+ VersionNumber _gtk_version = new VersionNumber(0, 0, 0);
+ Method m1=null, m2=null, m3=null, m4=null, m5=null, m6=null, m7=null, m8=null, m9=null, ma=null;
+ final Class<?> handleType = swt_uses_long_handles ? long.class : int.class ;
+ if( isX11 ) {
// mandatory
try {
c = ReflectionUtil.getClass(str_OS_gtk_class, false, SWTAccessor.class.getClassLoader());
+ Field field_OS_gtk_version = c.getField(str_OS_gtk_version);
+ _gtk_version = GTK_VERSION(field_OS_gtk_version.getInt(null));
m1 = c.getDeclaredMethod(str_gtk_widget_realize, handleType);
- m3 = c.getDeclaredMethod(str_GTK_WIDGET_WINDOW, handleType);
- m4 = c.getDeclaredMethod(str_gdk_x11_drawable_get_xdisplay, handleType);
- m5 = c.getDeclaredMethod(str_gdk_x11_drawable_get_xid, handleType);
+ if (_gtk_version.compareTo(GTK_VERSION_2_14_0) >= 0) {
+ m4 = c.getDeclaredMethod(str_gtk_widget_get_window, handleType);
+ } else {
+ m3 = c.getDeclaredMethod(str_GTK_WIDGET_WINDOW, handleType);
+ }
+ if (_gtk_version.compareTo(GTK_VERSION_2_24_0) >= 0) {
+ m6 = c.getDeclaredMethod(str_gdk_x11_display_get_xdisplay, handleType);
+ m7 = c.getDeclaredMethod(str_gdk_window_get_display, handleType);
+ } else {
+ m5 = c.getDeclaredMethod(str_gdk_x11_drawable_get_xdisplay, handleType);
+ }
+ if (_gtk_version.compareTo(GTK_VERSION_3_0_0) >= 0) {
+ m9 = c.getDeclaredMethod(str_gdk_x11_window_get_xid, handleType);
+ } else {
+ m8 = c.getDeclaredMethod(str_gdk_x11_drawable_get_xid, handleType);
+ }
+ ma = c.getDeclaredMethod(str_gdk_window_set_back_pixmap, handleType, handleType, boolean.class);
} catch (Exception ex) { throw new NativeWindowException(ex); }
// optional
try {
@@ -149,25 +208,41 @@ public class SWTAccessor {
} catch (Exception ex) { }
}
OS_gtk_class = c;
+ OS_gtk_version = _gtk_version;
OS_gtk_widget_realize = m1;
OS_gtk_widget_unrealize = m2;
OS_GTK_WIDGET_WINDOW = m3;
- OS_gdk_x11_drawable_get_xdisplay = m4;
- OS_gdk_x11_drawable_get_xid = m5;
+ OS_gtk_widget_get_window = m4;
+ OS_gdk_x11_drawable_get_xdisplay = m5;
+ OS_gdk_x11_display_get_xdisplay = m6;
+ OS_gdk_window_get_display = m7;
+ OS_gdk_x11_drawable_get_xid = m8;
+ OS_gdk_x11_window_get_xid = m9;
+ OS_gdk_window_set_back_pixmap = ma;
+
+ isX11GTK = isX11 && null != OS_gtk_class;
+
+ if(DEBUG) {
+ System.err.println("SWTAccessor.<init>: GTK Version: "+OS_gtk_version);
+ }
}
-
- static Object getIntOrLong(long arg) {
+
+ private static Number getIntOrLong(long arg) {
if(swt_uses_long_handles) {
return new Long(arg);
}
return new Integer((int) arg);
}
- static void callStaticMethodL2V(Method m, long arg) {
+ private static void callStaticMethodL2V(Method m, long arg) {
ReflectionUtil.callMethod(null, m, new Object[] { getIntOrLong(arg) });
}
- static long callStaticMethodL2L(Method m, long arg) {
+ private static void callStaticMethodLLZ2V(Method m, long arg0, long arg1, boolean arg3) {
+ ReflectionUtil.callMethod(null, m, new Object[] { getIntOrLong(arg0), getIntOrLong(arg1), Boolean.valueOf(arg3) });
+ }
+
+ private static long callStaticMethodL2L(Method m, long arg) {
Object o = ReflectionUtil.callMethod(null, m, new Object[] { getIntOrLong(arg) });
if(o instanceof Number) {
return ((Number)o).longValue();
@@ -175,33 +250,114 @@ public class SWTAccessor {
throw new InternalError("SWT method "+m.getName()+" didn't return int or long but "+o.getClass());
}
}
-
+
+ //
+ // Public properties
+ //
+
public static boolean isUsingLongHandles() {
return swt_uses_long_handles;
}
- public static long getHandle(Control swtControl) {
+ public static boolean useX11GTK() { return isX11GTK; }
+ public static VersionNumber GTK_VERSION() { return OS_gtk_version; }
+
+ //
+ // Common GTK
+ //
+
+ public static long gdk_widget_get_window(long handle) {
+ final long window;
+ if (OS_gtk_version.compareTo(GTK_VERSION_2_14_0) >= 0) {
+ window = callStaticMethodL2L(OS_gtk_widget_get_window, handle);
+ } else {
+ window = callStaticMethodL2L(OS_GTK_WIDGET_WINDOW, handle);
+ }
+ if(0 == window) {
+ throw new NativeWindowException("Null gtk-window-handle of SWT handle 0x"+Long.toHexString(handle));
+ }
+ return window;
+ }
+
+ public static long gdk_window_get_xdisplay(long window) {
+ final long xdisplay;
+ if (OS_gtk_version.compareTo(GTK_VERSION_2_24_0) >= 0) {
+ final long display = callStaticMethodL2L(OS_gdk_window_get_display, window);
+ if(0 == display) {
+ throw new NativeWindowException("Null display-handle of gtk-window-handle 0x"+Long.toHexString(window));
+ }
+ xdisplay = callStaticMethodL2L(OS_gdk_x11_display_get_xdisplay, display);
+ } else {
+ xdisplay = callStaticMethodL2L(OS_gdk_x11_drawable_get_xdisplay, window);
+ }
+ if(0 == xdisplay) {
+ throw new NativeWindowException("Null x11-display-handle of gtk-window-handle 0x"+Long.toHexString(window));
+ }
+ return xdisplay;
+ }
+
+ public static long gdk_window_get_xwindow(long window) {
+ final long xWindow;
+ if (OS_gtk_version.compareTo(GTK_VERSION_3_0_0) >= 0) {
+ xWindow = callStaticMethodL2L(OS_gdk_x11_window_get_xid, window);
+ } else {
+ xWindow = callStaticMethodL2L(OS_gdk_x11_drawable_get_xid, window);
+ }
+ if(0 == xWindow) {
+ throw new NativeWindowException("Null x11-window-handle of gtk-window-handle 0x"+Long.toHexString(window));
+ }
+ return xWindow;
+ }
+
+ public static void gdk_window_set_back_pixmap(long window, long pixmap, boolean parent_relative) {
+ callStaticMethodLLZ2V(OS_gdk_window_set_back_pixmap, window, pixmap, parent_relative);
+ }
+
+ //
+ // Common any toolkit
+ //
+
+ /**
+ * @param swtControl the SWT Control to retrieve the native widget-handle from
+ * @return the native widget-handle
+ * @throws NativeWindowException if the widget handle is null
+ */
+ public static long getHandle(Control swtControl) throws NativeWindowException {
long h = 0;
- if(NativeWindowFactory.TYPE_MACOSX == NativeWindowFactory.getNativeWindowType(false) ) {
+ if( isOSX ) {
+ synchronized(swt_osx_init) {
+ try {
+ if(null == swt_osx_view_id) {
+ swt_osx_control_view = Control.class.getField(str_osx_view);
+ Object view = swt_osx_control_view.get(swtControl);
+ swt_osx_view_id = view.getClass().getField(str_osx_id);
+ h = swt_osx_view_id.getLong(view);
+ } else {
+ h = swt_osx_view_id.getLong( swt_osx_control_view.get(swtControl) );
+ }
+ } catch (Exception ex) {
+ throw new NativeWindowException(ex);
+ }
+ }
+ } else {
try {
- Field fView = Control.class.getField(str_view);
- Object view = fView.get(swtControl);
- Field fId = view.getClass().getField(str_id);
- return fId.getLong(view);
+ h = swt_control_handle.getLong(swtControl);
} catch (Exception ex) {
throw new NativeWindowException(ex);
- }
+ }
}
-
- try {
- h = swt_control_handle.getLong(swtControl);
- } catch (Exception ex) {
- throw new NativeWindowException(ex);
+ if(0 == h) {
+ throw new NativeWindowException("Null widget-handle of SWT "+swtControl.getClass().getName()+": "+swtControl.toString());
}
return h;
}
- public static void setRealized(final Control swtControl, final boolean realize) {
+ public static void setRealized(final Control swtControl, final boolean realize)
+ throws NativeWindowException
+ {
+ if(!realize && swtControl.isDisposed()) {
+ return;
+ }
final long handle = getHandle(swtControl);
if(null != OS_gtk_class) {
@@ -216,55 +372,77 @@ public class SWTAccessor {
});
}
}
-
- public static AbstractGraphicsDevice getDevice(Control swtControl) {
- long handle = getHandle(swtControl);
- if( null != OS_gtk_class ) {
- long widgedHandle = callStaticMethodL2L(OS_GTK_WIDGET_WINDOW, handle);
- long displayHandle = callStaticMethodL2L(OS_gdk_x11_drawable_get_xdisplay, widgedHandle);
- return new X11GraphicsDevice(displayHandle, AbstractGraphicsDevice.DEFAULT_UNIT, false /* owner */);
+
+ /**
+ * @param swtControl the SWT Control to retrieve the native device handle from
+ * @return the AbstractGraphicsDevice w/ the native device handle
+ * @throws NativeWindowException if the widget handle is null
+ * @throws UnsupportedOperationException if the windowing system is not supported
+ */
+ public static AbstractGraphicsDevice getDevice(Control swtControl) throws NativeWindowException, UnsupportedOperationException {
+ final long handle = getHandle(swtControl);
+ if( isX11GTK ) {
+ final long xdisplay0 = gdk_window_get_xdisplay( gdk_widget_get_window( handle ) );
+ return new X11GraphicsDevice(xdisplay0, AbstractGraphicsDevice.DEFAULT_UNIT, false /* owner */);
}
- final String nwt = NativeWindowFactory.getNativeWindowType(false);
- if( NativeWindowFactory.TYPE_WINDOWS == nwt ) {
+ if( isWindows ) {
return new WindowsGraphicsDevice(AbstractGraphicsDevice.DEFAULT_CONNECTION, AbstractGraphicsDevice.DEFAULT_UNIT);
}
- if( NativeWindowFactory.TYPE_MACOSX == nwt ) {
+ if( isOSX ) {
return new MacOSXGraphicsDevice(AbstractGraphicsDevice.DEFAULT_UNIT);
}
throw new UnsupportedOperationException("n/a for this windowing system: "+nwt);
}
- public static AbstractGraphicsScreen getScreen(AbstractGraphicsDevice device, int screen) {
- if( null != OS_gtk_class ) {
- return new X11GraphicsScreen((X11GraphicsDevice)device, screen);
+
+ /**
+ *
+ * @param device
+ * @param screen -1 is default screen of the given device, e.g. maybe 0 or determined by native API. >= 0 is specific screen
+ * @return
+ * @throws UnsupportedOperationException
+ */
+ public static AbstractGraphicsScreen getScreen(AbstractGraphicsDevice device, int screen) throws UnsupportedOperationException {
+ if( isX11 ) {
+ X11GraphicsDevice x11Device = (X11GraphicsDevice)device;
+ if(0 > screen) {
+ screen = x11Device.getDefaultScreen();
+ }
+ return new X11GraphicsScreen(x11Device, screen);
}
- final String nwt = NativeWindowFactory.getNativeWindowType(false);
- if( NativeWindowFactory.TYPE_WINDOWS == nwt ||
- NativeWindowFactory.TYPE_MACOSX == nwt ) {
+ if(0 > screen) {
+ screen = 0; // FIXME: Needs native API utilization
+ }
+ if( isWindows || isOSX ) {
return new DefaultGraphicsScreen(device, screen);
}
throw new UnsupportedOperationException("n/a for this windowing system: "+nwt);
}
+
public static int getNativeVisualID(AbstractGraphicsDevice device, long windowHandle) {
- if( null != OS_gtk_class ) {
+ if( isX11 ) {
return X11Lib.GetVisualIDFromWindow(device.getHandle(), windowHandle);
}
- final String nwt = NativeWindowFactory.getNativeWindowType(false);
- if( NativeWindowFactory.TYPE_WINDOWS == nwt ||
- NativeWindowFactory.TYPE_MACOSX == nwt ) {
+ if( isWindows || isOSX ) {
return VisualIDHolder.VID_UNDEFINED;
}
throw new UnsupportedOperationException("n/a for this windowing system: "+nwt);
}
- public static long getWindowHandle(Control swtControl) {
- long handle = getHandle(swtControl);
- if( null != OS_gtk_class ) {
- long widgedHandle = callStaticMethodL2L(OS_GTK_WIDGET_WINDOW, handle);
- return callStaticMethodL2L(OS_gdk_x11_drawable_get_xid, widgedHandle);
+ /**
+ * @param swtControl the SWT Control to retrieve the native window handle from
+ * @return the native window handle
+ * @throws NativeWindowException if the widget handle is null
+ * @throws UnsupportedOperationException if the windowing system is not supported
+ */
+ public static long getWindowHandle(Control swtControl) throws NativeWindowException, UnsupportedOperationException {
+ final long handle = getHandle(swtControl);
+ if(0 == handle) {
+ throw new NativeWindowException("Null SWT handle of SWT control "+swtControl);
+ }
+ if( isX11GTK ) {
+ return gdk_window_get_xwindow( gdk_widget_get_window( handle ) );
}
- final String nwt = NativeWindowFactory.getNativeWindowType(false);
- if( NativeWindowFactory.TYPE_WINDOWS == nwt ||
- NativeWindowFactory.TYPE_MACOSX == nwt ) {
+ if( isWindows || isOSX ) {
return handle;
}
throw new UnsupportedOperationException("n/a for this windowing system: "+nwt);
@@ -283,7 +461,7 @@ public class SWTAccessor {
throw new InternalError("SWT internal_new_GC did not return int or long but "+o[0].getClass());
}
}
-
+
public static void disposeGC(final Control swtControl, final long gc, final GCData gcData) {
invoke(true, new Runnable() {
public void run() {
@@ -313,7 +491,7 @@ public class SWTAccessor {
* @see Platform#getOSType()
*/
public static void invoke(boolean wait, Runnable runnable) {
- if( Platform.OS_TYPE == Platform.OSType.MACOS ) {
+ if( isOSX ) {
// Use SWT main thread! Only reliable config w/ -XStartOnMainThread !?
OSXUtil.RunOnMainThread(wait, runnable);
} else {
@@ -321,4 +499,85 @@ public class SWTAccessor {
}
}
+ //
+ // Specific X11 GTK ChildWindow - Using plain X11 native parenting (works well)
+ //
+
+ public static long createCompatibleX11ChildWindow(AbstractGraphicsScreen screen, Control swtControl, int visualID, int width, int height) {
+ final long handle = getHandle(swtControl);
+ final long parentWindow = gdk_widget_get_window( handle );
+ gdk_window_set_back_pixmap (parentWindow, 0, false);
+
+ final long x11ParentHandle = gdk_window_get_xwindow(parentWindow);
+ final long x11WindowHandle = X11Lib.CreateWindow(x11ParentHandle, screen.getDevice().getHandle(), screen.getIndex(), visualID, width, height, true, true);
+
+ return x11WindowHandle;
+ }
+
+ public static void resizeX11Window(AbstractGraphicsDevice device, Rectangle clientArea, long x11Window) {
+ X11Lib.SetWindowPosSize(device.getHandle(), x11Window, clientArea.x, clientArea.y, clientArea.width, clientArea.height);
+ }
+ public static void destroyX11Window(AbstractGraphicsDevice device, long x11Window) {
+ X11Lib.DestroyWindow(device.getHandle(), x11Window);
+ }
+
+ //
+ // Specific X11 SWT/GTK ChildWindow - Using SWT/GTK native parenting (buggy - sporadic resize flickering, sporadic drop of rendering)
+ //
+ // FIXME: Need to use reflection for 32bit access as well !
+ //
+
+ // public static final int GDK_WA_TYPE_HINT = 1 << 9;
+ // public static final int GDK_WA_VISUAL = 1 << 6;
+
+ public static long createCompatibleGDKChildWindow(Control swtControl, int visualID, int width, int height) {
+ return 0;
+ /**
+ final long handle = SWTAccessor.getHandle(swtControl);
+ final long parentWindow = gdk_widget_get_window( handle );
+
+ final long screen = OS.gdk_screen_get_default ();
+ final long gdkvisual = OS.gdk_x11_screen_lookup_visual (screen, visualID);
+
+ final GdkWindowAttr attrs = new GdkWindowAttr();
+ attrs.width = width > 0 ? width : 1;
+ attrs.height = height > 0 ? height : 1;
+ attrs.event_mask = OS.GDK_KEY_PRESS_MASK | OS.GDK_KEY_RELEASE_MASK |
+ OS.GDK_FOCUS_CHANGE_MASK | OS.GDK_POINTER_MOTION_MASK |
+ OS.GDK_BUTTON_PRESS_MASK | OS.GDK_BUTTON_RELEASE_MASK |
+ OS.GDK_ENTER_NOTIFY_MASK | OS.GDK_LEAVE_NOTIFY_MASK |
+ OS.GDK_EXPOSURE_MASK | OS.GDK_VISIBILITY_NOTIFY_MASK |
+ OS.GDK_POINTER_MOTION_HINT_MASK;
+ attrs.window_type = OS.GDK_WINDOW_CHILD;
+ attrs.visual = gdkvisual;
+
+ final long childWindow = OS.gdk_window_new (parentWindow, attrs, OS.GDK_WA_VISUAL|GDK_WA_TYPE_HINT);
+ OS.gdk_window_set_user_data (childWindow, handle);
+ OS.gdk_window_set_back_pixmap (parentWindow, 0, false);
+
+ OS.gdk_window_show (childWindow);
+ OS.gdk_flush();
+ return childWindow; */
+ }
+
+ public static void showGDKWindow(long gdkWindow) {
+ /* OS.gdk_window_show (gdkWindow);
+ OS.gdk_flush(); */
+ }
+ public static void focusGDKWindow(long gdkWindow) {
+ /*
+ OS.gdk_window_show (gdkWindow);
+ OS.gdk_window_focus(gdkWindow, 0);
+ OS.gdk_flush(); */
+ }
+ public static void resizeGDKWindow(Rectangle clientArea, long gdkWindow) {
+ /**
+ OS.gdk_window_move (gdkWindow, clientArea.x, clientArea.y);
+ OS.gdk_window_resize (gdkWindow, clientArea.width, clientArea.height);
+ OS.gdk_flush(); */
+ }
+
+ public static void destroyGDKWindow(long gdkWindow) {
+ // OS.gdk_window_destroy (gdkWindow);
+ }
}
diff --git a/src/nativewindow/classes/jogamp/nativewindow/x11/X11DummyUpstreamSurfaceHook.java b/src/nativewindow/classes/jogamp/nativewindow/x11/X11DummyUpstreamSurfaceHook.java
index 67a33e55c..827862002 100644
--- a/src/nativewindow/classes/jogamp/nativewindow/x11/X11DummyUpstreamSurfaceHook.java
+++ b/src/nativewindow/classes/jogamp/nativewindow/x11/X11DummyUpstreamSurfaceHook.java
@@ -37,7 +37,7 @@ public class X11DummyUpstreamSurfaceHook extends UpstreamSurfaceHookMutableSize
s.addUpstreamOptionBits( ProxySurface.OPT_PROXY_OWNS_UPSTREAM_DEVICE );
}
if( 0 == s.getSurfaceHandle() ) {
- final long windowHandle = X11Lib.CreateDummyWindow(device.getHandle(), screen.getIndex(), cfg.getXVisualID(), 64, 64);
+ final long windowHandle = X11Lib.CreateWindow(0, device.getHandle(), screen.getIndex(), cfg.getXVisualID(), 64, 64, false, false);
if(0 == windowHandle) {
throw new NativeWindowException("Creating dummy window failed w/ "+cfg);
}
@@ -59,7 +59,7 @@ public class X11DummyUpstreamSurfaceHook extends UpstreamSurfaceHookMutableSize
}
device.lock();
try {
- X11Lib.DestroyDummyWindow(device.getHandle(), s.getSurfaceHandle());
+ X11Lib.DestroyWindow(device.getHandle(), s.getSurfaceHandle());
s.setSurfaceHandle(0);
s.clearUpstreamOptionBits( ProxySurface.OPT_PROXY_OWNS_UPSTREAM_SURFACE );
} finally {
diff --git a/src/nativewindow/native/x11/Xmisc.c b/src/nativewindow/native/x11/Xmisc.c
index c73952693..a8d45f288 100644
--- a/src/nativewindow/native/x11/Xmisc.c
+++ b/src/nativewindow/native/x11/Xmisc.c
@@ -31,6 +31,8 @@
#include "jogamp_nativewindow_x11_X11Lib.h"
#include "jogamp_nativewindow_x11_X11Util.h"
+#include <X11/Xatom.h>
+
// #define VERBOSE_ON 1
#ifdef VERBOSE_ON
@@ -85,6 +87,8 @@ Bool XF86VidModeSetGammaRamp(
#define RTLD_DEFAULT NULL
#endif
+#define X11_MOUSE_EVENT_MASK (ButtonPressMask | ButtonReleaseMask | PointerMotionMask | EnterWindowMask | LeaveWindowMask)
+
static const char * const ClazzNameBuffers = "com/jogamp/common/nio/Buffers";
static const char * const ClazzNameBuffersStaticCstrName = "copyByteBuffer";
static const char * const ClazzNameBuffersStaticCstrSignature = "(Ljava/nio/ByteBuffer;)Ljava/nio/ByteBuffer;";
@@ -436,17 +440,62 @@ Java_jogamp_nativewindow_x11_X11Lib_XCloseDisplay__J(JNIEnv *env, jclass _unused
return _res;
}
+static void NativewindowX11_setNormalWindowEWMH (Display *dpy, Window w) {
+ Atom _NET_WM_WINDOW_TYPE = XInternAtom( dpy, "_NET_WM_WINDOW_TYPE", False );
+ Atom types[1]={0};
+ types[0] = XInternAtom( dpy, "_NET_WM_WINDOW_TYPE_NORMAL", False );
+ XChangeProperty( dpy, w, _NET_WM_WINDOW_TYPE, XA_ATOM, 32, PropModeReplace, (unsigned char *)&types, 1);
+ XSync(dpy, False);
+}
+
+#define DECOR_USE_MWM 1 // works for known WMs
+// #define DECOR_USE_EWMH 1 // haven't seen this to work (NORMAL->POPUP, never gets undecorated)
+
+/* see <http://tonyobryan.com/index.php?article=9> */
+#define MWM_HINTS_DECORATIONS (1L << 1)
+#define PROP_MWM_HINTS_ELEMENTS 5
+
+static void NativewindowX11_setDecorations (Display *dpy, Window w, Bool decorated) {
+
+#ifdef DECOR_USE_MWM
+ unsigned long mwmhints[PROP_MWM_HINTS_ELEMENTS] = { MWM_HINTS_DECORATIONS, 0, decorated, 0, 0 }; // flags, functions, decorations, input_mode, status
+ Atom _MOTIF_WM_HINTS = XInternAtom( dpy, "_MOTIF_WM_HINTS", False );
+#endif
+
+#ifdef DECOR_USE_EWMH
+ Atom _NET_WM_WINDOW_TYPE = XInternAtom( dpy, "_NET_WM_WINDOW_TYPE", False );
+ Atom types[3]={0};
+ int ntypes=0;
+ if(True==decorated) {
+ types[ntypes++] = XInternAtom( dpy, "_NET_WM_WINDOW_TYPE_NORMAL", False );
+ } else {
+ types[ntypes++] = XInternAtom( dpy, "_NET_WM_WINDOW_TYPE_POPUP_MENU", False );
+ }
+#endif
+
+#ifdef DECOR_USE_MWM
+ XChangeProperty( dpy, w, _MOTIF_WM_HINTS, _MOTIF_WM_HINTS, 32, PropModeReplace, (unsigned char *)&mwmhints, PROP_MWM_HINTS_ELEMENTS);
+#endif
+
+#ifdef DECOR_USE_EWMH
+ XChangeProperty( dpy, w, _NET_WM_WINDOW_TYPE, XA_ATOM, 32, PropModeReplace, (unsigned char *)&types, ntypes);
+#endif
+
+ XSync(dpy, False);
+}
+
/*
* Class: jogamp_nativewindow_x11_X11Lib
- * Method: CreateDummyWindow
- * Signature: (JIIII)J
+ * Method: CreateWindow
+ * Signature: (JJIIIIZZ)J
*/
-JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateDummyWindow
- (JNIEnv *env, jclass unused, jlong display, jint screen_index, jint visualID, jint width, jint height)
+JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateWindow
+ (JNIEnv *env, jclass unused, jlong parent, jlong display, jint screen_index, jint visualID, jint width, jint height, jboolean input, jboolean visible)
{
Display * dpy = (Display *)(intptr_t)display;
int scrn_idx = (int)screen_index;
- Window windowParent = 0;
+ Window root = RootWindow(dpy, scrn_idx);
+ Window windowParent = (Window) parent;
Window window = 0;
XVisualInfo visualTemplate;
@@ -473,6 +522,9 @@ JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateDummyWindow
NativewindowCommon_x11ErrorHandlerEnable(env, dpy, 0, 1, 0, 0);
scrn = ScreenOfDisplay(dpy, scrn_idx);
+ if(0==windowParent) {
+ windowParent = root;
+ }
// try given VisualID on screen
memset(&visualTemplate, 0, sizeof(XVisualInfo));
@@ -500,9 +552,6 @@ JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateDummyWindow
pVisualQuery=NULL;
}
- if(0==windowParent) {
- windowParent = XRootWindowOfScreen(scrn);
- }
attrMask = ( CWBackingStore | CWBackingPlanes | CWBackingPixel | CWBackPixmap |
CWBorderPixel | CWColormap | CWOverrideRedirect ) ;
@@ -514,15 +563,22 @@ JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateDummyWindow
xswa.backing_store=NotUseful; /* NotUseful, WhenMapped, Always */
xswa.backing_planes=0; /* planes to be preserved if possible */
xswa.backing_pixel=0; /* value to use in restoring planes */
+ if( input ) {
+ xswa.event_mask = X11_MOUSE_EVENT_MASK;
+ xswa.event_mask |= KeyPressMask | KeyReleaseMask ;
+ }
+ if( visible ) {
+ xswa.event_mask |= FocusChangeMask | SubstructureNotifyMask | StructureNotifyMask | ExposureMask ;
+ }
xswa.colormap = XCreateColormap(dpy,
- XRootWindow(dpy, scrn_idx),
+ windowParent,
visual,
AllocNone);
window = XCreateWindow(dpy,
windowParent,
- 0, 0,
+ 0, 0, // only a hint, WM most likely will override
width, height,
0, // border width
depth,
@@ -530,9 +586,25 @@ JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateDummyWindow
visual,
attrMask,
&xswa);
+ if(0==window) {
+ NativewindowCommon_throwNewRuntimeException(env, "could not create Window, bail out!");
+ return 0;
+ }
+
+ NativewindowX11_setNormalWindowEWMH(dpy, window);
+ NativewindowX11_setDecorations(dpy, window, False);
+
+ if( visible ) {
+ XEvent event;
+
+ XMapWindow(dpy, window);
+ }
+
XSync(dpy, False);
- XSelectInput(dpy, window, 0); // no events
+ if( !input ) {
+ XSelectInput(dpy, window, 0); // no events
+ }
// NativewindowCommon_x11ErrorHandlerEnable(env, dpy, 0, 0, 0, 1);
@@ -544,10 +616,10 @@ JNIEXPORT jlong JNICALL Java_jogamp_nativewindow_x11_X11Lib_CreateDummyWindow
/*
* Class: jogamp_nativewindow_x11_X11Lib
- * Method: DestroyDummyWindow
+ * Method: DestroyWindow
* Signature: (JJ)V
*/
-JNIEXPORT void JNICALL Java_jogamp_nativewindow_x11_X11Lib_DestroyDummyWindow
+JNIEXPORT void JNICALL Java_jogamp_nativewindow_x11_X11Lib_DestroyWindow
(JNIEnv *env, jclass unused, jlong display, jlong window)
{
Display * dpy = (Display *)(intptr_t)display;
@@ -559,12 +631,37 @@ JNIEXPORT void JNICALL Java_jogamp_nativewindow_x11_X11Lib_DestroyDummyWindow
}
NativewindowCommon_x11ErrorHandlerEnable(env, dpy, 0, 1, 0, 0);
+ XSelectInput(dpy, w, 0);
XUnmapWindow(dpy, w);
XSync(dpy, False);
XDestroyWindow(dpy, w);
// NativewindowCommon_x11ErrorHandlerEnable(env, dpy, 0, 0, 0, 1);
}
+JNIEXPORT void JNICALL Java_jogamp_nativewindow_x11_X11Lib_SetWindowPosSize
+ (JNIEnv *env, jclass unused, jlong display, jlong window, jint x, jint y, jint width, jint height) {
+ Display * dpy = (Display *)(intptr_t)display;
+ Window w = (Window) window;
+ XWindowChanges xwc;
+ int flags = 0;
+
+ memset(&xwc, 0, sizeof(XWindowChanges));
+
+ if(0<=x && 0<=y) {
+ flags |= CWX | CWY;
+ xwc.x=x;
+ xwc.y=y;
+ }
+
+ if(0<width && 0<height) {
+ flags |= CWWidth | CWHeight;
+ xwc.width=width;
+ xwc.height=height;
+ }
+ XConfigureWindow(dpy, w, flags, &xwc);
+ XSync(dpy, False);
+}
+
/*
* Class: jogamp_nativewindow_x11_X11Lib
* Method: GetRelativeLocation
diff --git a/src/newt/classes/com/jogamp/newt/Display.java b/src/newt/classes/com/jogamp/newt/Display.java
index e97dec88d..993aa33eb 100644
--- a/src/newt/classes/com/jogamp/newt/Display.java
+++ b/src/newt/classes/com/jogamp/newt/Display.java
@@ -158,19 +158,15 @@ public abstract class Display {
* </p>
* <p>
* If a previous one exists and it differs from the new one,
- * it's being stopped, wait-until-idle and reset to allow restart.
+ * it's being stopped, wait-until-idle and reset to allow a restart at a later time.
* </p>
* <p>
* If <code>newEDTUtil</code> is not null and equals the previous one,
- * <code>null</code> is returned and no change is being made.
+ * no change is being made.
* </p>
* <p>
- * Note that <code>newEDTUtil</code> will not be started if not done so already,
- * to do so you may issue {@link EDTUtil#invoke(boolean, Runnable) invoke}
- * on the new EDTUtil:
- * <pre>
- * newEDTUtil.invoke(true, new Runnable() { public void run() { } } );
- * </pre>
+ * Note that <code>newEDTUtil</code> will be started by this method,
+ * if it is not running yet.
* </p>
*/
public abstract EDTUtil setEDTUtil(EDTUtil newEDTUtil);
diff --git a/src/newt/classes/com/jogamp/newt/swt/NewtCanvasSWT.java b/src/newt/classes/com/jogamp/newt/swt/NewtCanvasSWT.java
index 525225804..dbe7c0d98 100644
--- a/src/newt/classes/com/jogamp/newt/swt/NewtCanvasSWT.java
+++ b/src/newt/classes/com/jogamp/newt/swt/NewtCanvasSWT.java
@@ -26,7 +26,6 @@
* or implied, of JogAmp Community.
*/
-
package com.jogamp.newt.swt;
import javax.media.nativewindow.AbstractGraphicsConfiguration;
@@ -44,18 +43,18 @@ import javax.media.nativewindow.WindowClosingProtocol;
import javax.media.nativewindow.util.Insets;
import javax.media.nativewindow.util.InsetsImmutable;
import javax.media.nativewindow.util.Point;
+import javax.media.opengl.GLCapabilities;
import jogamp.nativewindow.macosx.OSXUtil;
import jogamp.newt.Debug;
+import jogamp.newt.swt.SWTEDTUtil;
import org.eclipse.swt.SWT;
-import org.eclipse.swt.events.ControlAdapter;
-import org.eclipse.swt.events.ControlEvent;
-import org.eclipse.swt.events.PaintEvent;
-import org.eclipse.swt.events.PaintListener;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Canvas;
import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Event;
+import org.eclipse.swt.widgets.Listener;
import com.jogamp.nativewindow.swt.SWTAccessor;
import com.jogamp.newt.Display;
@@ -65,6 +64,9 @@ import com.jogamp.newt.util.EDTUtil;
/**
* SWT {@link Canvas} containing a NEWT {@link Window} using native parenting.
+ * <p>
+ * Implementation allows use of custom {@link GLCapabilities}.
+ * </p>
*/
public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
private static final boolean DEBUG = Debug.debug("Window");
@@ -77,6 +79,8 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
private volatile SWTNativeWindow nativeWindow;
private volatile Window newtChild = null;
+ private volatile boolean newtChildReady = false; // ready if SWTEDTUtil is set and newtChild parented
+ private volatile boolean postSetSize = false; // pending resize
/**
* Creates an instance using {@link #NewtCanvasSWT(Composite, int, Window)}
@@ -122,45 +126,51 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
clientArea = getClientArea();
final AbstractGraphicsDevice device = SWTAccessor.getDevice(this);
- screen = SWTAccessor.getScreen(device, 0);
+ screen = SWTAccessor.getScreen(device, -1 /* default */);
nativeWindow = null;
if(null != child) {
setNEWTChild(child);
}
-
- /* Register SWT listeners (e.g. PaintListener) to render/resize GL surface. */
- /* TODO: verify that these do not need to be manually de-registered when destroying the SWT component */
- addPaintListener(new PaintListener() {
+
+ final Listener listener = new Listener () {
@Override
- public void paintControl(final PaintEvent arg0) {
- if( null != nativeWindow || validateNative() ) {
- if( null !=newtChild ) {
- newtChild.windowRepaint(0, 0, clientArea.width, clientArea.height);
+ public void handleEvent (Event event) {
+ switch (event.type) {
+ case SWT.Paint:
+ if( null != nativeWindow || validateNative() ) {
+ if( newtChildReady ) {
+ if( postSetSize ) {
+ newtChild.setSize(clientArea.width, clientArea.height);
+ postSetSize = false;
+ }
+ newtChild.windowRepaint(0, 0, clientArea.width, clientArea.height);
+ }
}
+ break;
+ case SWT.Resize:
+ updateSizeCheck();
+ break;
+ case SWT.Dispose:
+ NewtCanvasSWT.this.dispose();
+ break;
}
}
- });
-
- addControlListener(new ControlAdapter() {
- @Override
- public void controlResized(final ControlEvent arg0) {
- updateSizeCheck();
- }
- });
+ };
+ addListener (SWT.Resize, listener);
+ addListener (SWT.Paint, listener);
+ addListener (SWT.Dispose, listener);
}
/** assumes nativeWindow == null ! */
protected final boolean validateNative() {
- if( isDisposed() ) {
- return false;
- }
updateSizeCheck();
final Rectangle nClientArea = clientArea;
if(0 >= nClientArea.width || 0 >= nClientArea.height) {
return false;
}
-
+ screen.getDevice().open();
+
/* Native handle for the control, used to associate with GLContext */
final long nativeWindowHandle = SWTAccessor.getWindowHandle(this);
final int visualID = SWTAccessor.getNativeVisualID(screen.getDevice(), nativeWindowHandle);
@@ -196,12 +206,18 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
( nClientArea.width != oClientArea.width || nClientArea.height != oClientArea.height )
) {
clientArea = nClientArea; // write back new value
- if( null != newtChild ) {
+ if(DEBUG) {
+ final long nsh = newtChildReady ? newtChild.getSurfaceHandle() : 0;
+ System.err.println("NewtCanvasSWT.sizeChanged: ("+Thread.currentThread().getName()+"): newtChildReady "+newtChildReady+", "+nClientArea.x+"/"+nClientArea.y+" "+nClientArea.width+"x"+nClientArea.height+" - surfaceHandle 0x"+Long.toHexString(nsh));
+ }
+ if( newtChildReady ) {
newtChild.setSize(clientArea.width, clientArea.height);
+ } else {
+ postSetSize = true;
}
}
}
-
+
@Override
public void update() {
// don't paint background etc .. nop avoids flickering
@@ -230,6 +246,7 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
newtChild.destroy();
newtChild = null;
}
+ screen.getDevice().close();
nativeWindow = null;
super.dispose();
}
@@ -238,11 +255,11 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
public NativeWindow getNativeWindow() { return nativeWindow; }
public WindowClosingMode getDefaultCloseOperation() {
- return newtChildCloseOp; // FIXME
+ return newtChildCloseOp; // TODO: implement ?!
}
public WindowClosingMode setDefaultCloseOperation(WindowClosingMode op) {
- return newtChildCloseOp = op; // FIXME
+ return newtChildCloseOp = op; // TODO: implement ?!
}
@@ -299,7 +316,7 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
}
/* package */ void configureNewtChild(boolean attach) {
-
+ newtChildReady = attach;
if( null != newtChild ) {
newtChild.setKeyboardFocusHandler(null);
if(attach) {
@@ -324,23 +341,21 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
updateSizeCheck();
final int w = clientArea.width;
final int h = clientArea.height;
-
+
// set SWT EDT and start it
{
final Display newtDisplay = newtChild.getScreen().getDisplay();
- final EDTUtil edt = new SWTEDTUtil(newtDisplay, getDisplay());
- newtDisplay.setEDTUtil(edt);
- edt.invoke(true, new Runnable() { public void run() { } } ); // start EDT
+ newtDisplay.setEDTUtil( new SWTEDTUtil(newtDisplay, getDisplay()) );
}
- newtChild.setSize(w, h);
+ newtChild.setSize(w, h);
newtChild.reparentWindow(nativeWindow);
newtChild.setVisible(true);
- configureNewtChild(true);
+ configureNewtChild(true);
newtChild.sendWindowEvent(WindowEvent.EVENT_WINDOW_RESIZED); // trigger a resize/relayout to listener
-
+
// force this SWT Canvas to be focus-able,
- // since this it is completely covered by the newtChild (z-order).
+ // since it is completely covered by the newtChild (z-order).
setEnabled(true);
} else {
configureNewtChild(false);
@@ -353,7 +368,7 @@ public class NewtCanvasSWT extends Canvas implements WindowClosingProtocol {
}
private final void requestFocusNEWTChild() {
- if( null != newtChild ) {
+ if( newtChildReady ) {
newtChild.setFocusAction(null);
newtChild.requestFocus();
}
diff --git a/src/newt/classes/com/jogamp/newt/util/EDTUtil.java b/src/newt/classes/com/jogamp/newt/util/EDTUtil.java
index 7e19d9de5..0183da592 100644
--- a/src/newt/classes/com/jogamp/newt/util/EDTUtil.java
+++ b/src/newt/classes/com/jogamp/newt/util/EDTUtil.java
@@ -113,7 +113,8 @@ public interface EDTUtil {
/**
* Append the final task to the EDT task queue,
- * signals EDT to stop and wait until stopped.<br>
+ * signals EDT to stop and wait until stopped.<br/>
+ * <code>task</code> maybe <code>null</code><br/>
* Due to the nature of this method:
* <ul>
* <li>All previous queued tasks will be finished.</li>
@@ -125,7 +126,7 @@ public interface EDTUtil {
public void invokeStop(Runnable finalTask);
/**
- * Shall start the thread if not running.<br>
+ * Shall start the thread if not running, <code>task</code> maybe null for this purpose.<br>
* Append task to the EDT task queue.<br>
* Wait until execution is finished if <code>wait == true</code>.<br>
* Can be issued from within EDT, ie from within an enqueued task.<br>
diff --git a/src/newt/classes/jogamp/newt/DefaultEDTUtil.java b/src/newt/classes/jogamp/newt/DefaultEDTUtil.java
index 98987ef96..d8d04e79f 100644
--- a/src/newt/classes/jogamp/newt/DefaultEDTUtil.java
+++ b/src/newt/classes/jogamp/newt/DefaultEDTUtil.java
@@ -81,10 +81,10 @@ public class DefaultEDTUtil implements EDTUtil {
waitUntilStopped();
if(DEBUG) {
if(edt.tasks.size()>0) {
- System.err.println(Thread.currentThread()+": EDT reset, remaining tasks: "+edt.tasks.size()+" - "+edt);
+ System.err.println(Thread.currentThread()+": Default-EDT reset, remaining tasks: "+edt.tasks.size()+" - "+edt);
// Thread.dumpStack();
}
- System.err.println(Thread.currentThread()+": EDT reset - edt: "+edt);
+ System.err.println(Thread.currentThread()+": Default-EDT reset - edt: "+edt);
}
this.edt = new EventDispatchThread(threadGroup, name);
this.edt.setDaemon(true); // don't stop JVM from shutdown ..
@@ -93,13 +93,13 @@ public class DefaultEDTUtil implements EDTUtil {
private final void startImpl() {
if(edt.isAlive()) {
- throw new RuntimeException("EDT Thread.isAlive(): true, isRunning: "+edt.isRunning()+", edt: "+edt+", tasks: "+edt.tasks.size());
+ throw new RuntimeException("Default-EDT Thread.isAlive(): true, isRunning: "+edt.isRunning()+", edt: "+edt+", tasks: "+edt.tasks.size());
}
start_iter++;
edt.setName(name+start_iter);
edt.shouldStop = false;
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT START - edt: "+edt);
+ System.err.println(Thread.currentThread()+": Default-EDT START - edt: "+edt);
// Thread.dumpStack();
}
edt.start();
@@ -135,10 +135,12 @@ public class DefaultEDTUtil implements EDTUtil {
invokeImpl(wait, task, false);
}
+ private static Runnable nullTask = new Runnable() {
+ @Override
+ public void run() { }
+ };
+
private void invokeImpl(boolean wait, Runnable task, boolean stop) {
- if(task == null) {
- throw new RuntimeException("Null Runnable");
- }
Throwable throwable = null;
RunnableTask rTask = null;
Object rTaskLock = new Object();
@@ -147,45 +149,57 @@ public class DefaultEDTUtil implements EDTUtil {
if( edt.shouldStop ) {
// drop task ..
if(DEBUG) {
- System.err.println("Warning: EDT about (1) to stop, won't enqueue new task: "+edt);
+ System.err.println(Thread.currentThread()+": Warning: Default-EDT about (1) to stop, won't enqueue new task: "+edt);
Thread.dumpStack();
}
return;
}
// System.err.println(Thread.currentThread()+" XXX stop: "+stop+", tasks: "+edt.tasks.size()+", task: "+task);
// Thread.dumpStack();
- if(stop) {
- edt.shouldStop = true;
- if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT signal STOP (on edt: "+isCurrentThreadEDT()+") - tasks: "+edt.tasks.size()+" - "+edt);
- // Thread.dumpStack();
- }
- }
if( isCurrentThreadEDT() ) {
- task.run();
+ if(null != task) {
+ task.run();
+ }
wait = false; // running in same thread (EDT) -> no wait
- if(stop && edt.tasks.size()>0) {
- System.err.println("Warning: EDT about (2) to stop, having remaining tasks: "+edt.tasks.size()+" - "+edt);
- if(DEBUG) {
- Thread.dumpStack();
+ if(stop) {
+ edt.shouldStop = true;
+ if( edt.tasks.size()>0 ) {
+ System.err.println(Thread.currentThread()+": Warning: Default-EDT about (2) to stop, task executed. Remaining tasks: "+edt.tasks.size()+" - "+edt);
+ if(DEBUG) {
+ Thread.dumpStack();
+ }
}
}
} else {
- // start if should not stop && not started yet
- if( !stop && !edt.isRunning() ) {
- startImpl();
+ if( !edt.isRunning() ) {
+ if( !stop ) {
+ startImpl();
+ } else {
+ // drop task and don't wait
+ task = null;
+ System.err.println(Thread.currentThread()+": Warning: Default-EDT is about (3) to stop and stopped already, dropping task. Remaining tasks: "+edt.tasks.size()+" - "+edt);
+ if(true || DEBUG) {
+ Thread.dumpStack();
+ }
+ }
+ } else if(stop && null == task) {
+ task = nullTask;
}
- synchronized(edt.tasks) {
- wait = wait && edt.isRunning();
- rTask = new RunnableTask(task,
- wait ? rTaskLock : null,
- true /* always catch and report Exceptions, don't disturb EDT */);
- if(stop) {
- rTask.setAttachment(new Boolean(true)); // mark final task
+
+ if(null != task) {
+ synchronized(edt.tasks) {
+ rTask = new RunnableTask(task,
+ wait ? rTaskLock : null,
+ true /* always catch and report Exceptions, don't disturb EDT */);
+ if(stop) {
+ rTask.setAttachment(new Boolean(true)); // mark final task, will imply shouldStop:=true
+ }
+ // append task ..
+ edt.tasks.add(rTask);
+ edt.tasks.notifyAll();
}
- // append task ..
- edt.tasks.add(rTask);
- edt.tasks.notifyAll();
+ } else {
+ wait = false;
}
}
}
@@ -207,7 +221,7 @@ public class DefaultEDTUtil implements EDTUtil {
}
}
if(DEBUG && stop) {
- System.err.println(Thread.currentThread()+": EDT signal STOP X edt: "+edt);
+ System.err.println(Thread.currentThread()+": Default-EDT signal STOP X edt: "+edt);
}
}
@@ -282,7 +296,7 @@ public class DefaultEDTUtil implements EDTUtil {
@Override
final public void run() {
if(DEBUG) {
- System.err.println(getName()+": EDT run() START "+ getName());
+ System.err.println(getName()+": Default-EDT run() START "+ getName());
}
validateNoRecursiveLocksHold();
RuntimeException error = null;
@@ -307,6 +321,9 @@ public class DefaultEDTUtil implements EDTUtil {
if(tasks.size()>0) {
task = tasks.remove(0);
tasks.notifyAll();
+ if( null != task.getAttachment() ) {
+ shouldStop = true;
+ }
}
}
if(null!=task) {
@@ -324,41 +341,19 @@ public class DefaultEDTUtil implements EDTUtil {
if(t instanceof RuntimeException) {
error = (RuntimeException) t;
} else {
- error = new RuntimeException("Within EDT", t);
+ error = new RuntimeException("Within Default-EDT", t);
}
} finally {
if(DEBUG) {
RunnableTask rt = ( tasks.size() > 0 ) ? tasks.get(0) : null ;
- System.err.println(getName()+": EDT run() END "+ getName()+", tasks: "+tasks.size()+", "+rt+", "+error);
+ System.err.println(getName()+": Default-EDT run() END "+ getName()+", tasks: "+tasks.size()+", "+rt+", "+error);
}
synchronized(edtLock) {
- if(null==error) {
- synchronized(tasks) {
- // drain remaining tasks (stop not on EDT),
- // while having tasks and no previous-task, or previous-task is non final
- RunnableTask task = null;
- while ( ( null == task || task.getAttachment() == null ) && tasks.size() > 0 ) {
- task = tasks.remove(0);
- task.run();
- tasks.notifyAll();
- }
- if(DEBUG) {
- if(null!=task && task.getAttachment()==null) {
- System.err.println(getName()+" Warning: EDT exit: Last task Not Final: "+tasks.size()+", "+task+" - "+edt);
- } else if(tasks.size()>0) {
- System.err.println(getName()+" Warning: EDT exit: Remaining tasks Post Final: "+tasks.size());
- }
- Thread.dumpStack();
- }
- }
- }
- isRunning = !shouldStop;
- if(!isRunning) {
- edtLock.notifyAll();
- }
+ isRunning = false;
+ edtLock.notifyAll();
}
if(DEBUG) {
- System.err.println(getName()+": EDT run() EXIT "+ getName()+", exception: "+error);
+ System.err.println(getName()+": Default-EDT run() EXIT "+ getName()+", exception: "+error);
}
if(null!=error) {
throw error;
diff --git a/src/newt/classes/jogamp/newt/DisplayImpl.java b/src/newt/classes/jogamp/newt/DisplayImpl.java
index 317535805..20b915cae 100644
--- a/src/newt/classes/jogamp/newt/DisplayImpl.java
+++ b/src/newt/classes/jogamp/newt/DisplayImpl.java
@@ -84,9 +84,8 @@ public abstract class DisplayImpl extends Display {
display.hashCode = display.fqname.hashCode();
displayList.add(display);
}
- if(null == display.edtUtil) {
- display.setEDTUtil(null); // device's default if EDT is used, or null
- }
+ display.setEDTUtil(display.edtUtil); // device's default if EDT is used, or null
+
if(DEBUG) {
System.err.println("Display.create() NEW: "+display+" "+getThreadName());
}
@@ -166,20 +165,24 @@ public abstract class DisplayImpl extends Display {
@Override
public EDTUtil setEDTUtil(EDTUtil newEDTUtil) {
+ final EDTUtil oldEDTUtil = edtUtil;
if(null == newEDTUtil) {
- newEDTUtil = createEDTUtil();
- } else if( newEDTUtil == edtUtil ) {
if(DEBUG) {
- System.err.println("Display.setEDTUtil: "+newEDTUtil+" - keep!");
+ System.err.println("Display.setEDTUtil(default): "+oldEDTUtil+" -> "+newEDTUtil);
+ }
+ edtUtil = createEDTUtil();
+ } else if( newEDTUtil != edtUtil ) {
+ if(DEBUG) {
+ System.err.println("Display.setEDTUtil(custom): "+oldEDTUtil+" -> "+newEDTUtil);
}
- return null; // no change
+ removeEDT( null );
+ edtUtil = newEDTUtil;
+ } else if( DEBUG ) {
+ System.err.println("Display.setEDTUtil: "+newEDTUtil+" - keep!");
}
- final EDTUtil oldEDTUtil = edtUtil;
- if(DEBUG) {
- System.err.println("Display.setEDTUtil: "+oldEDTUtil+" -> "+newEDTUtil);
+ if( !edtUtil.isRunning() ) { // start EDT if not running yet
+ edtUtil.invoke(true, null);
}
- removeEDT( new Runnable() { public void run() {} } );
- edtUtil = newEDTUtil;
return oldEDTUtil;
}
@@ -209,11 +212,7 @@ public abstract class DisplayImpl extends Display {
public boolean validateEDT() {
if(0==refCount && null==aDevice && null != edtUtil && edtUtil.isRunning()) {
- removeEDT( new Runnable() {
- public void run() {
- // nop
- }
- } );
+ removeEDT( null );
return true;
}
return false;
diff --git a/src/newt/classes/jogamp/newt/WindowImpl.java b/src/newt/classes/jogamp/newt/WindowImpl.java
index 4f8eb3d3a..a9294c1ff 100644
--- a/src/newt/classes/jogamp/newt/WindowImpl.java
+++ b/src/newt/classes/jogamp/newt/WindowImpl.java
@@ -173,7 +173,6 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
window.parentWindowHandle = parentWindowHandle;
window.screen = (ScreenImpl) screen;
window.capsRequested = (CapabilitiesImmutable) caps.cloneMutable();
- window.setUndecorated(0!=parentWindowHandle);
window.instantiationFinished();
return window;
} catch (Throwable t) {
@@ -573,6 +572,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
} finally {
if (LOCK_SURFACE_NOT_READY >= res) {
+ surfaceLockCount--;
_wlock.unlock();
}
}
@@ -729,8 +729,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
} else if(WindowImpl.this.visible != visible) {
if(isNativeValid()) {
setVisibleImpl(visible, getX(), getY(), getWidth(), getHeight());
- WindowImpl.this.waitForVisible(visible, true);
+ WindowImpl.this.waitForVisible(visible, false);
madeVisible = visible;
+ } else {
+ WindowImpl.this.visible = true;
}
}
@@ -804,11 +806,13 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
} else if ( visible && !isNativeValid() && 0 < width && 0 < height ) {
visibleAction = 2; // visible (create)
defineSize(width, height);
- } else if ( isNativeValid() ) {
+ } else if ( visible && isNativeValid() ) {
visibleAction = 0;
// this width/height will be set by windowChanged, called by the native implementation
reconfigureWindowImpl(getX(), getY(), width, height, getReconfigureFlags(0, isVisible()));
+ WindowImpl.this.waitForSize(width, height, false, TIMEOUT_NATIVEWINDOW);
} else {
+ // invisible or invalid w/ 0 size
visibleAction = 0;
defineSize(width, height);
}
@@ -1045,8 +1049,8 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
if(null!=newParentWindowNEWT) {
setScreen( (ScreenImpl) newParentWindowNEWT.getScreen() );
} else {
- Screen newScreen = NewtFactory.createCompatibleScreen(newParentWindow, getScreen());
- if( getScreen() != newScreen ) {
+ final Screen newScreen = NewtFactory.createCompatibleScreen(newParentWindow, screen);
+ if( screen != newScreen ) {
// auto destroy on-the-fly created Screen/Display
setScreen( (ScreenImpl) newScreen );
}
@@ -1056,14 +1060,14 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
} else {
operation = ReparentOperation.ACTION_NATIVE_CREATION_PENDING;
}
- } else if ( forceDestroyCreate || !NewtFactory.isScreenCompatible(newParentWindow, getScreen()) ) {
+ } else if ( forceDestroyCreate || !NewtFactory.isScreenCompatible(newParentWindow, screen) ) {
// Destroy this window, may create a new compatible Screen/Display,
// and mark it for creation.
destroy();
if(null!=newParentWindowNEWT) {
setScreen( (ScreenImpl) newParentWindowNEWT.getScreen() );
} else {
- setScreen( (ScreenImpl) NewtFactory.createCompatibleScreen(newParentWindow, getScreen()) );
+ setScreen( (ScreenImpl) NewtFactory.createCompatibleScreen(newParentWindow, screen) );
}
operation = ReparentOperation.ACTION_NATIVE_CREATION;
} else {
@@ -1078,7 +1082,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
if( null != parentWindow ) {
// child -> top
// put client to current parent+child position
- Point p = getLocationOnScreen(null);
+ final Point p = getLocationOnScreen(null);
x = p.getX();
y = p.getY();
}
@@ -1134,13 +1138,13 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
if( ReparentOperation.ACTION_NATIVE_REPARENTING == operation ) {
- DisplayImpl display = (DisplayImpl) screen.getDisplay();
+ final DisplayImpl display = (DisplayImpl) screen.getDisplay();
display.dispatchMessagesNative(); // status up2date
if(wasVisible) {
setVisibleImpl(false, x, y, width, height);
- WindowImpl.this.waitForVisible(false, true);
- // some composite WM behave slacky .. give 'em chance to change state -> invisible,
+ WindowImpl.this.waitForVisible(false, false);
+ // FIXME: Some composite WM behave slacky .. give 'em chance to change state -> invisible,
// even though we do exactly that (KDE+Composite)
try { Thread.sleep(100); } catch (InterruptedException e) { }
display.dispatchMessagesNative(); // status up2date
@@ -1166,6 +1170,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
parentWindowLocked.unlockSurface();
}
}
+ definePosition(x, y); // position might not get updated by WM events (SWT parent apparently)
// set visible again
if(ok) {
@@ -1173,7 +1178,6 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
if(wasVisible) {
setVisibleImpl(true, x, y, width, height);
ok = WindowImpl.this.waitForVisible(true, false);
- display.dispatchMessagesNative(); // status up2date
if(ok) {
ok = WindowImpl.this.waitForSize(width, height, false, TIMEOUT_NATIVEWINDOW);
}
@@ -1202,7 +1206,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
if(DEBUG_IMPLEMENTATION) {
- System.err.println("Window.reparentWindow: END-1 ("+getThreadName()+") windowHandle "+toHexString(windowHandle)+", visible: "+visible+", parentWindowHandle "+toHexString(parentWindowHandle)+", parentWindow "+ Display.hashCodeNullSafe(parentWindow)+" "+x+"/"+y+" "+width+"x"+height);
+ System.err.println("Window.reparentWindow: END-1 ("+getThreadName()+") windowHandle "+toHexString(windowHandle)+", visible: "+visible+", parentWindowHandle "+toHexString(parentWindowHandle)+", parentWindow "+ Display.hashCodeNullSafe(parentWindow)+" "+getX()+"/"+getY()+" "+getWidth()+"x"+getHeight());
}
} finally {
_lock.unlock();
@@ -1223,7 +1227,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
}
if(DEBUG_IMPLEMENTATION) {
- System.err.println("Window.reparentWindow: END-X ("+getThreadName()+") windowHandle "+toHexString(windowHandle)+", visible: "+visible+", parentWindowHandle "+toHexString(parentWindowHandle)+", parentWindow "+ Display.hashCodeNullSafe(parentWindow)+" "+x+"/"+y+" "+width+"x"+height);
+ System.err.println("Window.reparentWindow: END-X ("+getThreadName()+") windowHandle "+toHexString(windowHandle)+", visible: "+visible+", parentWindowHandle "+toHexString(parentWindowHandle)+", parentWindow "+ Display.hashCodeNullSafe(parentWindow)+" "+getX()+"/"+getY()+" "+getWidth()+"x"+getHeight());
}
}
}
@@ -1557,7 +1561,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
for (int i = 0; i < keyListeners.size(); i++ ) {
sb.append(keyListeners.get(i)+", ");
}
- sb.append("], windowLock "+windowLock+"]");
+ sb.append("], windowLock "+windowLock+", surfaceLockCount "+surfaceLockCount+"]");
return sb.toString();
}
@@ -1566,15 +1570,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
public void runOnEDTIfAvail(boolean wait, final Runnable task) {
- if(windowLock.isOwner(Thread.currentThread())) {
+ if( windowLock.isOwner( Thread.currentThread() ) ) {
task.run();
} else {
- Screen scrn = getScreen();
- if(null==scrn) {
- throw new RuntimeException("Null screen of inner class: "+this);
- }
- DisplayImpl d = (DisplayImpl) scrn.getDisplay();
- d.runOnEDTIfAvail(wait, task);
+ ( (DisplayImpl) screen.getDisplay() ).runOnEDTIfAvail(wait, task);
}
}
@@ -1899,7 +1898,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
public void enqueueEvent(boolean wait, com.jogamp.newt.event.NEWTEvent event) {
if(isNativeValid()) {
- ((DisplayImpl)getScreen().getDisplay()).enqueueEvent(wait, event);
+ ((DisplayImpl)screen.getDisplay()).enqueueEvent(wait, event);
}
}
@@ -1914,7 +1913,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
repaintQueued=true;
final boolean discardTO = QUEUED_EVENT_TO <= System.currentTimeMillis()-e.getWhen();
if(DEBUG_IMPLEMENTATION) {
- System.err.println("Window.consumeEvent: "+Thread.currentThread().getName()+" - queued "+e+", discard-to "+discardTO);
+ System.err.println("Window.consumeEvent: REPAINT "+Thread.currentThread().getName()+" - queued "+e+", discard-to "+discardTO);
// Thread.dumpStack();
}
return discardTO; // discardTO:=true -> consumed
@@ -1930,7 +1929,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
if( null != windowLock.getOwner() ) {
final boolean discardTO = QUEUED_EVENT_TO <= System.currentTimeMillis()-e.getWhen();
if(DEBUG_IMPLEMENTATION) {
- System.err.println("Window.consumeEvent: "+Thread.currentThread().getName()+" - queued "+e+", discard-to "+discardTO);
+ System.err.println("Window.consumeEvent: RESIZED "+Thread.currentThread().getName()+" - queued "+e+", discard-to "+discardTO);
// Thread.dumpStack();
}
return discardTO; // discardTO:=true -> consumed
@@ -2430,10 +2429,11 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
private boolean waitForVisible(boolean visible, boolean failFast, long timeOut) {
- DisplayImpl display = (DisplayImpl) screen.getDisplay();
+ final DisplayImpl display = (DisplayImpl) screen.getDisplay();
+ display.dispatchMessagesNative(); // status up2date
for(long sleep = timeOut; 0<sleep && this.visible != visible; sleep-=10 ) {
- display.dispatchMessagesNative(); // status up2date
try { Thread.sleep(10); } catch (InterruptedException ie) {}
+ display.dispatchMessagesNative(); // status up2date
}
if(this.visible != visible) {
final String msg = "Visibility not reached as requested within "+timeOut+"ms : requested "+visible+", is "+this.visible;
@@ -2441,9 +2441,12 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
throw new NativeWindowException(msg);
} else if (DEBUG_IMPLEMENTATION) {
System.err.println(msg);
+ Thread.dumpStack();
}
+ return false;
+ } else {
+ return true;
}
- return this.visible == visible;
}
/** Triggered by implementation's WM events to update the client-area size w/o insets/decorations. */
@@ -2467,18 +2470,14 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
}
private boolean waitForSize(int w, int h, boolean failFast, long timeOut) {
- DisplayImpl display = (DisplayImpl) screen.getDisplay();
- boolean reached = false;
- for(long sleep = timeOut; !reached && 0<sleep; sleep-=10 ) {
- if( w==getWidth() && h==getHeight() ) {
- // reached pos/size
- reached = true;
- } else {
- display.dispatchMessagesNative(); // status up2date
- try { Thread.sleep(10); } catch (InterruptedException ie) {}
- }
+ final DisplayImpl display = (DisplayImpl) screen.getDisplay();
+ display.dispatchMessagesNative(); // status up2date
+ long sleep;
+ for(sleep = timeOut; 0<sleep && w!=getWidth() && h!=getHeight(); sleep-=10 ) {
+ try { Thread.sleep(10); } catch (InterruptedException ie) {}
+ display.dispatchMessagesNative(); // status up2date
}
- if(!reached) {
+ if(0 >= sleep) {
final String msg = "Size/Pos not reached as requested within "+timeOut+"ms : requested "+w+"x"+h+", is "+getWidth()+"x"+getHeight();
if(failFast) {
throw new NativeWindowException(msg);
@@ -2486,8 +2485,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
System.err.println(msg);
Thread.dumpStack();
}
+ return false;
+ } else {
+ return true;
}
- return reached;
}
/** Triggered by implementation's WM events to update the position. */
diff --git a/src/newt/classes/jogamp/newt/driver/awt/AWTEDTUtil.java b/src/newt/classes/jogamp/newt/driver/awt/AWTEDTUtil.java
index 2175f2190..27d0f3506 100644
--- a/src/newt/classes/jogamp/newt/driver/awt/AWTEDTUtil.java
+++ b/src/newt/classes/jogamp/newt/driver/awt/AWTEDTUtil.java
@@ -72,7 +72,7 @@ public class AWTEDTUtil implements EDTUtil {
synchronized(edtLock) {
waitUntilStopped();
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT reset - edt: "+nedt);
+ System.err.println(Thread.currentThread()+": AWT-EDT reset - edt: "+nedt);
}
this.nedt = new NewtEventDispatchThread(threadGroup, name);
this.nedt.setDaemon(true); // don't stop JVM from shutdown ..
@@ -81,13 +81,13 @@ public class AWTEDTUtil implements EDTUtil {
private final void startImpl() {
if(nedt.isAlive()) {
- throw new RuntimeException("EDT Thread.isAlive(): true, isRunning: "+nedt.isRunning()+", edt: "+nedt);
+ throw new RuntimeException("AWT-EDT Thread.isAlive(): true, isRunning: "+nedt.isRunning()+", edt: "+nedt);
}
start_iter++;
nedt.setName(name+start_iter);
nedt.shouldStop = false;
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT START - edt: "+nedt);
+ System.err.println(Thread.currentThread()+": AWT-EDT START - edt: "+nedt);
// Thread.dumpStack();
}
nedt.start();
@@ -124,9 +124,6 @@ public class AWTEDTUtil implements EDTUtil {
}
private void invokeImpl(boolean wait, Runnable task, boolean stop) {
- if(task == null) {
- throw new RuntimeException("Null Runnable");
- }
Throwable throwable = null;
RunnableTask rTask = null;
Object rTaskLock = new Object();
@@ -135,7 +132,7 @@ public class AWTEDTUtil implements EDTUtil {
if( nedt.shouldStop ) {
// drop task ..
if(DEBUG) {
- System.err.println("Warning: EDT about (1) to stop, won't enqueue new task: "+nedt);
+ System.err.println(Thread.currentThread()+": Warning: AWT-EDT about (1) to stop, won't enqueue new task: "+nedt);
Thread.dumpStack();
}
return;
@@ -143,20 +140,24 @@ public class AWTEDTUtil implements EDTUtil {
// System.err.println(Thread.currentThread()+" XXX stop: "+stop+", tasks: "+edt.tasks.size()+", task: "+task);
// Thread.dumpStack();
if(stop) {
- nedt.shouldStop = true;
+ synchronized(nedt.sync) {
+ nedt.shouldStop = true;
+ nedt.sync.notifyAll(); // stop immediate if waiting (poll freq)
+ }
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT signal STOP (on edt: "+isCurrentThreadEDT()+") - "+nedt);
+ System.err.println(Thread.currentThread()+": AWT-EDT signal STOP (on edt: "+isCurrentThreadEDT()+") - "+nedt);
// Thread.dumpStack();
}
+ } else if( !nedt.isRunning() ) {
+ // start if should not stop && not started yet
+ startImpl();
}
- if( isCurrentThreadEDT() ) {
+ if( null == task ) {
+ wait = false;
+ } else if( isCurrentThreadEDT() ) {
task.run();
wait = false; // running in same thread (EDT) -> no wait
} else {
- // start if should not stop && not started yet
- if( !stop && !nedt.isRunning() ) {
- startImpl();
- }
rTask = new RunnableTask(task,
wait ? rTaskLock : null,
true /* always catch and report Exceptions, don't disturb EDT */);
@@ -239,7 +240,7 @@ public class AWTEDTUtil implements EDTUtil {
@Override
final public void run() {
if(DEBUG) {
- System.err.println(getName()+": EDT run() START "+ getName());
+ System.err.println(getName()+": AWT-EDT run() START "+ getName());
}
RuntimeException error = null;
try {
@@ -269,11 +270,11 @@ public class AWTEDTUtil implements EDTUtil {
if(t instanceof RuntimeException) {
error = (RuntimeException) t;
} else {
- error = new RuntimeException("Within EDT", t);
+ error = new RuntimeException("Within AWT-EDT", t);
}
} finally {
if(DEBUG) {
- System.err.println(getName()+": EDT run() END "+ getName()+", "+error);
+ System.err.println(getName()+": AWT-EDT run() END "+ getName()+", "+error);
}
synchronized(edtLock) {
isRunning = !shouldStop;
@@ -282,7 +283,7 @@ public class AWTEDTUtil implements EDTUtil {
}
}
if(DEBUG) {
- System.err.println(getName()+": EDT run() EXIT "+ getName()+", exception: "+error);
+ System.err.println(getName()+": AWT-EDT run() EXIT "+ getName()+", exception: "+error);
}
if(null!=error) {
throw error;
diff --git a/src/newt/classes/jogamp/newt/driver/windows/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/windows/WindowDriver.java
index 6aac8617c..2ec88852c 100644
--- a/src/newt/classes/jogamp/newt/driver/windows/WindowDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/windows/WindowDriver.java
@@ -71,13 +71,15 @@ public class WindowDriver extends WindowImpl {
if (0 != hdc) {
throw new InternalError("surface not released");
}
- hdc = GDI.GetDC(getWindowHandle());
- hmon = MonitorFromWindow0(getWindowHandle());
+ final long hWnd = getWindowHandle();
+ hdc = GDI.GetDC(hWnd);
// return ( 0 == hdc ) ? LOCK_SURFACE_NOT_READY : ( hdc_old != hdc ) ? LOCK_SURFACE_CHANGED : LOCK_SUCCESS ;
if( 0 == hdc ) {
return LOCK_SURFACE_NOT_READY;
- }
+ }
+ hmon = MonitorFromWindow0(hWnd);
+
if( hdc_old == hdc ) {
return LOCK_SUCCESS;
}
@@ -217,14 +219,14 @@ public class WindowDriver extends WindowImpl {
@Override
protected boolean setPointerVisibleImpl(final boolean pointerVisible) {
- final Boolean[] res = new Boolean[] { Boolean.FALSE };
+ final boolean[] res = new boolean[] { false };
this.runOnEDTIfAvail(true, new Runnable() {
public void run() {
- res[0] = Boolean.valueOf(setPointerVisible0(getWindowHandle(), pointerVisible));
+ res[0] = setPointerVisible0(getWindowHandle(), pointerVisible);
}
});
- return res[0].booleanValue();
+ return res[0];
}
@Override
diff --git a/src/newt/classes/com/jogamp/newt/swt/SWTEDTUtil.java b/src/newt/classes/jogamp/newt/swt/SWTEDTUtil.java
index 42e1c9be5..7297e5858 100644
--- a/src/newt/classes/com/jogamp/newt/swt/SWTEDTUtil.java
+++ b/src/newt/classes/jogamp/newt/swt/SWTEDTUtil.java
@@ -25,9 +25,7 @@
* authors and should not be interpreted as representing official policies, either expressed
* or implied, of JogAmp Community.
*/
-package com.jogamp.newt.swt;
-
-import java.awt.EventQueue;
+package jogamp.newt.swt;
import javax.media.nativewindow.NativeWindowException;
@@ -83,7 +81,7 @@ public class SWTEDTUtil implements EDTUtil {
synchronized(edtLock) {
waitUntilStopped();
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT reset - edt: "+nedt);
+ System.err.println(Thread.currentThread()+": SWT-EDT reset - edt: "+nedt);
}
this.nedt = new NewtEventDispatchThread(threadGroup, name);
this.nedt.setDaemon(true); // don't stop JVM from shutdown ..
@@ -92,13 +90,13 @@ public class SWTEDTUtil implements EDTUtil {
private final void startImpl() {
if(nedt.isAlive()) {
- throw new RuntimeException("EDT Thread.isAlive(): true, isRunning: "+nedt.isRunning()+", edt: "+nedt);
+ throw new RuntimeException("SWT-EDT Thread.isAlive(): true, isRunning: "+nedt.isRunning()+", edt: "+nedt);
}
start_iter++;
nedt.setName(name+start_iter);
nedt.shouldStop = false;
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT START - edt: "+nedt);
+ System.err.println(Thread.currentThread()+": SWT-EDT START - edt: "+nedt);
// Thread.dumpStack();
}
nedt.start();
@@ -136,9 +134,6 @@ public class SWTEDTUtil implements EDTUtil {
}
private void invokeImpl(boolean wait, Runnable task, boolean stop) {
- if(task == null) {
- throw new RuntimeException("Null Runnable");
- }
Throwable throwable = null;
RunnableTask rTask = null;
Object rTaskLock = new Object();
@@ -147,7 +142,7 @@ public class SWTEDTUtil implements EDTUtil {
if( nedt.shouldStop ) {
// drop task ..
if(DEBUG) {
- System.err.println("Warning: EDT about (1) to stop, won't enqueue new task: "+nedt);
+ System.err.println(Thread.currentThread()+": Warning: SWT-EDT about (1) to stop, won't enqueue new task: "+nedt);
Thread.dumpStack();
}
return;
@@ -155,22 +150,26 @@ public class SWTEDTUtil implements EDTUtil {
// System.err.println(Thread.currentThread()+" XXX stop: "+stop+", tasks: "+edt.tasks.size()+", task: "+task);
// Thread.dumpStack();
if(stop) {
- nedt.shouldStop = true;
+ synchronized(nedt.sync) {
+ nedt.shouldStop = true;
+ nedt.sync.notifyAll(); // stop immediate if waiting (poll freq)
+ }
if(DEBUG) {
- System.err.println(Thread.currentThread()+": EDT signal STOP (on edt: "+isCurrentThreadEDT()+") - "+nedt);
+ System.err.println(Thread.currentThread()+": SWT-EDT signal STOP (on edt: "+isCurrentThreadEDT()+") - "+nedt);
// Thread.dumpStack();
}
+ } else if( !nedt.isRunning() ) {
+ // start if should not stop && not started yet
+ startImpl();
}
- if( isCurrentThreadEDT() ) {
+ if( null == task ) {
+ wait = false;
+ } else if( isCurrentThreadEDT() ) {
task.run();
wait = false; // running in same thread (EDT) -> no wait
} else if( swtDisplay.isDisposed() ) {
wait = false; // drop task, SWT disposed
} else {
- // start if should not stop && not started yet
- if( !stop && !nedt.isRunning() ) {
- startImpl();
- }
rTask = new RunnableTask(task,
wait ? rTaskLock : null,
true /* always catch and report Exceptions, don't disturb EDT */);
@@ -255,7 +254,7 @@ public class SWTEDTUtil implements EDTUtil {
@Override
final public void run() {
if(DEBUG) {
- System.err.println(getName()+": EDT run() START "+ getName());
+ System.err.println(getName()+": SWT-EDT run() START "+ getName());
}
RuntimeException error = null;
try {
@@ -289,11 +288,11 @@ public class SWTEDTUtil implements EDTUtil {
if(t instanceof RuntimeException) {
error = (RuntimeException) t;
} else {
- error = new RuntimeException("Within EDT", t);
+ error = new RuntimeException("Within SWT-EDT", t);
}
} finally {
if(DEBUG) {
- System.err.println(getName()+": EDT run() END "+ getName()+", "+error);
+ System.err.println(getName()+": SWT-EDT run() END "+ getName()+", "+error);
}
synchronized(edtLock) {
isRunning = !shouldStop;
@@ -302,7 +301,7 @@ public class SWTEDTUtil implements EDTUtil {
}
}
if(DEBUG) {
- System.err.println(getName()+": EDT run() EXIT "+ getName()+", exception: "+error);
+ System.err.println(getName()+": SWT-EDT run() EXIT "+ getName()+", exception: "+error);
}
if(null!=error) {
throw error;
diff --git a/src/newt/classes/jogamp/newt/swt/event/SWTNewtEventFactory.java b/src/newt/classes/jogamp/newt/swt/event/SWTNewtEventFactory.java
new file mode 100644
index 000000000..e238f5d9e
--- /dev/null
+++ b/src/newt/classes/jogamp/newt/swt/event/SWTNewtEventFactory.java
@@ -0,0 +1,249 @@
+/**
+ * Copyright 2012 JogAmp Community. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
+ * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * The views and conclusions contained in the software and documentation are those of the
+ * authors and should not be interpreted as representing official policies, either expressed
+ * or implied, of JogAmp Community.
+ */
+
+package jogamp.newt.swt.event;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.widgets.Event;
+import org.eclipse.swt.widgets.Listener;
+
+import com.jogamp.common.util.IntIntHashMap;
+import com.jogamp.newt.event.InputEvent;
+
+/**
+ * SWT event translator to NEWT, inclusive dispatch listener.
+ * <p>
+ * <b>Disclaimer:</b> This code is merely tested and subject to change.
+ * </p>
+ */
+public class SWTNewtEventFactory {
+
+ protected static final IntIntHashMap eventTypeSWT2NEWT;
+
+ static {
+ IntIntHashMap map = new IntIntHashMap();
+ map.setKeyNotFoundValue(0xFFFFFFFF);
+
+ // map.put(SWT.MouseXXX, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_CLICKED);
+ map.put(SWT.MouseDown, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_PRESSED);
+ map.put(SWT.MouseUp, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_RELEASED);
+ map.put(SWT.MouseMove, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_MOVED);
+ map.put(SWT.MouseEnter, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_ENTERED);
+ map.put(SWT.MouseExit, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_EXITED);
+ // map.put(SWT.MouseXXX, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_DRAGGED);
+ map.put(SWT.MouseVerticalWheel, com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_WHEEL_MOVED);
+
+ map.put(SWT.KeyDown, com.jogamp.newt.event.KeyEvent.EVENT_KEY_PRESSED);
+ map.put(SWT.KeyUp, com.jogamp.newt.event.KeyEvent.EVENT_KEY_RELEASED);
+ // map.put(SWT.KeyXXX, com.jogamp.newt.event.KeyEvent.EVENT_KEY_TYPED);
+
+ eventTypeSWT2NEWT = map;
+ }
+
+ public static final int swtModifiers2Newt(int awtMods, boolean mouseHint) {
+ int newtMods = 0;
+ if ((awtMods & SWT.SHIFT) != 0) newtMods |= com.jogamp.newt.event.InputEvent.SHIFT_MASK;
+ if ((awtMods & SWT.CTRL) != 0) newtMods |= com.jogamp.newt.event.InputEvent.CTRL_MASK;
+ if ((awtMods & SWT.ALT) != 0) newtMods |= com.jogamp.newt.event.InputEvent.ALT_MASK;
+ return newtMods;
+ }
+
+ public static final com.jogamp.newt.event.InputEvent createInputEvent(org.eclipse.swt.widgets.Event event, Object source) {
+ com.jogamp.newt.event.InputEvent res = createMouseEvent(event, source);
+ if(null == res) {
+ res = createKeyEvent(event, source);
+ }
+ return res;
+ }
+
+ public static final com.jogamp.newt.event.MouseEvent createMouseEvent(org.eclipse.swt.widgets.Event event, Object source) {
+ switch(event.type) {
+ case SWT.MouseDown:
+ case SWT.MouseUp:
+ case SWT.MouseMove:
+ case SWT.MouseEnter:
+ case SWT.MouseExit:
+ case SWT.MouseVerticalWheel:
+ break;
+ default:
+ return null;
+ }
+ int type = eventTypeSWT2NEWT.get(event.type);
+ if(0xFFFFFFFF != type) {
+ int rotation = 0;
+ if (SWT.MouseVerticalWheel == event.type) {
+ // SWT/NEWT rotation is reversed - AWT +1 is down, NEWT +1 is up.
+ // rotation = -1 * (int) event.rotation;
+ rotation = (int) event.rotation;
+ }
+
+ int mods = swtModifiers2Newt(event.stateMask, true);
+
+ if( source instanceof com.jogamp.newt.Window) {
+ final com.jogamp.newt.Window newtSource = (com.jogamp.newt.Window)source;
+ if(newtSource.isPointerConfined()) {
+ mods |= InputEvent.CONFINED_MASK;
+ }
+ if(!newtSource.isPointerVisible()) {
+ mods |= InputEvent.INVISIBLE_MASK;
+ }
+ }
+
+ return new com.jogamp.newt.event.MouseEvent(
+ type, (null==source)?(Object)event.data:source, (0xFFFFFFFFL & (long)event.time),
+ mods, event.x, event.y, event.count, event.button, rotation);
+ }
+ return null; // no mapping ..
+ }
+
+ public static final com.jogamp.newt.event.KeyEvent createKeyEvent(org.eclipse.swt.widgets.Event event, Object source) {
+ switch(event.type) {
+ case SWT.KeyDown:
+ case SWT.KeyUp:
+ break;
+ default:
+ return null;
+ }
+ int type = eventTypeSWT2NEWT.get(event.type);
+ if(0xFFFFFFFF != type) {
+ return new com.jogamp.newt.event.KeyEvent(
+ type, (null==source)?(Object)event.data:source, (0xFFFFFFFFL & (long)event.time),
+ swtModifiers2Newt(event.stateMask, false),
+ event.keyCode, event.character);
+ }
+ return null; // no mapping ..
+ }
+
+ //
+ //
+ //
+
+ int dragButtonDown = 0;
+
+ public SWTNewtEventFactory() {
+ resetButtonsDown();
+ }
+
+ final void resetButtonsDown() {
+ dragButtonDown = 0;
+ }
+
+ public final boolean dispatchMouseEvent(org.eclipse.swt.widgets.Event event, Object source, com.jogamp.newt.event.MouseListener l) {
+ com.jogamp.newt.event.MouseEvent res = createMouseEvent(event, source);
+ if(null != res) {
+ if(null != l) {
+ switch(event.type) {
+ case SWT.MouseDown:
+ dragButtonDown = event.button;
+ l.mousePressed(res); break;
+ case SWT.MouseUp:
+ dragButtonDown = 0;
+ l.mouseReleased(res);
+ {
+ final com.jogamp.newt.event.MouseEvent res2 = new com.jogamp.newt.event.MouseEvent(
+ com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_CLICKED,
+ res.getSource(),
+ res.getWhen(), res.getModifiers(),
+ res.getX(), res.getY(), res.getClickCount(),
+ res.getButton(), res.getWheelRotation() );
+ l.mouseClicked(res2);
+ }
+ break;
+ case SWT.MouseMove:
+ if( 0 < dragButtonDown ) {
+ final com.jogamp.newt.event.MouseEvent res2 = new com.jogamp.newt.event.MouseEvent(
+ com.jogamp.newt.event.MouseEvent.EVENT_MOUSE_DRAGGED,
+ res.getSource(),
+ res.getWhen(), res.getModifiers(),
+ res.getX(), res.getY(), res.getClickCount(),
+ dragButtonDown, res.getWheelRotation() );
+ l.mouseDragged( res2 );
+ } else {
+ l.mouseMoved(res);
+ }
+ break;
+ case SWT.MouseEnter:
+ l.mouseEntered(res);
+ break;
+ case SWT.MouseExit:
+ resetButtonsDown();
+ l.mouseExited(res);
+ break;
+ case SWT.MouseVerticalWheel:
+ l.mouseWheelMoved(res);
+ break;
+ }
+ }
+ return true;
+ }
+ return false;
+ }
+
+ public final boolean dispatchKeyEvent(org.eclipse.swt.widgets.Event event, Object source, com.jogamp.newt.event.KeyListener l) {
+ com.jogamp.newt.event.KeyEvent res = createKeyEvent(event, source);
+ if(null != res) {
+ if(null != l) {
+ switch(event.type) {
+ case SWT.KeyDown:
+ l.keyPressed(res);
+ break;
+ case SWT.KeyUp:
+ l.keyReleased(res);
+ l.keyTyped(res);
+ break;
+ }
+ }
+ return true;
+ }
+ return false;
+ }
+
+ public final void attachDispatchListener(final org.eclipse.swt.widgets.Control ctrl, final Object source,
+ final com.jogamp.newt.event.MouseListener ml,
+ final com.jogamp.newt.event.KeyListener kl) {
+ final Listener listener = new Listener () {
+ @Override
+ public void handleEvent (Event event) {
+ if( dispatchMouseEvent( event, source, ml ) ) {
+ return;
+ }
+ if( dispatchKeyEvent( event, source, kl ) ) {
+ return;
+ }
+ } };
+ ctrl.addListener(SWT.MouseDown, listener);
+ ctrl.addListener(SWT.MouseUp, listener);
+ ctrl.addListener(SWT.MouseMove, listener);
+ ctrl.addListener(SWT.MouseEnter, listener);
+ ctrl.addListener(SWT.MouseExit, listener);
+ ctrl.addListener(SWT.MouseVerticalWheel, listener);
+ ctrl.addListener(SWT.KeyDown, listener);
+ ctrl.addListener(SWT.KeyUp, listener);
+ }
+}
+
diff --git a/src/newt/native/WindowsWindow.c b/src/newt/native/WindowsWindow.c
index e3d5cffa0..e7b454580 100644
--- a/src/newt/native/WindowsWindow.c
+++ b/src/newt/native/WindowsWindow.c
@@ -1034,23 +1034,22 @@ static LRESULT CALLBACK wndProc(HWND wnd, UINT message, WPARAM wParam, LPARAM lP
case WM_PAINT: {
RECT r;
useDefWindowProc = 0;
- if (GetUpdateRect(wnd, &r, TRUE /* erase background */)) {
- /*
- jint width = r.right-r.left;
- jint height = r.bottom-r.top;
- if (width > 0 && height > 0) {
- (*env)->CallVoidMethod(env, window, windowRepaintID, JNI_FALSE, r.left, r.top, width, height);
- }
- ValidateRect(wnd, &r);
- */
+ if (GetUpdateRect(wnd, &r, FALSE /* do not erase background */)) {
+ // clear the whole client area and issue repaint for it, w/o looping through erase background
+ ValidateRect(wnd, NULL); // clear all!
+ (*env)->CallVoidMethod(env, window, windowRepaintID, JNI_FALSE, 0, 0, -1, -1);
+ } else {
+ // shall not happen ?
+ ValidateRect(wnd, NULL); // clear all!
}
+ // return 0 == done
break;
}
case WM_ERASEBKGND:
// ignore erase background
(*env)->CallVoidMethod(env, window, windowRepaintID, JNI_FALSE, 0, 0, -1, -1);
useDefWindowProc = 0;
- res = 1; // OpenGL, etc .. erases the background, hence we claim to have just done this
+ res = 1; // return 1 == done, OpenGL, etc .. erases the background, hence we claim to have just done this
break;
diff --git a/src/test/com/jogamp/opengl/test/junit/jogl/demos/es2/GearsES2.java b/src/test/com/jogamp/opengl/test/junit/jogl/demos/es2/GearsES2.java
index e9fe9b401..a3023538f 100644
--- a/src/test/com/jogamp/opengl/test/junit/jogl/demos/es2/GearsES2.java
+++ b/src/test/com/jogamp/opengl/test/junit/jogl/demos/es2/GearsES2.java
@@ -60,8 +60,8 @@ public class GearsES2 implements GLEventListener {
private int swapInterval = 0;
private boolean pmvUseBackingArray = true; // the default for PMVMatrix now, since it's faster
// private MouseListener gearsMouse = new TraceMouseAdapter(new GearsMouseAdapter());
- private MouseListener gearsMouse = new GearsMouseAdapter();
- private KeyListener gearsKeys = new GearsKeyAdapter();
+ public MouseListener gearsMouse = new GearsMouseAdapter();
+ public KeyListener gearsKeys = new GearsKeyAdapter();
private int prevMouseX, prevMouseY;
private boolean doRotate = true;
@@ -352,6 +352,10 @@ public class GearsES2 implements GLEventListener {
window = (Window) source;
width=window.getWidth();
height=window.getHeight();
+ } else if (source instanceof GLAutoDrawable) {
+ GLAutoDrawable glad = (GLAutoDrawable) source;
+ width = glad.getWidth();
+ height = glad.getHeight();
} else if (GLProfile.isAWTAvailable() && source instanceof java.awt.Component) {
java.awt.Component comp = (java.awt.Component) source;
width=comp.getWidth();
diff --git a/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestNewtCanvasSWTBug628ResizeDeadlock.java b/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestNewtCanvasSWTBug628ResizeDeadlock.java
index 9c0762c12..1f3bf3156 100644
--- a/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestNewtCanvasSWTBug628ResizeDeadlock.java
+++ b/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestNewtCanvasSWTBug628ResizeDeadlock.java
@@ -65,7 +65,7 @@ import com.jogamp.opengl.test.junit.util.UITestCase;
public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
- static int duration = 1000;
+ static int duration = 500;
static class BigFlashingX implements GLEventListener
{
@@ -262,7 +262,7 @@ public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
shell = new Shell( display );
Assert.assertNotNull( shell );
shell.setLayout( new FillLayout() );
- composite = new Composite( shell, SWT.NONE );
+ composite = new Composite( shell, SWT.NO_BACKGROUND );
composite.setLayout( new FillLayout() );
Assert.assertNotNull( composite );
}});
@@ -301,10 +301,9 @@ public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
dsc.init();
final GLWindow glWindow;
- final NewtCanvasSWT canvas;
{
final GLProfile gl2Profile = GLProfile.get( GLProfile.GL2 ) ;
- GLCapabilities caps = new GLCapabilities( gl2Profile ) ;
+ final GLCapabilities caps = new GLCapabilities( gl2Profile ) ;
glWindow = GLWindow.create( caps ) ;
glWindow.addGLEventListener( new BigFlashingX() ) ;
glWindow.addKeyListener(new KeyAdapter() {
@@ -314,7 +313,7 @@ public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
glWindow.display();
}
});
- canvas = NewtCanvasSWT.create( dsc.composite, 0, glWindow ) ;
+ NewtCanvasSWT.create( dsc.composite, 0, glWindow ) ;
}
dsc.display.syncExec( new Runnable() {
@@ -342,7 +341,7 @@ public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
}
{
- new Thread(new Runnable() {
+ final Thread t = new Thread(new Runnable() {
@Override
public void run() {
try {
@@ -360,13 +359,16 @@ public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
} catch( InterruptedException e ) { }
shallStop = true;
dsc.display.wake();
- } } ).start();
+ } } );
+ t.setDaemon(true);
+ t.start();
}
try {
while( !shallStop && !dsc.display.isDisposed() ) {
- if( !dsc.display.readAndDispatch() ) {
- dsc.display.sleep();
+ if( !dsc.display.readAndDispatch() && !shallStop ) {
+ // blocks on linux .. dsc.display.sleep();
+ Thread.sleep(10);
}
}
} catch (Exception e0) {
@@ -374,8 +376,7 @@ public class TestNewtCanvasSWTBug628ResizeDeadlock extends UITestCase {
Assert.assertTrue("Deadlock @ dispatch: "+e0, false);
}
- System.err.println("NewtCanvasAWT Dispose");
- canvas.dispose();
+ // canvas is disposed implicit, due to it's disposed listener !
dsc.dispose();
}
diff --git a/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTBug643AsyncExec.java b/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTBug643AsyncExec.java
new file mode 100644
index 000000000..97b3ab243
--- /dev/null
+++ b/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTBug643AsyncExec.java
@@ -0,0 +1,343 @@
+/**
+ * Copyright 2012 JogAmp Community. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without modification, are
+ * permitted provided that the following conditions are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright notice, this list of
+ * conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright notice, this list
+ * of conditions and the following disclaimer in the documentation and/or other materials
+ * provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
+ * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * The views and conclusions contained in the software and documentation are those of the
+ * authors and should not be interpreted as representing official policies, either expressed
+ * or implied, of JogAmp Community.
+ */
+
+package com.jogamp.opengl.test.junit.jogl.swt;
+
+import java.awt.AWTException;
+import java.lang.reflect.InvocationTargetException;
+
+import org.eclipse.swt.SWT ;
+
+import org.eclipse.swt.layout.FillLayout ;
+
+import org.eclipse.swt.widgets.Composite ;
+import org.eclipse.swt.widgets.Display ;
+import org.eclipse.swt.widgets.Shell ;
+import org.junit.Assume;
+import org.junit.Test;
+
+import javax.media.opengl.GLAutoDrawable;
+import javax.media.opengl.GLCapabilities ;
+import javax.media.opengl.GLProfile;
+
+import jogamp.newt.swt.SWTEDTUtil;
+import jogamp.newt.swt.event.SWTNewtEventFactory;
+import junit.framework.Assert;
+
+import com.jogamp.nativewindow.swt.SWTAccessor;
+import com.jogamp.newt.opengl.GLWindow ;
+import com.jogamp.newt.swt.NewtCanvasSWT ;
+import com.jogamp.opengl.swt.GLCanvas;
+import com.jogamp.opengl.test.junit.jogl.demos.es2.GearsES2;
+import com.jogamp.opengl.test.junit.util.AWTRobotUtil;
+import com.jogamp.opengl.test.junit.util.MiscUtils;
+import com.jogamp.opengl.test.junit.util.UITestCase;
+import com.jogamp.opengl.util.Animator;
+
+////////////////////////////////////////////////////////////////////////////////
+
+
+public class TestSWTBug643AsyncExec extends UITestCase {
+
+ static int duration = 500;
+ static boolean useAnimator = false;
+
+ ////////////////////////////////////////////////////////////////////////////////
+
+ static void resetSWTAndNEWTEDTCounter() {
+ synchronized(swtCountSync) {
+ swtCount=0;
+ }
+ synchronized(edtCountSync) {
+ edtCount=0;
+ }
+ }
+ static int incrSWTCount() {
+ synchronized(swtCountSync) {
+ swtCount++;
+ return swtCount;
+ }
+ }
+ static int getSWTCount() {
+ synchronized(swtCountSync) {
+ return swtCount;
+ }
+ }
+ static int incrNEWTCount() {
+ synchronized(edtCountSync) {
+ edtCount++;
+ return edtCount;
+ }
+ }
+ static int getNEWTCount() {
+ synchronized(edtCountSync) {
+ return edtCount;
+ }
+ }
+ static Object swtCountSync = new Object();
+ static int swtCount = 0;
+ static Object edtCountSync = new Object();
+ static int edtCount = 0;
+
+ ////////////////////////////////////////////////////////////////////////////////
+
+ static class AsyncExecEDTFeederThread extends Thread {
+ volatile boolean shallStop = false;
+ private Display swtDisplay ;
+ private jogamp.newt.DisplayImpl newtDisplay;
+ private int swtN, newtN ;
+
+ public AsyncExecEDTFeederThread( Display swtDisplay, com.jogamp.newt.Display newtDisplay )
+ {
+ super();
+ this.swtDisplay = swtDisplay ;
+ this.newtDisplay = (jogamp.newt.DisplayImpl)newtDisplay;
+ }
+
+ final Runnable swtAsyncAction = new Runnable() {
+ public void run()
+ {
+ ++swtN ; incrSWTCount();
+ System.err.println("[SWT A-i shallStop "+shallStop+"]: Counter[loc "+swtN+", glob: "+getSWTCount()+"]");
+ } };
+
+ final Runnable newtAsyncAction = new Runnable() {
+ public void run()
+ {
+ ++newtN ; incrNEWTCount();
+ System.err.println("[NEWT A-i shallStop "+shallStop+"]: Counter[loc "+newtN+", glob: "+getNEWTCount()+"]");
+ } };
+
+ public void run()
+ {
+ System.err.println("[A-0 shallStop "+shallStop+"]");
+
+ while( !shallStop && !swtDisplay.isDisposed() )
+ {
+ try
+ {
+ swtDisplay.asyncExec( swtAsyncAction );
+ if(null != newtDisplay && newtDisplay.isNativeValid() && newtDisplay.getEDTUtil().isRunning()) {
+ // only perform async exec on valid and already running NEWT EDT!
+ newtDisplay.runOnEDTIfAvail(false, newtAsyncAction);
+ }
+ Thread.sleep( 50L ) ;
+ } catch( InterruptedException e ) {
+ break ;
+ }
+ }
+ System.err.println("*R-Exit* shallStop "+shallStop);
+ }
+ }
+
+ ////////////////////////////////////////////////////////////////////////////////
+
+ private volatile boolean shallStop = false;
+
+ static class SWT_DSC {
+ Display display;
+ Shell shell;
+ Composite composite;
+
+ public void init() {
+ SWTAccessor.invoke(true, new Runnable() {
+ public void run() {
+ display = new Display();
+ Assert.assertNotNull( display );
+ }});
+
+ display.syncExec(new Runnable() {
+ public void run() {
+ shell = new Shell( display );
+ Assert.assertNotNull( shell );
+ shell.setLayout( new FillLayout() );
+ composite = new Composite( shell, SWT.NO_BACKGROUND );
+ composite.setLayout( new FillLayout() );
+ Assert.assertNotNull( composite );
+ }});
+ }
+
+ public void dispose() {
+ Assert.assertNotNull( display );
+ Assert.assertNotNull( shell );
+ Assert.assertNotNull( composite );
+ try {
+ display.syncExec(new Runnable() {
+ public void run() {
+ composite.dispose();
+ shell.dispose();
+ }});
+ SWTAccessor.invoke(true, new Runnable() {
+ public void run() {
+ display.dispose();
+ }});
+ }
+ catch( Throwable throwable ) {
+ throwable.printStackTrace();
+ Assume.assumeNoException( throwable );
+ }
+ display = null;
+ shell = null;
+ composite = null;
+ }
+ }
+
+ private void testImpl(boolean useJOGLGLCanvas, boolean useNewtCanvasSWT, boolean glWindowPreVisible) throws InterruptedException, AWTException, InvocationTargetException {
+ resetSWTAndNEWTEDTCounter();
+
+ final SWT_DSC dsc = new SWT_DSC();
+ dsc.init();
+
+ final com.jogamp.newt.Display newtDisplay;
+ {
+ final GLProfile gl2Profile = GLProfile.get( GLProfile.GL2 ) ;
+ final GLCapabilities caps = new GLCapabilities( gl2Profile ) ;
+
+ final GLAutoDrawable glad;
+ if( useJOGLGLCanvas ) {
+ final GearsES2 demo = new GearsES2();
+ final GLCanvas glc = GLCanvas.create(dsc.composite, 0, caps, null, null);
+ final SWTNewtEventFactory swtNewtEventFactory = new SWTNewtEventFactory();
+ swtNewtEventFactory.attachDispatchListener(glc, glc, demo.gearsMouse, demo.gearsKeys);
+ glc.addGLEventListener( demo ) ;
+ glad = glc;
+ newtDisplay = null;
+ } else if( useNewtCanvasSWT ) {
+ final GLWindow glWindow = GLWindow.create( caps ) ;
+ glWindow.addGLEventListener( new GearsES2() ) ;
+ newtDisplay = glWindow.getScreen().getDisplay();
+ if( glWindowPreVisible ) {
+ newtDisplay.setEDTUtil(new SWTEDTUtil(newtDisplay, dsc.display)); // Especially Windows requires creation access via same thread!
+ glWindow.setVisible(true);
+ AWTRobotUtil.waitForRealized(glWindow, true);
+ Thread.sleep(120); // let it render a bit, before consumed by SWT
+ }
+ glad = glWindow;
+ NewtCanvasSWT.create( dsc.composite, 0, glWindow ) ;
+ } else {
+ throw new InternalError("XXX");
+ }
+ if(useAnimator) {
+ Animator animator = new Animator(glad);
+ animator.start();
+ }
+ }
+
+ System.err.println("**** Pre Shell Open");
+ dsc.display.syncExec( new Runnable() {
+ public void run() {
+ dsc.shell.setText( "NewtCanvasSWT Resize Bug Demo" ) ;
+ dsc.shell.setSize( 400, 450 ) ;
+ dsc.shell.open() ;
+ } } );
+ System.err.println("**** Post Shell Open");
+
+ shallStop = false;
+
+ final int[] counterBeforeExit = new int[] { 0 /* SWT */, 0 /* NEWT */ };
+
+ final AsyncExecEDTFeederThread asyncExecFeeder;
+ {
+ asyncExecFeeder = new AsyncExecEDTFeederThread(dsc.display, newtDisplay) ;
+ asyncExecFeeder.start() ;
+ }
+
+ {
+ final Thread t = new Thread(new Runnable() {
+ @Override
+ public void run() {
+ try {
+ Thread.sleep(duration);
+ } catch (InterruptedException e) {}
+
+ counterBeforeExit[0] = getSWTCount();
+ counterBeforeExit[1] = getNEWTCount();
+ asyncExecFeeder.shallStop = true;
+ try
+ {
+ asyncExecFeeder.join();
+ } catch( InterruptedException e ) { }
+ shallStop = true;
+ dsc.display.wake();
+ } } );
+ t.setDaemon(true);
+ t.start();
+ }
+
+ try {
+ final Display d = dsc.display;
+ while( !shallStop && !d.isDisposed() ) {
+ if( !d.readAndDispatch() && !shallStop ) {
+ // blocks on linux .. dsc.display.sleep();
+ Thread.sleep(10);
+ }
+ }
+ } catch (Exception e0) {
+ e0.printStackTrace();
+ Assert.assertTrue("Deadlock @ dispatch: "+e0, false);
+ }
+
+ // canvas is disposed implicit, due to it's disposed listener !
+
+ dsc.dispose();
+
+ System.err.println("EDT Counter before exit: SWT " + counterBeforeExit[0] + ", NEWT "+counterBeforeExit[1]);
+ Assert.assertTrue("SWT EDT Counter not greater zero before dispose!", 0 < counterBeforeExit[0]);
+ if( null != newtDisplay ) {
+ Assert.assertTrue("NEWT EDT Counter not greater zero before dispose!", 0 < counterBeforeExit[1]);
+ }
+ }
+
+ @Test
+ public void test01JOGLGLCanvas() throws InterruptedException, AWTException, InvocationTargetException {
+ testImpl(true /* useJOGLGLCanvas */, false /* useNewtCanvasSWT */, false /* glWindowPreVisible */);
+ }
+
+ @Test
+ public void test02NewtCanvasSWTSimple() throws InterruptedException, AWTException, InvocationTargetException {
+ testImpl(false /* useJOGLGLCanvas */, true /* useNewtCanvasSWT */, false /* glWindowPreVisible */);
+ }
+
+ @Test
+ public void test02NewtCanvasSWTPreVisible() throws InterruptedException, AWTException, InvocationTargetException {
+ testImpl(false /* useJOGLGLCanvas */, true /* useNewtCanvasSWT */, true /* glWindowPreVisible */);
+ }
+
+ public static void main( String[] args ) {
+ for(int i=0; i<args.length; i++) {
+ if(args[i].equals("-time")) {
+ duration = MiscUtils.atoi(args[++i], duration);
+ } else if(args[i].equals("-anim")) {
+ useAnimator = true;
+ }
+ }
+ System.out.println("durationPerTest: "+duration);
+ org.junit.runner.JUnitCore.main(TestSWTBug643AsyncExec.class.getName());
+ }
+
+}
diff --git a/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTJOGLGLCanvas01GLn.java b/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTJOGLGLCanvas01GLn.java
index 6d9e2219c..1822d2eaf 100644
--- a/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTJOGLGLCanvas01GLn.java
+++ b/src/test/com/jogamp/opengl/test/junit/jogl/swt/TestSWTJOGLGLCanvas01GLn.java
@@ -50,17 +50,18 @@ import org.junit.Test;
import com.jogamp.nativewindow.swt.SWTAccessor;
import com.jogamp.opengl.swt.GLCanvas;
import com.jogamp.opengl.test.junit.jogl.demos.es2.GearsES2;
+import com.jogamp.opengl.test.junit.jogl.demos.es2.MultisampleDemoES2;
import com.jogamp.opengl.test.junit.util.UITestCase;
+import com.jogamp.opengl.util.Animator;
import com.jogamp.opengl.util.GLReadBufferUtil;
import com.jogamp.opengl.util.texture.TextureIO;
/**
* Tests that a basic SWT app can open without crashing under different GL profiles.
* <p>
- * Uses JOGL's new SWT GLCanvas.
- * </p>
- * <p>
- * Note: To employ custom GLCapabilities, NewtCanvasSWT shall be used.
+ * Uses JOGL's new SWT GLCanvas,
+ * which allows utilizing custom GLCapability settings,
+ * independent from the already instantiated SWT visual.
* </p>
* <p>
* Note that {@link SWTAccessor#invoke(boolean, Runnable)} is still used to comply w/
@@ -71,7 +72,8 @@ import com.jogamp.opengl.util.texture.TextureIO;
public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
static int duration = 250;
-
+ static boolean doAnimation = true;
+
static final int iwidth = 640;
static final int iheight = 480;
@@ -90,10 +92,13 @@ public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
public void run() {
display = new Display();
Assert.assertNotNull( display );
+ }});
+ display.syncExec(new Runnable() {
+ public void run() {
shell = new Shell( display );
Assert.assertNotNull( shell );
shell.setLayout( new FillLayout() );
- composite = new Composite( shell, SWT.NONE );
+ composite = new Composite( shell, SWT.NO_BACKGROUND );
composite.setLayout( new FillLayout() );
Assert.assertNotNull( composite );
}});
@@ -105,10 +110,13 @@ public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
Assert.assertNotNull( shell );
Assert.assertNotNull( composite );
try {
- SWTAccessor.invoke(true, new Runnable() {
+ display.syncExec(new Runnable() {
public void run() {
composite.dispose();
shell.dispose();
+ }});
+ SWTAccessor.invoke(true, new Runnable() {
+ public void run() {
display.dispose();
}});
}
@@ -140,13 +148,19 @@ public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
public void dispose(final GLAutoDrawable drawable) { }
});
- SWTAccessor.invoke(true, new Runnable() {
+ display.syncExec(new Runnable() {
public void run() {
shell.setText( getSimpleTestName(".") );
shell.setSize( 640, 480 );
shell.open();
} } );
+ Animator anim = new Animator();
+ if(doAnimation) {
+ anim.add(canvas);
+ anim.start();
+ }
+
long lStartTime = System.currentTimeMillis();
long lEndTime = lStartTime + duration;
try {
@@ -160,7 +174,10 @@ public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
throwable.printStackTrace();
Assume.assumeNoException( throwable );
}
- SWTAccessor.invoke(true, new Runnable() {
+
+ anim.stop();
+
+ display.syncExec(new Runnable() {
public void run() {
canvas.dispose();
} } );
@@ -171,6 +188,14 @@ public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
runTestAGL( new GLCapabilities(GLProfile.getGL2ES2()), new GearsES2() );
}
+ @Test
+ public void test_MultisampleAndAlpha() throws InterruptedException {
+ GLCapabilities caps = new GLCapabilities(GLProfile.getGL2ES2());
+ caps.setSampleBuffers(true);
+ caps.setNumSamples(2);
+ runTestAGL( caps, new MultisampleDemoES2(true) );
+ }
+
static int atoi(String a) {
int i=0;
try {
@@ -183,6 +208,8 @@ public class TestSWTJOGLGLCanvas01GLn extends UITestCase {
for(int i=0; i<args.length; i++) {
if(args[i].equals("-time")) {
duration = atoi(args[++i]);
+ } else if(args[i].equals("-still")) {
+ doAnimation = false;
}
}
System.out.println("durationPerTest: "+duration);
diff --git a/src/test/com/jogamp/opengl/test/junit/newt/TestDisplayLifecycle01NEWT.java b/src/test/com/jogamp/opengl/test/junit/newt/TestDisplayLifecycle01NEWT.java
index c9450c2d6..e4867e3fe 100644
--- a/src/test/com/jogamp/opengl/test/junit/newt/TestDisplayLifecycle01NEWT.java
+++ b/src/test/com/jogamp/opengl/test/junit/newt/TestDisplayLifecycle01NEWT.java
@@ -89,7 +89,7 @@ public class TestDisplayLifecycle01NEWT extends UITestCase {
Assert.assertEquals(0,display.getReferenceCount());
Assert.assertEquals(false,display.isNativeValid());
Assert.assertNotNull(display.getEDTUtil());
- Assert.assertEquals(false,display.getEDTUtil().isRunning());
+ Assert.assertEquals(true,display.getEDTUtil().isRunning());
Assert.assertEquals(0,screen.getReferenceCount());
Assert.assertEquals(false,screen.isNativeValid());
@@ -201,6 +201,8 @@ public class TestDisplayLifecycle01NEWT extends UITestCase {
Assert.assertEquals(false,display.isNativeValid());
Assert.assertNotNull(display.getEDTUtil());
Assert.assertEquals(false,display.getEDTUtil().isRunning());
+ display.getEDTUtil().invoke(true, null);
+ Assert.assertEquals(true,display.getEDTUtil().isRunning());
Assert.assertEquals(0,screen.getReferenceCount());
Assert.assertEquals(false,screen.isNativeValid());