From 472a9c60b5599bb01883c628339ab29628511ed5 Mon Sep 17 00:00:00 2001 From: Sven Gothel Date: Tue, 27 Sep 2011 12:20:38 +0200 Subject: NEWT: Adapt to GlueGen's Lock ChangeSet, all java callbacks for native have 'defer' 1st argument - Adapt to GlueGen's Lock ChangeSet: e4baba27507ce78e64a150ec6f69fb96f5721a34 - All java callbacks for native have 'defer' 1st argument. This allows enqueuing resulting events to the EDT if required, ie. the native thread may not be 'compatible' (MacOSX). - MacOSX-Native: enqueue key/mouse events and defer:=true for all java callbacks Since we are comming from a 3rd-party thread (AWT/NSApp-MainThread) we shall not abuse it. --- src/newt/classes/jogamp/newt/OffscreenWindow.java | 6 +- src/newt/classes/jogamp/newt/ScreenModeStatus.java | 5 +- src/newt/classes/jogamp/newt/WindowImpl.java | 90 +++++++++++++--------- .../jogamp/newt/driver/android/AndroidWindow.java | 6 +- .../classes/jogamp/newt/driver/awt/AWTWindow.java | 2 +- .../jogamp/newt/driver/broadcom/egl/Window.java | 2 +- .../jogamp/newt/driver/intel/gdl/Window.java | 2 +- .../classes/jogamp/newt/driver/kd/KDWindow.java | 8 +- .../jogamp/newt/driver/windows/WindowsWindow.java | 2 +- 9 files changed, 69 insertions(+), 54 deletions(-) (limited to 'src/newt/classes') diff --git a/src/newt/classes/jogamp/newt/OffscreenWindow.java b/src/newt/classes/jogamp/newt/OffscreenWindow.java index 7afc54d71..fa7bafe5b 100644 --- a/src/newt/classes/jogamp/newt/OffscreenWindow.java +++ b/src/newt/classes/jogamp/newt/OffscreenWindow.java @@ -91,7 +91,7 @@ public class OffscreenWindow extends WindowImpl implements SurfaceChangeable { @Override public void setSize(int width, int height) { if(!isVisible()) { - sizeChanged(width, height, false); + sizeChanged(false, width, height, false); } } @Override @@ -106,8 +106,8 @@ public class OffscreenWindow extends WindowImpl implements SurfaceChangeable { protected boolean reconfigureWindowImpl(int x, int y, int width, int height, int flags) { if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) ) { - sizeChanged(width, height, false); - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + sizeChanged(false, width, height, false); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } else { shouldNotCallThis(); } diff --git a/src/newt/classes/jogamp/newt/ScreenModeStatus.java b/src/newt/classes/jogamp/newt/ScreenModeStatus.java index dfd4e99a6..be87ce0dd 100644 --- a/src/newt/classes/jogamp/newt/ScreenModeStatus.java +++ b/src/newt/classes/jogamp/newt/ScreenModeStatus.java @@ -30,6 +30,7 @@ package jogamp.newt; import com.jogamp.common.util.ArrayHashSet; import com.jogamp.common.util.IntIntHashMap; +import com.jogamp.common.util.locks.LockFactory; import com.jogamp.common.util.locks.RecursiveLock; import com.jogamp.newt.Screen; import com.jogamp.newt.ScreenMode; @@ -41,7 +42,7 @@ import java.util.HashMap; public class ScreenModeStatus { private static boolean DEBUG = Screen.DEBUG; - private RecursiveLock lock = new RecursiveLock(); + private RecursiveLock lock = LockFactory.createRecursiveLock(); private ArrayHashSet screenModes; private IntIntHashMap screenModesIdx2NativeIdx; private ScreenMode currentScreenMode; @@ -49,7 +50,7 @@ public class ScreenModeStatus { private ArrayList listener = new ArrayList(); private static HashMap screenFQN2ScreenModeStatus = new HashMap(); - private static RecursiveLock screen2ScreenModeStatusLock = new RecursiveLock(); + private static RecursiveLock screen2ScreenModeStatusLock = LockFactory.createRecursiveLock(); protected static void mapScreenModeStatus(String screenFQN, ScreenModeStatus sms) { screen2ScreenModeStatusLock.lock(); diff --git a/src/newt/classes/jogamp/newt/WindowImpl.java b/src/newt/classes/jogamp/newt/WindowImpl.java index 77e69fef7..90b5a8226 100644 --- a/src/newt/classes/jogamp/newt/WindowImpl.java +++ b/src/newt/classes/jogamp/newt/WindowImpl.java @@ -42,6 +42,7 @@ import com.jogamp.newt.NewtFactory; import com.jogamp.newt.Display; import com.jogamp.newt.Screen; import com.jogamp.newt.Window; +import com.jogamp.common.util.locks.LockFactory; import com.jogamp.common.util.locks.RecursiveLock; import com.jogamp.newt.ScreenMode; import com.jogamp.newt.event.KeyEvent; @@ -76,8 +77,8 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer private volatile long windowHandle = 0; // lifecycle critical private volatile boolean visible = false; // lifecycle critical - private RecursiveLock windowLock = new RecursiveLock(); // Window instance wide lock - private RecursiveLock surfaceLock = new RecursiveLock(); // Surface only lock + private RecursiveLock windowLock = LockFactory.createRecursiveLock(); // Window instance wide lock + private RecursiveLock surfaceLock = LockFactory.createRecursiveLock(); // Surface only lock private ScreenImpl screen; // never null after create - may change reference though (reparent) private boolean screenReferenceAdded = false; @@ -395,10 +396,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer * to notify this Java object of state changes.

* * @see #windowDestroyNotify() - * @see #focusChanged(boolean) - * @see #visibleChanged(boolean) + * @see #focusChanged(boolean, boolean) + * @see #visibleChanged(boolean, boolean) * @see #sizeChanged(int,int) - * @see #positionChanged(int,int) + * @see #positionChanged(boolean,int, int) * @see #windowDestroyNotify() */ protected abstract void createNativeImpl(); @@ -406,11 +407,11 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer protected abstract void closeNativeImpl(); /** - * The native implementation must invoke {@link #focusChanged(boolean)} + * The native implementation must invoke {@link #focusChanged(boolean, boolean)} * to change the focus state, if force == false. * This may happen asynchronous within {@link #TIMEOUT_NATIVEWINDOW}. * - * @param force if true, bypass {@link #focusChanged(boolean)} and force focus request + * @param force if true, bypass {@link #focusChanged(boolean, boolean)} and force focus request */ protected abstract void requestFocusImpl(boolean force); @@ -442,7 +443,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer * @param flags bitfield of change and status flags * * @see #sizeChanged(int,int) - * @see #positionChanged(int,int) + * @see #positionChanged(boolean,int, int) */ protected abstract boolean reconfigureWindowImpl(int x, int y, int width, int height, int flags); @@ -508,10 +509,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer /** Triggered by user via {@link #getInsets()}.
* Implementations may implement this hook to update the insets.
- * However, they may prefer the event driven path via {@link #insetsChanged(int, int, int, int)}. + * However, they may prefer the event driven path via {@link #insetsChanged(boolean, int, int, int, int)}. * * @see #getInsets() - * @see #insetsChanged(int, int, int, int) + * @see #insetsChanged(boolean, int, int, int, int) */ protected abstract void updateInsetsImpl(Insets insets); @@ -522,7 +523,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer public final int lockSurface() { windowLock.lock(); surfaceLock.lock(); - int res = surfaceLock.getRecursionCount() == 0 ? LOCK_SURFACE_NOT_READY : LOCK_SUCCESS; + int res = surfaceLock.getHoldCount() == 1 ? LOCK_SURFACE_NOT_READY : LOCK_SUCCESS; // new lock ? if ( LOCK_SURFACE_NOT_READY == res ) { try { @@ -551,7 +552,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer surfaceLock.validateLocked(); windowLock.validateLocked(); - if (surfaceLock.getRecursionCount() == 0) { + if (surfaceLock.getHoldCount() == 1) { final AbstractGraphicsDevice adevice = config.getScreen().getDevice(); try { unlockSurfaceImpl(); @@ -741,8 +742,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer } if(DEBUG_IMPLEMENTATION) { - String msg = "Window setVisible: START ("+getThreadName()+") "+x+"/"+y+" "+width+"x"+height+", fs "+fullscreen+", windowHandle "+toHexString(windowHandle)+", visible: "+this.visible+" -> "+visible+", parentWindowHandle "+toHexString(parentWindowHandle)+", parentWindow "+(null!=parentWindow); - System.err.println(msg); + System.err.println("Window setVisible: START ("+getThreadName()+") "+x+"/"+y+" "+width+"x"+height+", fs "+fullscreen+", windowHandle "+toHexString(windowHandle)+", visible: "+this.visible+" -> "+visible+", parentWindowHandle "+toHexString(parentWindowHandle)+", parentWindow "+(null!=parentWindow)); Thread.dumpStack(); } runOnEDTIfAvail(true, new VisibleAction(visible)); @@ -1727,8 +1727,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer repaintQueued=true; if(DEBUG_IMPLEMENTATION) { System.err.println("Window.consumeEvent: queued "+e); - // Exception ee = new Exception("Window.windowRepaint: "+e); - // ee.printStackTrace(); + // Thread.dumpStack(); } return false; } @@ -1742,9 +1741,8 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer // queue event in case window is locked, ie in operation if( isWindowLocked() ) { if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.consumeEvent: queued "+e); - // Exception ee = new Exception("Window.windowRepaint: "+e); - // ee.printStackTrace(); + // System.err.println("Window.consumeEvent: queued "+e); + // Thread.dumpStack(); // JAU } return false; } @@ -2137,23 +2135,24 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer } } - /** Triggered by implementation's WM events to update the focus state. */ - protected void focusChanged(boolean focusGained) { + /** Triggered by implementation's WM events to update the focus state. */ + protected void focusChanged(boolean defer, boolean focusGained) { if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.focusChanged: ("+getThreadName()+"): "+this.hasFocus+" -> "+focusGained+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); + System.err.println("Window.focusChanged: ("+getThreadName()+"): (defer: "+defer+") "+this.hasFocus+" -> "+focusGained+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); } hasFocus = focusGained; - if (focusGained) { - sendWindowEvent(WindowEvent.EVENT_WINDOW_GAINED_FOCUS); + final int evt = focusGained ? WindowEvent.EVENT_WINDOW_GAINED_FOCUS : WindowEvent.EVENT_WINDOW_LOST_FOCUS ; + if(!defer) { + sendWindowEvent(evt); } else { - sendWindowEvent(WindowEvent.EVENT_WINDOW_LOST_FOCUS); + enqueueWindowEvent(false, evt); } } - /** Triggered by implementation's WM events to update the visibility state. */ - protected void visibleChanged(boolean visible) { + /** Triggered by implementation's WM events to update the visibility state. */ + protected void visibleChanged(boolean defer, boolean visible) { if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.visibleChanged ("+getThreadName()+"): "+this.visible+" -> "+visible+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); + System.err.println("Window.visibleChanged ("+getThreadName()+"): (defer: "+defer+") "+this.visible+" -> "+visible+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); } this.visible = visible ; } @@ -2180,10 +2179,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer } /** Triggered by implementation's WM events to update the client-area size w/o insets/decorations. */ - protected void sizeChanged(int newWidth, int newHeight, boolean force) { + protected void sizeChanged(boolean defer, int newWidth, int newHeight, boolean force) { if(force || width != newWidth || height != newHeight) { if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.sizeChanged: ("+getThreadName()+"): force "+force+", "+width+"x"+height+" -> "+newWidth+"x"+newHeight+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); + System.err.println("Window.sizeChanged: ("+getThreadName()+"): (defer: "+defer+") force "+force+", "+width+"x"+height+" -> "+newWidth+"x"+newHeight+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); } if(0>newWidth || 0>newHeight) { throw new NativeWindowException("Illegal width or height "+newWidth+"x"+newHeight+" (must be >= 0)"); @@ -2191,7 +2190,11 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer width = newWidth; height = newHeight; if(isNativeValid()) { - sendWindowEvent(WindowEvent.EVENT_WINDOW_RESIZED); + if(!defer) { + sendWindowEvent(WindowEvent.EVENT_WINDOW_RESIZED); + } else { + enqueueWindowEvent(false, WindowEvent.EVENT_WINDOW_RESIZED); + } } } } @@ -2221,14 +2224,18 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer } /** Triggered by implementation's WM events to update the position. */ - protected void positionChanged(int newX, int newY) { + protected void positionChanged(boolean defer, int newX, int newY) { if ( x != newX || y != newY ) { if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.positionChanged: ("+getThreadName()+"): "+x+"/"+y+" -> "+newX+"/"+newY+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); + System.err.println("Window.positionChanged: ("+getThreadName()+"): (defer: "+defer+") "+x+"/"+y+" -> "+newX+"/"+newY+" - windowHandle "+toHexString(windowHandle)+" parentWindowHandle "+toHexString(parentWindowHandle)); } x = newX; y = newY; - sendWindowEvent(WindowEvent.EVENT_WINDOW_MOVED); + if(!defer) { + sendWindowEvent(WindowEvent.EVENT_WINDOW_MOVED); + } else { + enqueueWindowEvent(false, WindowEvent.EVENT_WINDOW_MOVED); + } } } @@ -2238,7 +2245,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer * @see #getInsets() * @see #updateInsetsImpl(Insets) */ - protected void insetsChanged(int left, int right, int top, int bottom) { + protected void insetsChanged(boolean defer, int left, int right, int top, int bottom) { if ( left >= 0 && right >= 0 && top >= 0 && bottom >= 0 ) { if(isUndecorated()) { if(DEBUG_IMPLEMENTATION) { @@ -2252,7 +2259,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer insets.setTopHeight(top); insets.setBottomHeight(bottom); if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.insetsChanged: "+insets); + System.err.println("Window.insetsChanged: (defer: "+defer+") "+insets); } } } @@ -2276,18 +2283,25 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer } public void windowRepaint(int x, int y, int width, int height) { + windowRepaint(false, x, y, width, height); + } + + /** + * Triggered by implementation's WM events to update the content + */ + protected void windowRepaint(boolean defer, int x, int y, int width, int height) { x = ( 0 > x ) ? this.x : x; y = ( 0 > y ) ? this.y : y; width = ( 0 >= width ) ? this.width : width; height = ( 0 >= height ) ? this.height : height; if(DEBUG_IMPLEMENTATION) { - System.err.println("Window.windowRepaint "+getThreadName()+" - "+x+"/"+y+" "+width+"x"+height); + System.err.println("Window.windowRepaint "+getThreadName()+" (defer: "+defer+") "+x+"/"+y+" "+width+"x"+height); } if(isNativeValid()) { NEWTEvent e = new WindowUpdateEvent(WindowEvent.EVENT_WINDOW_REPAINT, this, System.currentTimeMillis(), new Rectangle(x, y, width, height)); - doEvent(false, false, e); + doEvent(defer, false, e); } } diff --git a/src/newt/classes/jogamp/newt/driver/android/AndroidWindow.java b/src/newt/classes/jogamp/newt/driver/android/AndroidWindow.java index 83f306b46..5ce40a05e 100644 --- a/src/newt/classes/jogamp/newt/driver/android/AndroidWindow.java +++ b/src/newt/classes/jogamp/newt/driver/android/AndroidWindow.java @@ -172,7 +172,7 @@ public class AndroidWindow extends jogamp.newt.WindowImpl implements Callback2 { return false; } if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) ) { - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } return true; } @@ -219,7 +219,7 @@ public class AndroidWindow extends jogamp.newt.WindowImpl implements Callback2 { Log.d(MD.TAG, "surfaceCreated - 0 - isValid: "+surface.isValid()+ ", surfaceHandle 0x"+Long.toHexString(surfaceHandle)+ ", "+nsv.getWidth()+"x"+nsv.getHeight()); - sizeChanged(width, height, false); + sizeChanged(false, width, height, false); windowRepaint(0, 0, nsv.getWidth(), nsv.getHeight()); } @@ -227,7 +227,7 @@ public class AndroidWindow extends jogamp.newt.WindowImpl implements Callback2 { int height) { Log.d(MD.TAG, "surfaceChanged: f "+Integer.toString(format)+", "+width+"x"+height); getScreen().getCurrentScreenMode(); // if ScreenMode changed .. trigger ScreenMode event - sizeChanged(width, height, false); + sizeChanged(false, width, height, false); } public void surfaceDestroyed(SurfaceHolder holder) { diff --git a/src/newt/classes/jogamp/newt/driver/awt/AWTWindow.java b/src/newt/classes/jogamp/newt/driver/awt/AWTWindow.java index d71015d6c..9aaa82fec 100644 --- a/src/newt/classes/jogamp/newt/driver/awt/AWTWindow.java +++ b/src/newt/classes/jogamp/newt/driver/awt/AWTWindow.java @@ -209,7 +209,7 @@ public class AWTWindow extends WindowImpl { } } } - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } return true; diff --git a/src/newt/classes/jogamp/newt/driver/broadcom/egl/Window.java b/src/newt/classes/jogamp/newt/driver/broadcom/egl/Window.java index 431ac934b..7df293c0d 100644 --- a/src/newt/classes/jogamp/newt/driver/broadcom/egl/Window.java +++ b/src/newt/classes/jogamp/newt/driver/broadcom/egl/Window.java @@ -108,7 +108,7 @@ public class Window extends jogamp.newt.WindowImpl { } if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) ) { - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } return true; } diff --git a/src/newt/classes/jogamp/newt/driver/intel/gdl/Window.java b/src/newt/classes/jogamp/newt/driver/intel/gdl/Window.java index 05833e93b..ab3e95e7e 100644 --- a/src/newt/classes/jogamp/newt/driver/intel/gdl/Window.java +++ b/src/newt/classes/jogamp/newt/driver/intel/gdl/Window.java @@ -109,7 +109,7 @@ public class Window extends jogamp.newt.WindowImpl { if(0 != ( FLAG_IS_VISIBLE & flags)) { ((Display)getScreen().getDisplay()).setFocus(this); } - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } return true; diff --git a/src/newt/classes/jogamp/newt/driver/kd/KDWindow.java b/src/newt/classes/jogamp/newt/driver/kd/KDWindow.java index d94538545..10a75a017 100644 --- a/src/newt/classes/jogamp/newt/driver/kd/KDWindow.java +++ b/src/newt/classes/jogamp/newt/driver/kd/KDWindow.java @@ -88,7 +88,7 @@ public class KDWindow extends WindowImpl { protected boolean reconfigureWindowImpl(int x, int y, int width, int height, int flags) { if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) ) { setVisible0(eglWindowHandle, 0 != ( FLAG_IS_VISIBLE & flags)); - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } if(0!=eglWindowHandle) { @@ -112,7 +112,7 @@ public class KDWindow extends WindowImpl { } if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) ) { - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } return true; @@ -143,11 +143,11 @@ public class KDWindow extends WindowImpl { } @Override - protected void sizeChanged(int newWidth, int newHeight, boolean force) { + protected void sizeChanged(boolean defer, int newWidth, int newHeight, boolean force) { if(fullscreen) { ((KDScreen)getScreen()).setScreenSize(width, height); } - super.sizeChanged(newWidth, newHeight, force); + super.sizeChanged(defer, newWidth, newHeight, force); } private long eglWindowHandle; diff --git a/src/newt/classes/jogamp/newt/driver/windows/WindowsWindow.java b/src/newt/classes/jogamp/newt/driver/windows/WindowsWindow.java index 9c80f0f85..ee057fb8f 100644 --- a/src/newt/classes/jogamp/newt/driver/windows/WindowsWindow.java +++ b/src/newt/classes/jogamp/newt/driver/windows/WindowsWindow.java @@ -174,7 +174,7 @@ public class WindowsWindow extends WindowImpl { reconfigureWindow0( getParentWindowHandle(), getWindowHandle(), x, y, width, height, flags); if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) ) { - visibleChanged(0 != ( FLAG_IS_VISIBLE & flags)); + visibleChanged(false, 0 != ( FLAG_IS_VISIBLE & flags)); } return true; } -- cgit v1.2.3