diff options
Diffstat (limited to 'src/newt')
9 files changed, 135 insertions, 47 deletions
diff --git a/src/newt/classes/com/jogamp/newt/Display.java b/src/newt/classes/com/jogamp/newt/Display.java index 993aa33eb..d6ddd9613 100644 --- a/src/newt/classes/com/jogamp/newt/Display.java +++ b/src/newt/classes/com/jogamp/newt/Display.java @@ -178,7 +178,7 @@ public abstract class Display { public abstract void dispatchMessages(); // Global Displays - protected static ArrayList<Display> displayList = new ArrayList<Display>(); + protected static final ArrayList<Display> displayList = new ArrayList<Display>(); protected static int displaysActive = 0; public static void dumpDisplayList(String prefix) { diff --git a/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java b/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java index 65b44b141..dd8939e43 100644 --- a/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java +++ b/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java @@ -31,6 +31,7 @@ package com.jogamp.newt.awt; import java.awt.AWTKeyStroke; import java.awt.Canvas; +import java.awt.Component; import java.awt.Graphics; import java.awt.GraphicsConfiguration; import java.awt.KeyboardFocusManager; @@ -222,18 +223,20 @@ public class NewtCanvasAWT extends java.awt.Canvas implements WindowClosingProto final Set<AWTKeyStroke> fwdKeys = keyboardFocusManager.getDefaultFocusTraversalKeys(KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS); final Set<AWTKeyStroke> bwdKeys = keyboardFocusManager.getDefaultFocusTraversalKeys(KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS); if(fwdKeys.contains(ks)) { + final Component nextFocus = AWTMisc.getNextFocus(NewtCanvasAWT.this); if(DEBUG) { - System.err.println("NewtCanvasAWT.focusKey (fwd): "+ks+", current focusOwner "+keyboardFocusManager.getFocusOwner()); + System.err.println("NewtCanvasAWT.focusKey (fwd): "+ks+", current focusOwner "+keyboardFocusManager.getFocusOwner()+", hasFocus: "+hasFocus()+", nextFocus "+nextFocus); } // Newt-EDT -> AWT-EDT may freeze Window's native peer requestFocus. - NewtCanvasAWT.this.transferFocus(); + nextFocus.requestFocus(); suppress = true; } else if(bwdKeys.contains(ks)) { + final Component prevFocus = AWTMisc.getPrevFocus(NewtCanvasAWT.this); if(DEBUG) { - System.err.println("NewtCanvasAWT.focusKey (bwd): "+ks+", current focusOwner "+keyboardFocusManager.getFocusOwner()); + System.err.println("NewtCanvasAWT.focusKey (bwd): "+ks+", current focusOwner "+keyboardFocusManager.getFocusOwner()+", hasFocus: "+hasFocus()+", prevFocus "+prevFocus); } // Newt-EDT -> AWT-EDT may freeze Window's native peer requestFocus. - NewtCanvasAWT.this.transferFocusBackward(); + prevFocus.requestFocus(); suppress = true; } } diff --git a/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java b/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java index 1500d48e6..345d92bc1 100644 --- a/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java +++ b/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java @@ -79,11 +79,16 @@ import com.jogamp.newt.event.WindowEvent; import com.jogamp.newt.event.WindowListener; import com.jogamp.newt.event.WindowUpdateEvent; import com.jogamp.opengl.JoglVersion; +import com.jogamp.opengl.GLStateKeeper; /** * An implementation of {@link GLAutoDrawable} and {@link Window} interface, * using a delegated {@link Window} instance, which may be an aggregation (lifecycle: created and destroyed). * <P> + * This implementation supports {@link GLStateKeeper GL state preservation}, + * hence {@link #isGLStatePreservationSupported()} returns <code>true</code>. + * </P> + * <P> * This implementation does not make the OpenGL context current<br> * before calling the various input EventListener callbacks, ie {@link com.jogamp.newt.event.MouseListener} etc.<br> * This design decision is made in favor of a more performant and simplified @@ -433,8 +438,8 @@ public class GLWindow extends GLAutoDrawableBase implements GLAutoDrawable, Wind protected class GLLifecycleHook implements WindowImpl.LifecycleHook { @Override - public void preserveGLStateAtDestroy() { - GLWindow.this.preserveGLStateAtDestroy(true); + public void preserveGLStateAtDestroy(boolean value) { + GLWindow.this.preserveGLStateAtDestroy(value); } @Override @@ -579,6 +584,12 @@ public class GLWindow extends GLAutoDrawableBase implements GLAutoDrawable, Wind } } + /** + * {@inheritDoc} + * <p> + * GLWindow supports GL state preservation, hence returns <code>true</code>. + * </p> + */ @Override public final boolean isGLStatePreservationSupported() { return true; } diff --git a/src/newt/classes/jogamp/newt/DisplayImpl.java b/src/newt/classes/jogamp/newt/DisplayImpl.java index d4842ba2f..3edb532db 100644 --- a/src/newt/classes/jogamp/newt/DisplayImpl.java +++ b/src/newt/classes/jogamp/newt/DisplayImpl.java @@ -45,10 +45,24 @@ import java.util.ArrayList; import javax.media.nativewindow.AbstractGraphicsDevice; import javax.media.nativewindow.NativeWindowException; +import javax.media.nativewindow.NativeWindowFactory; public abstract class DisplayImpl extends Display { private static int serialno = 1; + static { + NativeWindowFactory.addCustomShutdownHook(true /* head */, new Runnable() { + public void run() { + WindowImpl.shutdownAll(); + ScreenImpl.shutdownAll(); + DisplayImpl.shutdownAll(); + } + }); + } + + /** Ensure static init has been run. */ + /* pp */static void initSingleton() { } + private static Class<?> getDisplayClass(String type) throws ClassNotFoundException { @@ -232,11 +246,10 @@ public abstract class DisplayImpl extends Display { if(DEBUG) { System.err.println("Display.destroy(): "+this+" "+getThreadName()); } - final AbstractGraphicsDevice f_aDevice = aDevice; final DisplayImpl f_dpy = this; - removeEDT( new Runnable() { + removeEDT( new Runnable() { // blocks! public void run() { - if ( null != f_aDevice ) { + if ( null != aDevice ) { f_dpy.closeNativeImpl(); } } @@ -247,6 +260,32 @@ public abstract class DisplayImpl extends Display { dumpDisplayList("Display.destroy("+getFQName()+") END"); } } + + /** Maybe utilized at a shutdown hook, impl. does not synchronize, however the EDT removal blocks. */ + /* pp */ static final void shutdownAll() { + final int dCount = displayList.size(); + if(DEBUG) { + dumpDisplayList("Display.shutdownAll "+dCount+" instances, on thread "+getThreadName()); + } + for(int i=0; i<dCount && displayList.size()>0; i++) { // be safe .. + final DisplayImpl d = (DisplayImpl) displayList.remove(0); + if(0 < displaysActive) { + displaysActive--; + } + if(DEBUG) { + System.err.println("Display.shutdownAll["+(i+1)+"/"+dCount+"]: "+d); + } + d.removeEDT( new Runnable() { + public void run() { + if ( null != d.getGraphicsDevice() ) { + d.closeNativeImpl(); + } + } + } ); + d.aDevice = null; + d.refCount=0; + } + } public synchronized final int addReference() { if(DEBUG) { diff --git a/src/newt/classes/jogamp/newt/ScreenImpl.java b/src/newt/classes/jogamp/newt/ScreenImpl.java index 7edf7b63a..f63d1499e 100644 --- a/src/newt/classes/jogamp/newt/ScreenImpl.java +++ b/src/newt/classes/jogamp/newt/ScreenImpl.java @@ -34,8 +34,6 @@ package jogamp.newt; -import java.security.AccessController; -import java.security.PrivilegedAction; import java.util.ArrayList; import java.util.Iterator; import java.util.List; @@ -64,6 +62,13 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener { public static final int default_sm_rate = 60; public static final int default_sm_rotation = 0; + static { + DisplayImpl.initSingleton(); + } + + /** Ensure static init has been run. */ + /* pp */static void initSingleton() { } + protected DisplayImpl display; protected int screen_idx; protected String fqname; @@ -77,15 +82,6 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener { private long tCreated; // creationTime - static { - AccessController.doPrivileged(new PrivilegedAction<Object>() { - public Object run() { - registerShutdownHook(); - return null; - } - }); - } - private static Class<?> getScreenClass(String type) throws ClassNotFoundException { final Class<?> screenClass = NewtFactory.getCustomClass(type, "ScreenDriver"); @@ -660,23 +656,18 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener { ScreenMonitorState.unmapScreenMonitorStateUnlocked(getFQName()); } } - private static final void shutdownAll() { - for(int i=0; i < screenList.size(); i++) { - ((ScreenImpl)screenList.get(i)).shutdown(); - } - } - private static synchronized void registerShutdownHook() { - final Thread shutdownHook = new Thread(new Runnable() { - public void run() { - ScreenImpl.shutdownAll(); - } - }); - AccessController.doPrivileged(new PrivilegedAction<Object>() { - public Object run() { - Runtime.getRuntime().addShutdownHook(shutdownHook); - return null; + /** pp */ static final void shutdownAll() { + final int sCount = screenList.size(); + if(DEBUG) { + System.err.println("Screen.shutdownAll "+sCount+" instances, on thread "+Display.getThreadName()); + } + for(int i=0; i<sCount && screenList.size()>0; i++) { // be safe .. + final ScreenImpl s = (ScreenImpl) screenList.remove(0); + if(DEBUG) { + System.err.println("Screen.shutdownAll["+(i+1)+"/"+sCount+"]: "+s); } - }); + s.shutdown(); + } } } diff --git a/src/newt/classes/jogamp/newt/WindowImpl.java b/src/newt/classes/jogamp/newt/WindowImpl.java index dca287c6b..1ac97b07c 100644 --- a/src/newt/classes/jogamp/newt/WindowImpl.java +++ b/src/newt/classes/jogamp/newt/WindowImpl.java @@ -82,6 +82,27 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer { public static final boolean DEBUG_TEST_REPARENT_INCOMPATIBLE = Debug.isPropertyDefined("newt.test.Window.reparent.incompatible", true); + protected static final ArrayList<WindowImpl> windowList = new ArrayList<WindowImpl>(); + + static { + ScreenImpl.initSingleton(); + } + + /** Maybe utilized at a shutdown hook, impl. does not synchronize, however the Window destruction and EDT removal blocks. */ + public static final void shutdownAll() { + final int wCount = windowList.size(); + if(DEBUG_IMPLEMENTATION) { + System.err.println("Window.shutdownAll "+wCount+" instances, on thread "+getThreadName()); + } + for(int i=0; i<wCount && windowList.size()>0; i++) { // be safe .. + final WindowImpl w = windowList.remove(0); + if(DEBUG_IMPLEMENTATION) { + System.err.println("Window.shutdownAll["+(i+1)+"/"+wCount+"]: "+toHexString(w.getWindowHandle())); + } + w.markInvalid(); + } + } + /** Timeout of queued events (repaint and resize) */ static final long QUEUED_EVENT_TO = 1200; // ms @@ -186,6 +207,9 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer window.screen = (ScreenImpl) screen; window.capsRequested = (CapabilitiesImmutable) caps.cloneMutable(); window.instantiationFinished(); + synchronized( windowList ) { + windowList.add(window); + } return window; } catch (Throwable t) { t.printStackTrace(); @@ -207,12 +231,27 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer WindowImpl window = (WindowImpl) ReflectionUtil.createInstance( windowClass, cstrArgumentTypes, cstrArguments ) ; window.screen = (ScreenImpl) screen; window.capsRequested = (CapabilitiesImmutable) caps.cloneMutable(); + window.instantiationFinished(); + synchronized( windowList ) { + windowList.add(window); + } return window; } catch (Throwable t) { throw new NativeWindowException(t); } } + /** Fast invalidation of instance w/o any blocking function call. */ + private final void markInvalid() { + setWindowHandle(0); + visible = false; + fullscreen = false; + fullscreenMonitors = null; + fullscreenUseMainMonitor = true; + hasFocus = false; + parentWindowHandle = 0; + } + protected final void setGraphicsConfiguration(AbstractGraphicsConfiguration cfg) { config = cfg; } @@ -233,9 +272,10 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer /** * Notifies the receiver to preserve resources (GL, ..) - * for the next destroy*() calls (only). + * for the next destroy*() calls (only), if supported and if <code>value</code> is <code>true</code>, otherwise clears preservation flag. + * @param value <code>true</code> to set the one-shot preservation if supported, otherwise clears it. */ - void preserveGLStateAtDestroy(); + void preserveGLStateAtDestroy(boolean value); /** * Invoked before Window destroy action, @@ -995,13 +1035,16 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer @Override public void destroy() { + synchronized( windowList ) { + windowList.remove(this); + } visible = false; // Immediately mark synchronized visibility flag, avoiding possible recreation runOnEDTIfAvail(true, destroyAction); } protected void destroy(boolean preserveResources) { - if( preserveResources && null != WindowImpl.this.lifecycleHook ) { - WindowImpl.this.lifecycleHook.preserveGLStateAtDestroy(); + if( null != lifecycleHook ) { + lifecycleHook.preserveGLStateAtDestroy( preserveResources ); } destroy(); } @@ -1108,7 +1151,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer } // Destroy this window and use parent's Screen. // It may be created properly when the parent is made visible. - destroy(false); + destroy( false ); setScreen( (ScreenImpl) newParentWindowNEWT.getScreen() ); operation = ReparentOperation.ACTION_NATIVE_CREATION_PENDING; } else if(newParentWindow != getParent()) { diff --git a/src/newt/classes/jogamp/newt/driver/x11/DisplayDriver.java b/src/newt/classes/jogamp/newt/driver/x11/DisplayDriver.java index 4fe025ec4..88d06f69c 100644 --- a/src/newt/classes/jogamp/newt/driver/x11/DisplayDriver.java +++ b/src/newt/classes/jogamp/newt/driver/x11/DisplayDriver.java @@ -57,10 +57,8 @@ public class DisplayDriver extends DisplayImpl { } } - public static void initSingleton() { - // just exist to ensure static init has been run - } - + /** Ensure static init has been run. */ + /* pp */static void initSingleton() { } public DisplayDriver() { } diff --git a/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java index b8b13939b..e1373bba5 100644 --- a/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java +++ b/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java @@ -60,6 +60,9 @@ public class ScreenDriver extends ScreenImpl { DisplayDriver.initSingleton(); } + /** Ensure static init has been run. */ + /* pp */static void initSingleton() { } + public ScreenDriver() { } diff --git a/src/newt/classes/jogamp/newt/driver/x11/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/x11/WindowDriver.java index c752977a9..786587d65 100644 --- a/src/newt/classes/jogamp/newt/driver/x11/WindowDriver.java +++ b/src/newt/classes/jogamp/newt/driver/x11/WindowDriver.java @@ -59,7 +59,7 @@ public class WindowDriver extends WindowImpl { private static final int X11_WHEEL_TWO_DOWN_BUTTON = 7; static { - DisplayDriver.initSingleton(); + ScreenDriver.initSingleton(); } public WindowDriver() { |