summaryrefslogtreecommitdiffstats
path: root/src/newt/classes/com/jogamp
diff options
context:
space:
mode:
authorSven Gothel <[email protected]>2010-09-10 05:33:17 +0200
committerSven Gothel <[email protected]>2010-09-10 05:33:17 +0200
commit63be4a40aa6ecfe9fbc6585acccbc6f6f6689377 (patch)
tree41bcd52797e1602ffa409079b7d1744a399f77b8 /src/newt/classes/com/jogamp
parent340b1ceb07907be113e33c54d084e53ddc93e368 (diff)
NEWT: Changed Lifecycle of Display/Screen
Display/Screen: - Removed Display reusage by unique TLS key: type + name, instead use user-responsibility or Destroy-When-Unused (usage reference count). - Removed X11 Display TLS pool usage - Display creation means i, incl the later native one (X11). - Added reference counting as follows: - Display's refCount: number it is referenced by Screen: display.addReference()/display.removeReference() - Screen's refCount: number it is referenced by Window: screen.addReference()/screen.removeReference() - Lazy creation using refcount 0 -> 1 All resources are created when they are needed. This also removes redundant native Display/Screen objects, ie in case of [AWT] reparenting. - Default lifecycle is user-responsibility, ie no Destroy-When-Unused, where Window may be destroyed unrecoverable, which removes the Screen reference only. - If using optional Destroy-When-Unused a Window may be destroyed unrecoverable, which removes the Screen reference: Screen.removeReference(); IF Screen.refCount == 0 THEN Screen.destroy(); Display.removeReference(); IF Display.refCount == 0 THEN Display.destroy(); - Use Destroy-When-Unused lifecycle for all automatic created Display/Screen instances (GLWindow, NewtCanvasAWT,..) - Display/Screen destroy/create cycles valid, ie you can reuse destroyed Display/Screen's - EDTUtil: - Created right away. - Started always via invoke, if not running. - DefaultEDTUtil: - Simplified locking a bit locking on: - edtLock for start/stop - edtTasks for tasks queue - invoke-wait doubles check shouldStop - invoke-wait 'waiting' outside of edtLock +++ NEWT: Cleanup - Window.destroy/invalidate: deep -> unrecoverable - Window.isNativeWindowValid() -> Window.isNativeValid() to unify with Display/Screen - Window.isDestroyed() -> Window.isValid() to unify and simplify logic. Returns false if destroy(true) has been called. - NewtFactory.wrapDisplay(.. handle) -> NewtFactory.createDisplay(.. handle), since it actually creates a compatible display. +++ NativeWindow X11Util: Added non TLS createDisplay()/closeDisplay() +++ TODO: - Stabilize (many tests fail) - OSX
Diffstat (limited to 'src/newt/classes/com/jogamp')
-rw-r--r--src/newt/classes/com/jogamp/newt/Display.java318
-rw-r--r--src/newt/classes/com/jogamp/newt/NewtFactory.java6
-rw-r--r--src/newt/classes/com/jogamp/newt/OffscreenWindow.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/Screen.java95
-rw-r--r--src/newt/classes/com/jogamp/newt/Window.java106
-rw-r--r--src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java18
-rw-r--r--src/newt/classes/com/jogamp/newt/awt/NewtFactoryAWT.java46
-rw-r--r--src/newt/classes/com/jogamp/newt/event/awt/AWTParentWindowAdapter.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/event/awt/AWTWindowAdapter.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/awt/AWTDisplay.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/awt/AWTScreen.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/awt/AWTWindow.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/intel/gdl/Display.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/intel/gdl/Screen.java8
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/intel/gdl/Window.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/macosx/MacDisplay.java33
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/macosx/MacScreen.java8
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/macosx/MacWindow.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Display.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Screen.java6
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Window.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDDisplay.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDScreen.java6
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDWindow.java2
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/windows/WindowsDisplay.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/windows/WindowsScreen.java8
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/windows/WindowsWindow.java6
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/x11/X11Display.java12
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/x11/X11Screen.java14
-rw-r--r--src/newt/classes/com/jogamp/newt/impl/x11/X11Window.java4
-rw-r--r--src/newt/classes/com/jogamp/newt/opengl/GLWindow.java56
-rw-r--r--src/newt/classes/com/jogamp/newt/util/DefaultEDTUtil.java178
-rw-r--r--src/newt/classes/com/jogamp/newt/util/EDTUtil.java3
-rw-r--r--src/newt/classes/com/jogamp/newt/util/MainThread.java4
34 files changed, 555 insertions, 422 deletions
diff --git a/src/newt/classes/com/jogamp/newt/Display.java b/src/newt/classes/com/jogamp/newt/Display.java
index b9ef93572..1c1fdd7ec 100644
--- a/src/newt/classes/com/jogamp/newt/Display.java
+++ b/src/newt/classes/com/jogamp/newt/Display.java
@@ -69,111 +69,54 @@ public abstract class Display {
return displayClass;
}
- // Unique Display for each thread
- private static ThreadLocal currentDisplayMap = new ThreadLocal();
-
- /** Returns the thread local display map */
- public static Map getCurrentDisplayMap() {
- Map displayMap = (Map) currentDisplayMap.get();
- if(null==displayMap) {
- displayMap = new HashMap();
- currentDisplayMap.set( displayMap );
+ // Global Displays
+ private static ArrayList displayList = new ArrayList();
+ private static int displaysActive = 0;
+ private static int serialno = 1;
+
+ public static void dumpDisplayList(String prefix) {
+ synchronized(displayList) {
+ Iterator i = displayList.iterator();
+ System.err.println(prefix+" DisplayList[] entries: "+displayList.size()+" - "+getThreadName());
+ for(int j=0; i.hasNext(); j++) {
+ Display d = (Display) i.next();
+ System.err.println(" ["+j+"] : "+d);
+ }
}
- return displayMap;
}
- /** maps the given display to the thread local display map
- * and notifies all threads synchronized to this display map. */
- protected static Display setCurrentDisplay(Display display) {
- Map displayMap = getCurrentDisplayMap();
- Display oldDisplay = null;
- synchronized(displayMap) {
- oldDisplay = (Display) displayMap.put(display.getFQName(), display);
- displayMap.notifyAll();
+ /** Returns the global display collection */
+ public static Collection getAllDisplays() {
+ ArrayList list;
+ synchronized(displayList) {
+ list = (ArrayList) displayList.clone();
}
- return oldDisplay;
+ return list;
}
- /** removes the mapping of the given name from the thread local display map
- * and notifies all threads synchronized to this display map. */
- protected static Display removeCurrentDisplay(String type, String name) {
- Map displayMap = getCurrentDisplayMap();
- Display oldDisplay = null;
- synchronized(displayMap) {
- oldDisplay = (Display) displayMap.remove(getFQName(type,name));
- displayMap.notifyAll();
+ public static int getActiveDisplayNumber() {
+ synchronized(displayList) {
+ return displaysActive;
}
- return oldDisplay;
- }
-
- /** Returns the thread local display mapped to the given name */
- public static Display getCurrentDisplay(String type, String name) {
- Map displayMap = getCurrentDisplayMap();
- Display display = (Display) displayMap.get(getFQName(type,name));
- return display;
- }
-
- public static void dumpDisplayMap(String prefix) {
- Map displayMap = getCurrentDisplayMap();
- Set entrySet = displayMap.entrySet();
- Iterator i = entrySet.iterator();
- System.err.println(prefix+" DisplayMap[] entries: "+entrySet.size()+" - "+getThreadName());
- for(int j=0; i.hasNext(); j++) {
- Map.Entry entry = (Map.Entry) i.next();
- System.err.println(" ["+j+"] "+entry.getKey()+" -> "+entry.getValue());
- }
- }
-
- /** Returns the thread local display collection */
- public static Collection getCurrentDisplays() {
- return getCurrentDisplayMap().values();
}
/** Make sure to reuse a Display with the same name */
- protected static synchronized Display create(String type, String name, final long handle) {
+ protected static Display create(String type, String name, final long handle) {
try {
Class displayClass = getDisplayClass(type);
- Display tmpDisplay = (Display) displayClass.newInstance();
- name = tmpDisplay.validateDisplayName(name, handle);
-
- if(DEBUG) {
- dumpDisplayMap("Display.create("+getFQName(type, name)+") BEGIN");
- }
- Display display = getCurrentDisplay(type, name);
- if(null==display) {
- display = tmpDisplay;
- tmpDisplay = null;
- display.name = name;
- display.type=type;
- display.refCount=0;
- if(DEBUG) {
- System.err.println("Display.create("+getFQName(type, name)+") NEW: refCount "+display.refCount+", "+display+" "+getThreadName());
- }
- } else {
- tmpDisplay = null;
- if(DEBUG) {
- System.err.println("Display.create("+getFQName(type, name)+") REUSE: refCount "+display.refCount+", "+display+" "+getThreadName());
- }
- }
- synchronized(display) {
- display.refCount++;
- if(null==display.aDevice) {
- final Display f_dpy = display;
- display.runOnEDTIfAvail(true, new Runnable() {
- public void run() {
- f_dpy.createNative();
- }});
- if(null==display.aDevice) {
- throw new RuntimeException("Display.createNative() failed to instanciate an AbstractGraphicsDevice");
- }
- setCurrentDisplay(display);
- if(DEBUG) {
- System.err.println("Display.create("+getFQName(type, name)+") CreateNative: "+display+" "+getThreadName());
- }
- }
+ Display display = (Display) displayClass.newInstance();
+ name = display.validateDisplayName(name, handle);
+ display.name = name;
+ display.type=type;
+ display.destroyWhenUnused=false;
+ synchronized(displayList) {
+ display.id = serialno++;
+ display.fqname = getFQName(display.id, display.type, display.name);
+ displayList.add(display);
}
+ display.createEDTUtil();
if(DEBUG) {
- dumpDisplayMap("Display.create("+getFQName(type, name)+") END");
+ System.err.println("Display.create() NEW: "+display+" "+getThreadName());
}
return display;
} catch (Exception e) {
@@ -181,98 +124,138 @@ public abstract class Display {
}
}
+ protected synchronized final void createNative() {
+ if(null==aDevice) {
+ if(DEBUG) {
+ System.out.println("Display.createNative() START ("+getThreadName()+", "+this+")");
+ }
+ final Display f_dpy = this;
+ runOnEDTIfAvail(true, new Runnable() {
+ public void run() {
+ f_dpy.createNativeImpl();
+ }});
+ if(null==aDevice) {
+ throw new RuntimeException("Display.createNative() failed to instanciate an AbstractGraphicsDevice");
+ }
+ if(DEBUG) {
+ System.out.println("Display.createNative() END ("+getThreadName()+", "+this+")");
+ }
+ synchronized(displayList) {
+ displaysActive++;
+ }
+ }
+ }
+
protected boolean getShallRunOnEDT() {
return true;
}
- public EDTUtil getEDTUtil() {
- if( null == edtUtil ) {
- synchronized (this) {
- if( null == edtUtil ) {
- if(NewtFactory.useEDT()) {
- final Display f_dpy = this;
- if ( ! DEBUG_TEST_EDT_MAINTHREAD ) {
- Thread current = Thread.currentThread();
- edtUtil = new DefaultEDTUtil(current.getThreadGroup(),
- "Display_"+getFQName(),
- new Runnable() {
- public void run() {
- if(null!=f_dpy.getGraphicsDevice()) {
- f_dpy.dispatchMessages();
- } } } );
- } else {
- // Begin JAU EDT Test ..
- MainThread.addPumpMessage(this,
- new Runnable() {
- public void run() {
- if(null!=f_dpy.getGraphicsDevice()) {
- f_dpy.dispatchMessages();
- } } } );
- edtUtil = MainThread.getSingleton();
- System.err.println("Display.getEDTUtil("+getFQName()+") Test EDT MainThread: "+edtUtil.getClass().getName());
- // End JAU EDT Test ..
- }
- edtUtil.start();
- }
- }
+ protected void createEDTUtil() {
+ if(NewtFactory.useEDT()) {
+ if ( ! DEBUG_TEST_EDT_MAINTHREAD ) {
+ Thread current = Thread.currentThread();
+ edtUtil = new DefaultEDTUtil(current.getThreadGroup(), "Display_"+getFQName(), dispatchMessagesRunnable);
+ } else {
+ // Begin JAU EDT Test ..
+ MainThread.addPumpMessage(this, dispatchMessagesRunnable);
+ edtUtil = MainThread.getSingleton();
+ // End JAU EDT Test ..
+ }
+ if(DEBUG) {
+ System.err.println("Display.createNative("+getFQName()+") Create EDTUtil: "+edtUtil.getClass().getName());
}
}
- return edtUtil;
}
- protected void releaseEDTUtil() {
- if(null!=edtUtil) {
- if ( DEBUG_TEST_EDT_MAINTHREAD ) {
- MainThread.removePumpMessage(this); // JAU EDT Test ..
- }
- edtUtil.waitUntilStopped();
- edtUtil=null;
- }
+ public final EDTUtil getEDTUtil() {
+ return edtUtil;
}
public void runOnEDTIfAvail(boolean wait, final Runnable task) {
- EDTUtil _edtUtil = getEDTUtil();
- if(getShallRunOnEDT() && null!=_edtUtil) {
- _edtUtil.invoke(wait, task);
+ if( getShallRunOnEDT() && null!=edtUtil ) {
+ edtUtil.invoke(wait, task);
} else {
task.run();
}
}
- public synchronized void destroy() {
- if(DEBUG) {
- dumpDisplayMap("Display.destroy("+getFQName()+") BEGIN");
- }
- refCount--;
- if(0==refCount) {
- removeCurrentDisplay(type, name);
+ public synchronized final void destroy() {
+ if ( null != aDevice ) {
+ if(DEBUG) {
+ dumpDisplayList("Display.destroy("+getFQName()+") BEGIN");
+ }
+ synchronized(displayList) {
+ displayList.remove(this);
+ displaysActive--;
+ }
if(DEBUG) {
- System.err.println("Display.destroy("+getFQName()+") REMOVE: "+this+" "+getThreadName());
+ System.err.println("Display.destroy(): "+this+" "+getThreadName());
}
final Display f_dpy = this;
final EDTUtil f_edtUtil = edtUtil;
runOnEDTIfAvail(true, new Runnable() {
public void run() {
- f_dpy.closeNative();
+ f_dpy.closeNativeImpl();
if(null!=f_edtUtil) {
f_edtUtil.stop();
}
}
} );
- releaseEDTUtil();
+ if(null!=edtUtil) {
+ if ( DEBUG_TEST_EDT_MAINTHREAD ) {
+ MainThread.removePumpMessage(this); // JAU EDT Test ..
+ }
+ edtUtil.waitUntilStopped();
+ edtUtil.reset();
+ }
aDevice = null;
- } else {
if(DEBUG) {
- System.err.println("Display.destroy("+getFQName()+") KEEP: refCount "+refCount+", "+this+" "+getThreadName());
+ dumpDisplayList("Display.destroy("+getFQName()+") END");
}
}
+ }
+
+ protected synchronized final int addReference() {
if(DEBUG) {
- dumpDisplayMap("Display.destroy("+getFQName()+") END");
+ System.out.println("Display.addReference() ("+Display.getThreadName()+"): "+refCount+" -> "+(refCount+1));
+ }
+ if ( 0 == refCount ) {
+ createNative();
+ }
+ if(null == aDevice) {
+ throw new RuntimeException("Display.addReference() (refCount "+refCount+") null AbstractGraphicsDevice");
}
+ return ++refCount;
}
- protected abstract void createNative();
- protected abstract void closeNative();
+
+ protected synchronized final int removeReference() {
+ if(DEBUG) {
+ System.out.println("Display.removeReference() ("+Display.getThreadName()+"): "+refCount+" -> "+(refCount-1));
+ }
+ refCount--;
+ if(0==refCount && destroyWhenUnused) {
+ destroy();
+ }
+ return refCount;
+ }
+
+ /**
+ * @return number of references by Screen
+ */
+ public synchronized final int getReferenceCount() {
+ return refCount;
+ }
+
+ public final boolean getDestroyWhenUnused() { return destroyWhenUnused; }
+ public final void setDestroyWhenUnused(boolean v) { destroyWhenUnused=v; }
+
+ protected abstract void createNativeImpl();
+ protected abstract void closeNativeImpl();
+
+ public final int getId() {
+ return id;
+ }
public final String getType() {
return type;
@@ -283,35 +266,45 @@ public abstract class Display {
}
public final String getFQName() {
- return getFQName(type, name);
+ return fqname;
}
- static final String nilString = "nil" ;
+ public static final String nilString = "nil" ;
- protected String validateDisplayName(String name, long handle) {
+ public String validateDisplayName(String name, long handle) {
if(null==name && 0!=handle) {
name="wrapping-"+toHexString(handle);
}
return ( null == name ) ? nilString : name ;
}
- public static final String getFQName(String type, String name) {
+ public static final String getFQName(int id, String type, String name) {
if(null==type) type=nilString;
if(null==name) name=nilString;
- return type+"_"+name;
+ StringBuffer sb = new StringBuffer();
+ sb.append(type);
+ sb.append("_");
+ sb.append(name);
+ sb.append("_");
+ sb.append(id);
+ return sb.toString();
}
- public long getHandle() {
+ public final long getHandle() {
if(null!=aDevice) {
return aDevice.getHandle();
}
return 0;
}
- public AbstractGraphicsDevice getGraphicsDevice() {
+ public final AbstractGraphicsDevice getGraphicsDevice() {
return aDevice;
}
+ public final boolean isNativeValid() {
+ return null != aDevice;
+ }
+
public synchronized void pumpMessages() {
dispatchMessages();
}
@@ -338,8 +331,16 @@ public abstract class Display {
private Object eventsLock = new Object();
private LinkedList/*<NEWTEvent>*/ events = new LinkedList();
+ class DispatchMessagesRunnable implements Runnable {
+ public void run() {
+ Display.this.dispatchMessages();
+ }
+ }
+ DispatchMessagesRunnable dispatchMessagesRunnable = new DispatchMessagesRunnable();
+
public void dispatchMessages() {
- if(0==refCount) return; // in destruction ..
+ if(0==refCount) return; // no screens
+ if(null==getGraphicsDevice()) return; // no native device
LinkedList/*<NEWTEvent>*/ _events = null;
@@ -405,9 +406,12 @@ public abstract class Display {
}
protected EDTUtil edtUtil = null;
+ protected int id;
protected String name;
protected String type;
- protected int refCount;
+ protected String fqname;
+ protected int refCount; // number of Display references by Screen
+ protected boolean destroyWhenUnused;
protected AbstractGraphicsDevice aDevice;
}
diff --git a/src/newt/classes/com/jogamp/newt/NewtFactory.java b/src/newt/classes/com/jogamp/newt/NewtFactory.java
index 3959c6a8d..12dadc310 100644
--- a/src/newt/classes/com/jogamp/newt/NewtFactory.java
+++ b/src/newt/classes/com/jogamp/newt/NewtFactory.java
@@ -145,12 +145,13 @@ public abstract class NewtFactory {
if(null!=nParentConfig) {
AbstractGraphicsScreen nParentScreen = nParentConfig.getScreen();
AbstractGraphicsDevice nParentDevice = nParentScreen.getDevice();
- Display display = NewtFactory.wrapDisplay(type, nParentDevice.getHandle());
+ Display display = NewtFactory.createDisplay(type, nParentDevice.getHandle());
screen = NewtFactory.createScreen(type, display, nParentScreen.getIndex());
} else {
Display display = NewtFactory.createDisplay(type, null); // local display
screen = NewtFactory.createScreen(type, display, 0); // screen 0
}
+ screen.setDestroyWhenUnused(true);
final Window win = createWindowImpl(type, nParentWindow, screen, caps, undecorated);
win.setSize(nParentWindow.getWidth(), nParentWindow.getHeight());
@@ -177,6 +178,7 @@ public abstract class NewtFactory {
protected static Window createWindowImpl(String type, Capabilities caps, boolean undecorated) {
Display display = NewtFactory.createDisplay(type, null); // local display
Screen screen = NewtFactory.createScreen(type, display, 0); // screen 0
+ screen.setDestroyWhenUnused(true);
return Window.create(type, null, 0, screen, caps, undecorated);
}
@@ -217,7 +219,7 @@ public abstract class NewtFactory {
/**
* Instantiate a Display entity using the native handle.
*/
- public static Display wrapDisplay(String type, long handle) {
+ public static Display createDisplay(String type, long handle) {
return Display.create(type, null, handle);
}
diff --git a/src/newt/classes/com/jogamp/newt/OffscreenWindow.java b/src/newt/classes/com/jogamp/newt/OffscreenWindow.java
index e85714d4f..d17f8df07 100644
--- a/src/newt/classes/com/jogamp/newt/OffscreenWindow.java
+++ b/src/newt/classes/com/jogamp/newt/OffscreenWindow.java
@@ -62,7 +62,7 @@ public class OffscreenWindow extends Window implements SurfaceChangeable {
}
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
// nop
}
diff --git a/src/newt/classes/com/jogamp/newt/Screen.java b/src/newt/classes/com/jogamp/newt/Screen.java
index 26342519e..e9697647d 100644
--- a/src/newt/classes/com/jogamp/newt/Screen.java
+++ b/src/newt/classes/com/jogamp/newt/Screen.java
@@ -40,6 +40,8 @@ import java.security.*;
public abstract class Screen {
+ public static final boolean DEBUG = Debug.debug("Display");
+
private static Class getScreenClass(String type)
throws ClassNotFoundException
{
@@ -62,7 +64,7 @@ public abstract class Screen {
return screenClass;
}
- protected static Screen create(String type, Display display, int idx) {
+ protected static Screen create(String type, Display display, final int idx) {
try {
if(usrWidth<0 || usrHeight<0) {
usrWidth = Debug.getIntProperty("newt.ws.swidth", true, localACC);
@@ -74,48 +76,105 @@ public abstract class Screen {
Class screenClass = getScreenClass(type);
Screen screen = (Screen) screenClass.newInstance();
screen.display = display;
- screen.createNative(idx);
- if(null==screen.aScreen) {
- throw new RuntimeException("Screen.createNative() failed to instanciate an AbstractGraphicsScreen");
- }
+ screen.idx = idx;
return screen;
} catch (Exception e) {
throw new RuntimeException(e);
}
}
- public synchronized void destroy() {
- closeNative();
- display = null;
- aScreen = null;
+ protected synchronized final void createNative() {
+ if(null == aScreen) {
+ if(DEBUG) {
+ System.out.println("Screen.createNative() START ("+Display.getThreadName()+", "+this+")");
+ }
+ display.addReference();
+ createNativeImpl();
+ if(null == aScreen) {
+ throw new RuntimeException("Screen.createNative() failed to instanciate an AbstractGraphicsScreen");
+ }
+ if(DEBUG) {
+ System.out.println("Screen.createNative() END ("+Display.getThreadName()+", "+this+")");
+ }
+ }
+ }
+
+ public synchronized final void destroy() {
+ if ( null != aScreen ) {
+ closeNativeImpl();
+ display.removeReference();
+ aScreen = null;
+ }
+ }
+
+ protected synchronized final int addReference() {
+ if(DEBUG) {
+ System.out.println("Screen.addReference() ("+Display.getThreadName()+"): "+refCount+" -> "+(refCount+1));
+ }
+ if ( 0 == refCount ) {
+ createNative();
+ }
+ if(null == aScreen) {
+ throw new RuntimeException("Screen.addReference() (refCount "+refCount+") null AbstractGraphicsScreen");
+ }
+ return ++refCount;
+ }
+
+ protected synchronized final int removeReference() {
+ if(DEBUG) {
+ System.out.println("Screen.removeReference() ("+Display.getThreadName()+"): "+refCount+" -> "+(refCount-1));
+ }
+ refCount--;
+ if(0==refCount && getDestroyWhenUnused()) {
+ destroy();
+ }
+ return refCount;
+ }
+
+ /**
+ * @return number of references by Window
+ */
+ public synchronized final int getReferenceCount() {
+ return refCount;
}
- protected abstract void createNative(int index);
- protected abstract void closeNative();
+ public final boolean getDestroyWhenUnused() {
+ return display.getDestroyWhenUnused();
+ }
+ public final void setDestroyWhenUnused(boolean v) {
+ display.setDestroyWhenUnused(v);
+ }
+
+ protected abstract void createNativeImpl();
+ protected abstract void closeNativeImpl();
protected void setScreenSize(int w, int h) {
System.out.println("Detected screen size "+w+"x"+h);
width=w; height=h;
}
- public Display getDisplay() {
+ public final Display getDisplay() {
return display;
}
- public int getIndex() {
- return aScreen.getIndex();
+ public final int getIndex() {
+ return idx;
}
- public AbstractGraphicsScreen getGraphicsScreen() {
+ public final AbstractGraphicsScreen getGraphicsScreen() {
return aScreen;
}
+ public final boolean isNativeValid() {
+ return null != aScreen;
+ }
+
/**
* The actual implementation shall return the detected display value,
* if not we return 800.
* This can be overwritten with the user property 'newt.ws.swidth',
*/
- public int getWidth() {
+ public final int getWidth() {
return (usrWidth>0) ? usrWidth : (width>0) ? width : 480;
}
@@ -124,12 +183,14 @@ public abstract class Screen {
* if not we return 480.
* This can be overwritten with the user property 'newt.ws.sheight',
*/
- public int getHeight() {
+ public final int getHeight() {
return (usrHeight>0) ? usrHeight : (height>0) ? height : 480;
}
protected Display display;
+ protected int idx;
protected AbstractGraphicsScreen aScreen;
+ protected int refCount; // number of Screen references by Window
protected int width=-1, height=-1; // detected values: set using setScreenSize
protected static int usrWidth=-1, usrHeight=-1; // property values: newt.ws.swidth and newt.ws.sheight
private static AccessControlContext localACC = AccessController.getContext();
diff --git a/src/newt/classes/com/jogamp/newt/Window.java b/src/newt/classes/com/jogamp/newt/Window.java
index d002791ca..3f07e63de 100644
--- a/src/newt/classes/com/jogamp/newt/Window.java
+++ b/src/newt/classes/com/jogamp/newt/Window.java
@@ -150,8 +150,9 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
protected String title = "Newt Window";
protected boolean undecorated = false;
+ protected boolean screenRefAdded = false;
- private boolean createNative() {
+ private final boolean createNative() {
if( null==screen || 0!=windowHandle || !visible ) {
return 0 != windowHandle ;
}
@@ -159,7 +160,11 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
System.out.println("Window.createNative() START ("+getThreadName()+", "+this+")");
}
if(validateParentWindowHandle()) {
- Display dpy = getScreen().getDisplay();
+ if(!screenRefAdded) {
+ // only once .. at 1st creation
+ screenRefAdded = true;
+ getScreen().addReference();
+ }
createNativeImpl();
setVisibleImpl(true);
}
@@ -219,7 +224,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
*/
protected abstract void createNativeImpl();
- protected abstract void closeNative();
+ protected abstract void closeNativeImpl();
public Capabilities getRequestedCapabilities() {
return (Capabilities)caps.clone();
@@ -348,7 +353,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
windowLock.lock();
// if(windowLock.getRecursionCount() == 0) { // allow recursion to lock again, always
- if(isDestroyed() || !isNativeWindowValid()) {
+ if(!isNativeValid()) {
windowLock.unlock();
return LOCK_SURFACE_NOT_READY;
}
@@ -381,7 +386,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
* windowing related resources.<br></p>
* <p>
* all other resources and states are kept intact,
- * ie listeners, parent handles and size, position etc.<br></p>
+ * ie listeners, parent handles, size, position and Screen reference.<br></p>
*
* @see #destroy(boolean)
* @see #invalidate()
@@ -391,49 +396,51 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
}
/**
- * @param deep If true, all resources, ie listeners, parent handles, size, position
- * and the referenced NEWT screen and display, will be destroyed as well. Be aware that if you call
- * this method with deep = true, you will not be able to regenerate the Window.
+ * Destroys the Window and it's children.
+ * @param unrecoverable If true, all resources, ie listeners, parent handles,
+ * size, position and reference to it's Screen will be destroyed as well.
+ * Otherwise you can recreate the window, via <code>setVisible(true)</code>.
* @see #destroy()
* @see #invalidate(boolean)
+ * @see #setVisible(boolean)
*/
- public void destroy(boolean deep) {
- if(!isDestroyed()) {
- runOnEDTIfAvail(true, new DestroyAction(deep));
+ public void destroy(boolean unrecoverable) {
+ if(isValid()) {
+ runOnEDTIfAvail(true, new DestroyAction(unrecoverable));
}
}
class DestroyAction implements Runnable {
- boolean deep;
- public DestroyAction(boolean deep) {
- this.deep = deep;
+ boolean unrecoverable;
+ public DestroyAction(boolean unrecoverable) {
+ this.unrecoverable = unrecoverable;
}
public void run() {
windowLock();
try {
if(DEBUG_IMPLEMENTATION) {
- System.out.println("Window.destroy(deep: "+deep+") START "+getThreadName()+", "+Window.this);
+ System.out.println("Window.destroy(unrecoverable: "+unrecoverable+") START "+getThreadName()+", "+Window.this);
}
// Childs first ..
synchronized(childWindowsLock) {
for(Iterator i = childWindows.iterator(); i.hasNext(); ) {
NativeWindow nw = (NativeWindow) i.next();
- System.out.println("Window.destroy(deep: "+deep+") CHILD BEGIN");
+ System.out.println("Window.destroy(unrecoverable: "+unrecoverable+") CHILD BEGIN");
if(nw instanceof Window) {
((Window)nw).sendWindowEvent(WindowEvent.EVENT_WINDOW_DESTROY_NOTIFY);
- if(deep) {
- ((Window)nw).destroy(deep);
+ if(unrecoverable) {
+ ((Window)nw).destroy(unrecoverable);
}
} else {
nw.destroy();
}
- System.out.println("Window.destroy(deep: "+deep+") CHILD END");
+ System.out.println("Window.destroy(unrecoverable: "+unrecoverable+") CHILD END");
}
}
// Now us ..
- if(deep) {
+ if(unrecoverable) {
synchronized(childWindowsLock) {
childWindows = new ArrayList();
}
@@ -444,24 +451,20 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
mouseListeners = new ArrayList();
keyListeners = new ArrayList();
}
- Display dpy = null;
Screen scr = null;
if( null != screen && 0 != windowHandle ) {
scr = screen;
- dpy = screen.getDisplay();
- closeNative();
+ closeNativeImpl();
}
- invalidate(deep);
- if(deep) {
+ invalidate(unrecoverable);
+ if(unrecoverable) {
if(null!=scr) {
- scr.destroy();
- }
- if(null!=dpy) {
- dpy.destroy();
+ // only once .. at final destruction
+ scr.removeReference();
}
}
if(DEBUG_IMPLEMENTATION) {
- System.out.println("Window.destroy(deep: "+deep+") END "+getThreadName()+", "+Window.this);
+ System.out.println("Window.destroy(unrecoverable: "+unrecoverable+") END "+getThreadName()+", "+Window.this);
}
} finally {
windowUnlock();
@@ -486,18 +489,18 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
}
/**
- * @param deep if false only the native window handle is invalidated, otherwise all
- * states (references and properties) are reset. Be aware that if you call
- * this method with deep = true, you will not be able to regenerate the Window.
+ * @param unrecoverable If true, all states, size, position, parent handles,
+ * reference to it's Screen are reset.
+ * Otherwise you can recreate the window, via <code>setVisible(true)</code>.
* @see #invalidate()
* @see #destroy()
* @see #destroy(boolean)
*/
- public void invalidate(boolean deep) {
+ public void invalidate(boolean unrecoverable) {
windowLock();
try{
if(DEBUG_IMPLEMENTATION || DEBUG_WINDOW_EVENT) {
- String msg = new String("!!! Window Invalidate(deep: "+deep+") "+getThreadName());
+ String msg = new String("!!! Window Invalidate(unrecoverable: "+unrecoverable+") "+getThreadName());
//System.out.println(msg);
Exception e = new Exception(msg);
e.printStackTrace();
@@ -506,7 +509,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
visible = false;
fullscreen = false;
- if(deep) {
+ if(unrecoverable) {
screen = null;
parentWindowHandle = 0;
parentNativeWindow = null;
@@ -523,13 +526,24 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
}
}
- /** @return true if the native window handle is valid and ready to operate */
- public boolean isNativeWindowValid() {
- return 0 != windowHandle ;
+ /** @return true if the native window handle is valid and ready to operate, ie
+ * if the native window has been created, otherwise false.
+ *
+ * @see #setVisible(boolean)
+ * @see #destroy(boolean)
+ */
+ public boolean isNativeValid() {
+ return null != screen && 0 != windowHandle ;
}
- public boolean isDestroyed() {
- return null == screen ;
+ /** @return True if native window is valid, can be created or recovered.
+ * Otherwise false, ie this window is unrecoverable due to a <code>destroy(true)</code> call.
+ *
+ * @see #destroy(boolean)
+ * @see #setVisible(boolean)
+ */
+ public boolean isValid() {
+ return null != screen ;
}
public boolean surfaceSwap() {
@@ -713,7 +727,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
* this Screen is being used.
*/
public void reparentWindow(NativeWindow newParent, Screen newScreen) {
- if(!isDestroyed()) {
+ if(isValid()) {
runOnEDTIfAvail(true, new ReparentAction(newParent, newScreen));
if( isVisible() ) {
sendWindowEvent(WindowEvent.EVENT_WINDOW_RESIZED); // trigger a resize/relayout to listener
@@ -730,7 +744,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
public void run() {
windowLock();
try{
- if( !isDestroyed() ) {
+ if( isValid() ) {
if(!visible && childWindows.size()>0) {
synchronized(childWindowsLock) {
for(Iterator i = childWindows.iterator(); i.hasNext(); ) {
@@ -805,7 +819,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
Exception ee = new Exception(msg);
ee.printStackTrace();
}
- if(!isDestroyed()) {
+ if(isValid()) {
runOnEDTIfAvail(true, new VisibleAction(visible));
}
}
@@ -985,7 +999,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
}
public void enqueueEvent(boolean wait, com.jogamp.newt.event.NEWTEvent event) {
- if(!getInnerWindow().isDestroyed()) {
+ if(getInnerWindow().isValid()) {
getInnerWindow().getScreen().getDisplay().enqueueEvent(wait, event);
}
}
@@ -1523,7 +1537,7 @@ public abstract class Window implements NativeWindow, NEWTEventConsumer
enqueueWindowEvent(false, WindowEvent.EVENT_WINDOW_DESTROY_NOTIFY);
- if(handleDestroyNotify && !isDestroyed()) {
+ if(handleDestroyNotify && isValid()) {
destroy();
}
diff --git a/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java b/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java
index 57647df5c..d7e75a5b9 100644
--- a/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java
+++ b/src/newt/classes/com/jogamp/newt/awt/NewtCanvasAWT.java
@@ -55,7 +55,7 @@ import com.jogamp.newt.Window;
import com.jogamp.newt.impl.Debug;
public class NewtCanvasAWT extends java.awt.Canvas {
- public static final boolean DEBUG_IMPLEMENTATION = Debug.debug("Window");
+ public static final boolean DEBUG = Debug.debug("Window");
NativeWindow parent = null;
Window newtChild = null;
@@ -93,7 +93,7 @@ public class NewtCanvasAWT extends java.awt.Canvas {
class FocusActionImpl implements Runnable {
public final boolean result = false; // NEWT shall always proceed requesting the native focus
public void run() {
- if(DEBUG_IMPLEMENTATION) {
+ if(DEBUG) {
System.out.println("FocusActionImpl.run() "+Window.getThreadName());
}
NewtCanvasAWT.this.requestFocusAWTParent();
@@ -150,7 +150,7 @@ public class NewtCanvasAWT extends java.awt.Canvas {
super.addNotify();
disableBackgroundErase();
java.awt.Container cont = getContainer(this);
- if(DEBUG_IMPLEMENTATION) {
+ if(DEBUG) {
// if ( isShowing() == false ) -> Container was not visible yet.
// if ( isShowing() == true ) -> Container is already visible.
System.err.println("NewtCanvasAWT.addNotify: "+newtChild+", "+this+", visible "+isVisible()+", showing "+isShowing()+
@@ -161,7 +161,7 @@ public class NewtCanvasAWT extends java.awt.Canvas {
public void removeNotify() {
java.awt.Container cont = getContainer(this);
- if(DEBUG_IMPLEMENTATION) {
+ if(DEBUG) {
System.err.println("NewtCanvasAWT.removeNotify: "+newtChild+", from "+cont);
}
reparentWindow(false, cont);
@@ -178,15 +178,19 @@ public class NewtCanvasAWT extends java.awt.Canvas {
parent = NewtFactoryAWT.getNativeWindow(this, newtChild.getRequestedCapabilities());
}
if(null!=parent) {
- if(DEBUG_IMPLEMENTATION) {
+ if(DEBUG) {
System.err.println("NewtCanvasAWT.reparentWindow: "+newtChild);
}
setSize(cont.getWidth(), cont.getHeight());
newtChild.setSize(cont.getWidth(), cont.getHeight());
Screen screen = null;
- if( !newtChild.isNativeWindowValid() ) {
- screen = NewtFactoryAWT.createCompatibleScreen(parent);
+ if( !newtChild.isNativeValid() ) {
+ Screen currentScreen = newtChild.getScreen();
+ screen = NewtFactoryAWT.createCompatibleScreen(parent, currentScreen);
+ if( currentScreen != screen ) {
+ screen.setDestroyWhenUnused(true);
+ }
}
newtChild.reparentWindow(parent, screen);
newtChild.setVisible(true);
diff --git a/src/newt/classes/com/jogamp/newt/awt/NewtFactoryAWT.java b/src/newt/classes/com/jogamp/newt/awt/NewtFactoryAWT.java
index 6409ab7a8..bd5a6cd73 100644
--- a/src/newt/classes/com/jogamp/newt/awt/NewtFactoryAWT.java
+++ b/src/newt/classes/com/jogamp/newt/awt/NewtFactoryAWT.java
@@ -86,15 +86,57 @@ public class NewtFactoryAWT extends NewtFactory {
}
public static Screen createCompatibleScreen(NativeWindow parent) {
+ return createCompatibleScreen(parent, null);
+ }
+
+ public static Screen createCompatibleScreen(NativeWindow parent, Screen childScreen) {
// Get parent's NativeWindow details
AWTGraphicsConfiguration parentConfig = (AWTGraphicsConfiguration) parent.getGraphicsConfiguration();
AWTGraphicsScreen parentScreen = (AWTGraphicsScreen) parentConfig.getScreen();
AWTGraphicsDevice parentDevice = (AWTGraphicsDevice) parentScreen.getDevice();
- // Prep NEWT's Display and Screen according to the parent
final String type = NativeWindowFactory.getNativeWindowType(true);
- Display display = NewtFactory.wrapDisplay(type, parentDevice.getHandle());
+
+ if(null != childScreen) {
+ // check if child Display/Screen is compatible already
+ Display childDisplay = childScreen.getDisplay();
+ String parentDisplayName = childDisplay.validateDisplayName(null, parentDevice.getHandle());
+ String childDisplayName = childDisplay.getName();
+ boolean displayEqual = parentDisplayName.equals( childDisplayName );
+ boolean screenEqual = parentScreen.getIndex() == childScreen.getIndex();
+ if(DEBUG_IMPLEMENTATION) {
+ System.out.println("NewtFactoryAWT.createCompatibleScreen: Display: "+
+ parentDisplayName+" =? "+childDisplayName+" : "+displayEqual+"; Screen: "+
+ parentScreen.getIndex()+" =? "+childScreen.getIndex()+" : "+screenEqual);
+ }
+ if( displayEqual && screenEqual ) {
+ // match: display/screen
+ return childScreen;
+ }
+ }
+
+ // Prep NEWT's Display and Screen according to the parent
+ Display display = NewtFactory.createDisplay(type, parentDevice.getHandle());
return NewtFactory.createScreen(type, display, parentScreen.getIndex());
}
+
+ public static boolean isScreenCompatible(NativeWindow parent, Screen childScreen) {
+ // Get parent's NativeWindow details
+ AWTGraphicsConfiguration parentConfig = (AWTGraphicsConfiguration) parent.getGraphicsConfiguration();
+ AWTGraphicsScreen parentScreen = (AWTGraphicsScreen) parentConfig.getScreen();
+ AWTGraphicsDevice parentDevice = (AWTGraphicsDevice) parentScreen.getDevice();
+
+ Display childDisplay = childScreen.getDisplay();
+ String parentDisplayName = childDisplay.validateDisplayName(null, parentDevice.getHandle());
+ String childDisplayName = childDisplay.getName();
+ if( ! parentDisplayName.equals( childDisplayName ) ) {
+ return false;
+ }
+
+ if( parentScreen.getIndex() != childScreen.getIndex() ) {
+ return false;
+ }
+ return true;
+ }
}
diff --git a/src/newt/classes/com/jogamp/newt/event/awt/AWTParentWindowAdapter.java b/src/newt/classes/com/jogamp/newt/event/awt/AWTParentWindowAdapter.java
index 9f0944ea0..c5a60226f 100644
--- a/src/newt/classes/com/jogamp/newt/event/awt/AWTParentWindowAdapter.java
+++ b/src/newt/classes/com/jogamp/newt/event/awt/AWTParentWindowAdapter.java
@@ -104,7 +104,7 @@ public class AWTParentWindowAdapter
if(DEBUG_IMPLEMENTATION) {
System.out.println("AWT: hierarchyChanged SHOWING_CHANGED: showing "+showing+", "+changed);
}
- if(!newtWindow.isDestroyed()) {
+ if(newtWindow.isValid()) {
newtWindow.runOnEDTIfAvail(false, new Runnable() {
public void run() {
newtWindow.setVisible(showing);
diff --git a/src/newt/classes/com/jogamp/newt/event/awt/AWTWindowAdapter.java b/src/newt/classes/com/jogamp/newt/event/awt/AWTWindowAdapter.java
index 875401544..5df853610 100644
--- a/src/newt/classes/com/jogamp/newt/event/awt/AWTWindowAdapter.java
+++ b/src/newt/classes/com/jogamp/newt/event/awt/AWTWindowAdapter.java
@@ -131,7 +131,7 @@ public class AWTWindowAdapter
}
/**
if(null==newtListener) {
- if(!newtWindow.isDestroyed()) {
+ if(newtWindow.isValid()) {
newtWindow.runOnEDTIfAvail(false, new Runnable() {
public void run() {
newtWindow.setVisible(true);
@@ -148,7 +148,7 @@ public class AWTWindowAdapter
}
/**
if(null==newtListener) {
- if(!newtWindow.isDestroyed()) {
+ if(newtWindow.isValid()) {
newtWindow.runOnEDTIfAvail(false, new Runnable() {
public void run() {
newtWindow.setVisible(false);
diff --git a/src/newt/classes/com/jogamp/newt/impl/awt/AWTDisplay.java b/src/newt/classes/com/jogamp/newt/impl/awt/AWTDisplay.java
index 92c4e53eb..c9c6c63fc 100644
--- a/src/newt/classes/com/jogamp/newt/impl/awt/AWTDisplay.java
+++ b/src/newt/classes/com/jogamp/newt/impl/awt/AWTDisplay.java
@@ -44,7 +44,7 @@ public class AWTDisplay extends Display {
public AWTDisplay() {
}
- protected void createNative() {
+ protected void createNativeImpl() {
aDevice = (AWTGraphicsDevice) AWTGraphicsDevice.createDevice(null); // default
}
@@ -52,7 +52,7 @@ public class AWTDisplay extends Display {
aDevice = d;
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
protected boolean getShallRunOnEDT() {
return false;
diff --git a/src/newt/classes/com/jogamp/newt/impl/awt/AWTScreen.java b/src/newt/classes/com/jogamp/newt/impl/awt/AWTScreen.java
index 8702686c0..eec83d721 100644
--- a/src/newt/classes/com/jogamp/newt/impl/awt/AWTScreen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/awt/AWTScreen.java
@@ -42,7 +42,7 @@ public class AWTScreen extends Screen {
public AWTScreen() {
}
- protected void createNative(int index) {
+ protected void createNativeImpl() {
aScreen = new AWTGraphicsScreen((AWTGraphicsDevice)display.getGraphicsDevice());
DisplayMode mode = ((AWTGraphicsDevice)getDisplay().getGraphicsDevice()).getGraphicsDevice().getDisplayMode();
@@ -60,6 +60,6 @@ public class AWTScreen extends Screen {
super.setScreenSize(w, h);
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
}
diff --git a/src/newt/classes/com/jogamp/newt/impl/awt/AWTWindow.java b/src/newt/classes/com/jogamp/newt/impl/awt/AWTWindow.java
index db55aee6f..9da1eb860 100644
--- a/src/newt/classes/com/jogamp/newt/impl/awt/AWTWindow.java
+++ b/src/newt/classes/com/jogamp/newt/impl/awt/AWTWindow.java
@@ -148,7 +148,7 @@ public class AWTWindow extends Window {
this.windowHandle = 1; // just a marker ..
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
this.windowHandle = 0; // just a marker ..
if(null!=container) {
runOnEDT(true, new Runnable() {
diff --git a/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Display.java b/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Display.java
index d19aaf796..c8e69dac6 100644
--- a/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Display.java
+++ b/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Display.java
@@ -58,7 +58,7 @@ public class Display extends com.jogamp.newt.Display {
public Display() {
}
- protected void createNative() {
+ protected void createNativeImpl() {
synchronized(Display.class) {
if(0==initCounter) {
displayHandle = CreateDisplay();
@@ -71,7 +71,7 @@ public class Display extends com.jogamp.newt.Display {
aDevice = new DefaultGraphicsDevice(NativeWindowFactory.TYPE_DEFAULT, displayHandle);
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if(0==displayHandle) {
throw new NativeWindowException("displayHandle null; initCnt "+initCounter);
}
diff --git a/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Screen.java b/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Screen.java
index 3d9a5a309..3aded5df3 100644
--- a/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Screen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Screen.java
@@ -45,13 +45,13 @@ public class Screen extends com.jogamp.newt.Screen {
public Screen() {
}
- protected void createNative(int index) {
+ protected void createNativeImpl() {
AbstractGraphicsDevice adevice = getDisplay().getGraphicsDevice();
- GetScreenInfo(adevice.getHandle(), index);
- aScreen = new DefaultGraphicsScreen(adevice, index);
+ GetScreenInfo(adevice.getHandle(), idx);
+ aScreen = new DefaultGraphicsScreen(adevice, idx);
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
//----------------------------------------------------------------------
// Internals only
diff --git a/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Window.java b/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Window.java
index 14621807a..5f40a35ae 100644
--- a/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Window.java
+++ b/src/newt/classes/com/jogamp/newt/impl/intel/gdl/Window.java
@@ -67,7 +67,7 @@ public class Window extends com.jogamp.newt.Window {
}
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if(0!=surfaceHandle) {
synchronized(Window.class) {
CloseSurface(getDisplayHandle(), surfaceHandle);
diff --git a/src/newt/classes/com/jogamp/newt/impl/macosx/MacDisplay.java b/src/newt/classes/com/jogamp/newt/impl/macosx/MacDisplay.java
index 11f825282..9b8689114 100644
--- a/src/newt/classes/com/jogamp/newt/impl/macosx/MacDisplay.java
+++ b/src/newt/classes/com/jogamp/newt/impl/macosx/MacDisplay.java
@@ -65,31 +65,24 @@ public class MacDisplay extends Display {
dispatchMessages0();
}
- protected void createNative() {
+ protected void createNativeImpl() {
aDevice = new MacOSXGraphicsDevice();
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
- public EDTUtil getEDTUtil() {
- if( null == edtUtil ) {
- synchronized (this) {
- if( null == edtUtil ) {
- if(NewtFactory.useEDT()) {
- final Display f_dpy = this;
- MainThread.addPumpMessage(this,
- new Runnable() {
- public void run() {
- if(null!=f_dpy.getGraphicsDevice()) {
- f_dpy.dispatchMessages();
- } } } );
- edtUtil = MainThread.getSingleton();
- edtUtil.start();
- }
- }
- }
+ protected void createEDTUtil() {
+ if(NewtFactory.useEDT()) {
+ final Display f_dpy = this;
+ MainThread.addPumpMessage(this,
+ new Runnable() {
+ public void run() {
+ if(null!=f_dpy.getGraphicsDevice()) {
+ f_dpy.dispatchMessages();
+ } } } );
+ edtUtil = MainThread.getSingleton();
+ edtUtil.start();
}
- return edtUtil;
}
protected void releaseEDTUtil() {
diff --git a/src/newt/classes/com/jogamp/newt/impl/macosx/MacScreen.java b/src/newt/classes/com/jogamp/newt/impl/macosx/MacScreen.java
index d7deb13ee..317a3161c 100644
--- a/src/newt/classes/com/jogamp/newt/impl/macosx/MacScreen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/macosx/MacScreen.java
@@ -44,12 +44,12 @@ public class MacScreen extends Screen {
public MacScreen() {
}
- protected void createNative(int index) {
- aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), index);
- setScreenSize(getWidthImpl0(getIndex()), getHeightImpl0(getIndex()));
+ protected void createNativeImpl() {
+ aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), idx);
+ setScreenSize(getWidthImpl0(idx), getHeightImpl0(idx));
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
private static native int getWidthImpl0(int scrn_idx);
private static native int getHeightImpl0(int scrn_idx);
diff --git a/src/newt/classes/com/jogamp/newt/impl/macosx/MacWindow.java b/src/newt/classes/com/jogamp/newt/impl/macosx/MacWindow.java
index a8e6febf5..7571c05be 100644
--- a/src/newt/classes/com/jogamp/newt/impl/macosx/MacWindow.java
+++ b/src/newt/classes/com/jogamp/newt/impl/macosx/MacWindow.java
@@ -149,7 +149,7 @@ public class MacWindow extends Window {
}
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
nsViewLock.lock();
try {
if(DEBUG_IMPLEMENTATION) { System.out.println("MacWindow.CloseAction "+Thread.currentThread().getName()); }
diff --git a/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Display.java b/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Display.java
index c2d323e56..8b8ce1f41 100644
--- a/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Display.java
+++ b/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Display.java
@@ -56,7 +56,7 @@ public class Display extends com.jogamp.newt.Display {
public Display() {
}
- protected void createNative() {
+ protected void createNativeImpl() {
long handle = CreateDisplay(Screen.fixedWidth, Screen.fixedHeight);
if (handle == EGL.EGL_NO_DISPLAY) {
throw new NativeWindowException("BC EGL CreateDisplay failed");
@@ -64,7 +64,7 @@ public class Display extends com.jogamp.newt.Display {
aDevice = new EGLGraphicsDevice(handle);
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if (aDevice.getHandle() != EGL.EGL_NO_DISPLAY) {
DestroyDisplay(aDevice.getHandle());
}
diff --git a/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Screen.java b/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Screen.java
index e30896468..f38e7b4dc 100644
--- a/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Screen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Screen.java
@@ -45,12 +45,12 @@ public class Screen extends com.jogamp.newt.Screen {
public Screen() {
}
- protected void createNative(int index) {
- aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), index);
+ protected void createNativeImpl() {
+ aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), idx);
setScreenSize(fixedWidth, fixedHeight);
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
//----------------------------------------------------------------------
// Internals only
diff --git a/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Window.java b/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Window.java
index ca06699f5..d6b802a85 100644
--- a/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Window.java
+++ b/src/newt/classes/com/jogamp/newt/impl/opengl/broadcom/egl/Window.java
@@ -64,7 +64,7 @@ public class Window extends com.jogamp.newt.Window {
}
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if(0!=windowHandleClose) {
CloseWindow(getDisplayHandle(), windowHandleClose);
}
diff --git a/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDDisplay.java b/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDDisplay.java
index 2ab30773f..1845342a0 100644
--- a/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDDisplay.java
+++ b/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDDisplay.java
@@ -57,7 +57,7 @@ public class KDDisplay extends Display {
public KDDisplay() {
}
- protected void createNative() {
+ protected void createNativeImpl() {
// FIXME: map name to EGL_*_DISPLAY
long handle = EGL.eglGetDisplay(EGL.EGL_DEFAULT_DISPLAY);
if (handle == EGL.EGL_NO_DISPLAY) {
@@ -69,7 +69,7 @@ public class KDDisplay extends Display {
aDevice = new EGLGraphicsDevice(handle);
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if (aDevice.getHandle() != EGL.EGL_NO_DISPLAY) {
EGL.eglTerminate(aDevice.getHandle());
}
diff --git a/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDScreen.java b/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDScreen.java
index d570d9f5b..c7db047f6 100644
--- a/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDScreen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDScreen.java
@@ -44,11 +44,11 @@ public class KDScreen extends Screen {
public KDScreen() {
}
- protected void createNative(int index) {
- aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), index);
+ protected void createNativeImpl() {
+ aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), idx);
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
// elevate access to this package ..
protected void setScreenSize(int w, int h) {
diff --git a/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDWindow.java b/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDWindow.java
index 2f534548b..43e4ac021 100644
--- a/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDWindow.java
+++ b/src/newt/classes/com/jogamp/newt/impl/opengl/kd/KDWindow.java
@@ -78,7 +78,7 @@ public class KDWindow extends Window {
windowHandleClose = eglWindowHandle;
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if(0!=windowHandleClose) {
CloseWindow(windowHandleClose, windowUserData);
windowUserData=0;
diff --git a/src/newt/classes/com/jogamp/newt/impl/windows/WindowsDisplay.java b/src/newt/classes/com/jogamp/newt/impl/windows/WindowsDisplay.java
index ef033d1c8..cfc35e1f8 100644
--- a/src/newt/classes/com/jogamp/newt/impl/windows/WindowsDisplay.java
+++ b/src/newt/classes/com/jogamp/newt/impl/windows/WindowsDisplay.java
@@ -60,11 +60,11 @@ public class WindowsDisplay extends Display {
public WindowsDisplay() {
}
- protected void createNative() {
+ protected void createNativeImpl() {
aDevice = new WindowsGraphicsDevice();
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
// Can't do .. only at application shutdown
// UnregisterWindowClass0(getWindowClassAtom(), getHInstance());
}
diff --git a/src/newt/classes/com/jogamp/newt/impl/windows/WindowsScreen.java b/src/newt/classes/com/jogamp/newt/impl/windows/WindowsScreen.java
index 1b4be0d55..2197667cd 100644
--- a/src/newt/classes/com/jogamp/newt/impl/windows/WindowsScreen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/windows/WindowsScreen.java
@@ -45,12 +45,12 @@ public class WindowsScreen extends Screen {
public WindowsScreen() {
}
- protected void createNative(int index) {
- aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), index);
- setScreenSize(getWidthImpl0(getIndex()), getHeightImpl0(getIndex()));
+ protected void createNativeImpl() {
+ aScreen = new DefaultGraphicsScreen(getDisplay().getGraphicsDevice(), idx);
+ setScreenSize(getWidthImpl0(idx), getHeightImpl0(idx));
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
private native int getWidthImpl0(int scrn_idx);
private native int getHeightImpl0(int scrn_idx);
diff --git a/src/newt/classes/com/jogamp/newt/impl/windows/WindowsWindow.java b/src/newt/classes/com/jogamp/newt/impl/windows/WindowsWindow.java
index 69cd62201..15d9ac8b0 100644
--- a/src/newt/classes/com/jogamp/newt/impl/windows/WindowsWindow.java
+++ b/src/newt/classes/com/jogamp/newt/impl/windows/WindowsWindow.java
@@ -115,14 +115,14 @@ public class WindowsWindow extends Window {
}
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if (hdc != 0) {
if(windowHandleClose != 0) {
try {
ReleaseDC0(windowHandleClose, hdc);
} catch (Throwable t) {
if(DEBUG_IMPLEMENTATION) {
- Exception e = new Exception("closeNative failed - "+Thread.currentThread().getName(), t);
+ Exception e = new Exception("closeNativeImpl failed - "+Thread.currentThread().getName(), t);
e.printStackTrace();
}
}
@@ -134,7 +134,7 @@ public class WindowsWindow extends Window {
DestroyWindow0(windowHandleClose);
} catch (Throwable t) {
if(DEBUG_IMPLEMENTATION) {
- Exception e = new Exception("closeNative failed - "+Thread.currentThread().getName(), t);
+ Exception e = new Exception("closeNativeImpl failed - "+Thread.currentThread().getName(), t);
e.printStackTrace();
}
} finally {
diff --git a/src/newt/classes/com/jogamp/newt/impl/x11/X11Display.java b/src/newt/classes/com/jogamp/newt/impl/x11/X11Display.java
index 6701d6c8e..22b5e8470 100644
--- a/src/newt/classes/com/jogamp/newt/impl/x11/X11Display.java
+++ b/src/newt/classes/com/jogamp/newt/impl/x11/X11Display.java
@@ -61,26 +61,26 @@ public class X11Display extends Display {
public X11Display() {
}
- protected String validateDisplayName(String name, long handle) {
+ public String validateDisplayName(String name, long handle) {
return X11Util.validateDisplayName(name, handle);
}
- protected void createNative() {
- long handle = X11Util.createThreadLocalDisplay(name);
+ protected void createNativeImpl() {
+ long handle = X11Util.createDisplay(name);
if( 0 == handle ) {
throw new RuntimeException("Error creating display: "+name);
}
try {
CompleteDisplay0(handle);
} catch(RuntimeException e) {
- X11Util.closeThreadLocalDisplay(name);
+ X11Util.closeDisplay(handle);
throw e;
}
aDevice = new X11GraphicsDevice(handle);
}
- protected void closeNative() {
- X11Util.closeThreadLocalDisplay(name);
+ protected void closeNativeImpl() {
+ X11Util.closeDisplay(getHandle());
}
protected void dispatchMessagesNative() {
diff --git a/src/newt/classes/com/jogamp/newt/impl/x11/X11Screen.java b/src/newt/classes/com/jogamp/newt/impl/x11/X11Screen.java
index 453d8e5e1..aa53ea5d0 100644
--- a/src/newt/classes/com/jogamp/newt/impl/x11/X11Screen.java
+++ b/src/newt/classes/com/jogamp/newt/impl/x11/X11Screen.java
@@ -46,17 +46,17 @@ public class X11Screen extends Screen {
public X11Screen() {
}
- protected void createNative(int index) {
- long handle = GetScreen0(display.getHandle(), index);
+ protected void createNativeImpl() {
+ long handle = GetScreen0(display.getHandle(), idx);
if (handle == 0 ) {
- throw new RuntimeException("Error creating screen: "+index);
+ throw new RuntimeException("Error creating screen: "+idx);
}
- aScreen = new X11GraphicsScreen((X11GraphicsDevice)getDisplay().getGraphicsDevice(), index);
- setScreenSize(getWidth0(display.getHandle(), index),
- getHeight0(display.getHandle(), index));
+ aScreen = new X11GraphicsScreen((X11GraphicsDevice)getDisplay().getGraphicsDevice(), idx);
+ setScreenSize(getWidth0(display.getHandle(), idx),
+ getHeight0(display.getHandle(), idx));
}
- protected void closeNative() { }
+ protected void closeNativeImpl() { }
//----------------------------------------------------------------------
// Internals only
diff --git a/src/newt/classes/com/jogamp/newt/impl/x11/X11Window.java b/src/newt/classes/com/jogamp/newt/impl/x11/X11Window.java
index 7a770f770..894de9ae5 100644
--- a/src/newt/classes/com/jogamp/newt/impl/x11/X11Window.java
+++ b/src/newt/classes/com/jogamp/newt/impl/x11/X11Window.java
@@ -67,7 +67,7 @@ public class X11Window extends Window {
windowHandleClose = windowHandle;
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
if(0!=windowHandleClose && null!=getScreen() ) {
X11Display display = (X11Display) getScreen().getDisplay();
try {
@@ -75,7 +75,7 @@ public class X11Window extends Window {
display.getJavaObjectAtom(), display.getWindowDeleteAtom());
} catch (Throwable t) {
if(DEBUG_IMPLEMENTATION) {
- Exception e = new Exception("closeNative failed - "+Thread.currentThread().getName(), t);
+ Exception e = new Exception("closeNativeImpl failed - "+Thread.currentThread().getName(), t);
e.printStackTrace();
}
} finally {
diff --git a/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java b/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java
index 99b4314a3..2aca37cab 100644
--- a/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java
+++ b/src/newt/classes/com/jogamp/newt/opengl/GLWindow.java
@@ -82,8 +82,8 @@ public class GLWindow extends Window implements GLAutoDrawable {
if( !windowIsLocked() && null == getAnimator() ) {
destroy();
} else {
- sendDestroy = true;
- }
+ sendDestroy = true;
+ }
}
});
}
@@ -125,12 +125,12 @@ public class GLWindow extends Window implements GLAutoDrawable {
return new GLWindow(window);
}
- public boolean isNativeWindowValid() {
- return (null!=window)?window.isNativeWindowValid():false;
+ public boolean isNativeValid() {
+ return (null!=window)?window.isNativeValid():false;
}
- public boolean isDestroyed() {
- return (null!=window)?window.isDestroyed():true;
+ public boolean isValid() {
+ return (null!=window)?window.isValid():true;
}
public final Window getInnerWindow() {
@@ -145,7 +145,7 @@ public class GLWindow extends Window implements GLAutoDrawable {
shouldNotCallThis();
}
- protected void closeNative() {
+ protected void closeNativeImpl() {
shouldNotCallThis();
}
@@ -158,23 +158,23 @@ public class GLWindow extends Window implements GLAutoDrawable {
private DisposeAction disposeAction = new DisposeAction();
class DestroyAction implements Runnable {
- boolean deep;
- public DestroyAction(boolean deep) {
- this.deep = deep;
+ boolean unrecoverable;
+ public DestroyAction(boolean unrecoverable) {
+ this.unrecoverable = unrecoverable;
}
public void run() {
// Lock: Have to cover whole workflow (dispose all, context, drawable and window)
windowLock();
try {
- if( isDestroyed() ) {
+ if( !isValid() ) {
return; // nop
}
if(Window.DEBUG_WINDOW_EVENT || window.DEBUG_IMPLEMENTATION) {
- Exception e1 = new Exception("GLWindow.destroy("+deep+") "+Thread.currentThread()+", start: "+GLWindow.this);
+ Exception e1 = new Exception("GLWindow.destroy("+unrecoverable+") "+Thread.currentThread()+", start: "+GLWindow.this);
e1.printStackTrace();
}
- if( window.isNativeWindowValid() && null != drawable && drawable.isRealized() ) {
+ if( window.isNativeValid() && null != drawable && drawable.isRealized() ) {
if( null != context && context.isCreated() ) {
// Catch dispose GLExceptions by GLEventListener, just 'print' them
// so we can continue with the destruction.
@@ -193,14 +193,14 @@ public class GLWindow extends Window implements GLAutoDrawable {
}
if(null!=window) {
- window.destroy(deep);
+ window.destroy(unrecoverable);
}
- if(deep) {
+ if(unrecoverable) {
helper=null;
}
if(Window.DEBUG_WINDOW_EVENT || window.DEBUG_IMPLEMENTATION) {
- System.out.println("GLWindow.destroy("+deep+") "+Thread.currentThread()+", fin: "+GLWindow.this);
+ System.out.println("GLWindow.destroy("+unrecoverable+") "+Thread.currentThread()+", fin: "+GLWindow.this);
}
} finally {
windowUnlock();
@@ -208,15 +208,9 @@ public class GLWindow extends Window implements GLAutoDrawable {
}
}
- /**
- * @param deep If true, all resources, ie listeners, parent handles, size, position
- * and the referenced NEWT screen and display, will be destroyed as well. Be aware that if you call
- * this method with deep = true, you will not be able to regenerate the Window.
- * @see #destroy()
- */
- public void destroy(boolean deep) {
- if( !isDestroyed() ) {
- runOnEDTIfAvail(true, new DestroyAction(deep));
+ public void destroy(boolean unrecoverable) {
+ if( isValid() ) {
+ runOnEDTIfAvail(true, new DestroyAction(unrecoverable));
}
}
@@ -269,7 +263,7 @@ public class GLWindow extends Window implements GLAutoDrawable {
}
public void setVisible(boolean visible) {
- if(!isDestroyed()) {
+ if(isValid()) {
runOnEDTIfAvail(true, new VisibleAction(visible));
}
}
@@ -512,17 +506,17 @@ public class GLWindow extends Window implements GLAutoDrawable {
if( null == window ) { return; }
if(sendDestroy || ( null!=window && window.hasDeviceChanged() && GLAutoDrawable.SCREEN_CHANGE_ACTION_ENABLED ) ) {
- sendDestroy=false;
- destroy();
- return;
- }
+ sendDestroy=false;
+ destroy();
+ return;
+ }
if( null == context && window.isVisible() ) {
// retry native window and drawable/context creation
setVisible(true);
}
- if( window.isVisible() && window.isNativeWindowValid() && null != context ) {
+ if( window.isVisible() && window.isNativeValid() && null != context ) {
if(forceReshape) {
sendReshape = true;
}
diff --git a/src/newt/classes/com/jogamp/newt/util/DefaultEDTUtil.java b/src/newt/classes/com/jogamp/newt/util/DefaultEDTUtil.java
index 87dfdb9d8..96bfc50e0 100644
--- a/src/newt/classes/com/jogamp/newt/util/DefaultEDTUtil.java
+++ b/src/newt/classes/com/jogamp/newt/util/DefaultEDTUtil.java
@@ -47,8 +47,8 @@ public class DefaultEDTUtil implements EDTUtil {
private ThreadGroup threadGroup;
private volatile boolean shouldStop = false;
private EventDispatchThread edt = null;
- private Object edtLock = new Object();
- private ArrayList tasks = new ArrayList(); // one shot tasks
+ private Object edtLock = new Object(); // locking the EDT start/stop state
+ private ArrayList edtTasks = new ArrayList(); // one shot tasks
private String name;
private Runnable pumpMessages;
@@ -56,123 +56,137 @@ public class DefaultEDTUtil implements EDTUtil {
this.threadGroup = tg;
this.name=new String(Thread.currentThread().getName()+"-"+"EDT-"+name);
this.pumpMessages=pumpMessages;
+ this.edt = new EventDispatchThread(threadGroup, name);
}
- public void start() {
+ public final void reset() {
synchronized(edtLock) {
- if(null==edt) {
- edt = new EventDispatchThread(threadGroup, name);
+ waitUntilStopped();
+ if(edtTasks.size()>0) {
+ throw new RuntimeException("Remaining EDTTasks: "+edtTasks.size());
}
+ this.edt = new EventDispatchThread(threadGroup, name);
+ }
+ }
+
+ public final void start() {
+ synchronized(edtLock) {
if(!edt.isRunning()) {
shouldStop = false;
edt.start();
+ if(DEBUG) {
+ System.out.println(Thread.currentThread()+": EDT START");
+ }
}
- edtLock.notifyAll();
}
}
- public void stop() {
+ public final void stop() {
synchronized(edtLock) {
- if(null!=edt && edt.isRunning()) {
+ if(edt.isRunning()) {
shouldStop = true;
+ if(DEBUG) {
+ System.out.println(Thread.currentThread()+": EDT signal STOP");
+ }
}
edtLock.notifyAll();
- if(DEBUG) {
- System.out.println(Thread.currentThread()+": EDT signal STOP");
- }
}
}
- public boolean isCurrentThreadEDT() {
- return null!=edt && edt == Thread.currentThread();
- }
-
- public boolean isRunning() {
- return null!=edt && edt.isRunning() ;
+ public final boolean isCurrentThreadEDT() {
+ return edt == Thread.currentThread();
}
- private void invokeLater(Runnable task) {
- synchronized(edtLock) {
- if(null!=edt && edt.isRunning() && edt != Thread.currentThread() ) {
- tasks.add(task);
- edtLock.notifyAll();
- } else {
- // if !running or isEDTThread, do it right away
- task.run();
- }
- }
+ public final boolean isRunning() {
+ return !shouldStop && edt.isRunning() ;
}
public void invoke(boolean wait, Runnable task) {
if(task == null) {
return;
}
- boolean doWait = wait && null!=edt && edt.isRunning() && edt != Thread.currentThread();
- Object lock = new Object();
- RunnableTask rTask = new RunnableTask(task, doWait?lock:null, true);
Throwable throwable = null;
- synchronized(lock) {
- invokeLater(rTask);
- if( doWait ) {
+ RunnableTask rTask = null;
+ Object rTaskLock = new Object();
+ synchronized(rTaskLock) { // lock the optional task execution
+ synchronized(edtLock) { // lock the EDT status
+ start(); // start if not started yet
+ if(isRunning() && edt != Thread.currentThread() ) {
+ rTask = new RunnableTask(task, wait?rTaskLock:null, true);
+ synchronized(edtTasks) {
+ edtTasks.add(rTask);
+ edtTasks.notifyAll();
+ }
+ } else {
+ // if !running or isEDTThread, do it right away
+ wait = false;
+ task.run();
+ }
+ }
+ // wait until task finished, if requested
+ // and no stop() call slipped through.
+ if( wait && !shouldStop ) {
try {
- lock.wait();
+ rTaskLock.wait();
} catch (InterruptedException ie) {
throwable = ie;
}
+ if(null==throwable) {
+ throwable = rTask.getThrowable();
+ }
+ if(null!=throwable) {
+ throw new RuntimeException(throwable);
+ }
}
}
- if(null==throwable) {
- throwable = rTask.getThrowable();
- }
- if(null!=throwable) {
- throw new RuntimeException(throwable);
- }
}
public void waitUntilIdle() {
- synchronized(edtLock) {
- if(null!=edt && edt.isRunning() && tasks.size()>0 && edt != Thread.currentThread() ) {
- try {
- edtLock.wait();
- } catch (InterruptedException e) {
- e.printStackTrace();
+ if(edt.isRunning() && edt != Thread.currentThread()) {
+ synchronized(edtTasks) {
+ while(edt.isRunning() && edtTasks.size()>0) {
+ try {
+ edtTasks.wait();
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
}
}
}
}
public void waitUntilStopped() {
- synchronized(edtLock) {
- while(null!=edt && edt.isRunning() && edt != Thread.currentThread() ) {
- try {
- edtLock.wait();
- } catch (InterruptedException e) {
- e.printStackTrace();
+ if(edt.isRunning() && edt != Thread.currentThread() ) {
+ synchronized(edtLock) {
+ while(edt.isRunning()) {
+ try {
+ edtLock.wait();
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
}
}
}
}
class EventDispatchThread extends Thread {
- boolean isRunning = false;
+ volatile boolean isRunning = false;
public EventDispatchThread(ThreadGroup tg, String name) {
super(tg, name);
}
- public synchronized boolean isRunning() {
+ public final boolean isRunning() {
return isRunning;
}
public void start() throws IllegalThreadStateException {
- synchronized(this) {
- isRunning = true;
- }
+ isRunning = true;
super.start();
}
/**
- * Utilizing edtLock only for local resources and task execution,
+ * Utilizing locking only on edtTasks and its execution,
* not for event dispatching.
*/
public void run() {
@@ -180,41 +194,39 @@ public class DefaultEDTUtil implements EDTUtil {
System.out.println(Thread.currentThread()+": EDT run() START");
}
try {
- while(!shouldStop) {
- // wait for something todo
- while(!shouldStop && tasks.size()==0) {
- synchronized(edtLock) {
- if(!shouldStop && tasks.size()==0) {
- try {
- edtLock.wait(defaultEDTPollGranularity);
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- }
- }
- pumpMessages.run(); // event dispatch
+ do {
+ // event dispatch
+ if(!shouldStop) {
+ pumpMessages.run();
}
- if(!shouldStop && tasks.size()>0) {
- synchronized(edtLock) {
- if(!shouldStop && tasks.size()>0) {
- Runnable task = (Runnable) tasks.remove(0);
- task.run(); // FIXME: could be run outside of lock
- edtLock.notifyAll();
+ // wait and work on tasks
+ synchronized(edtTasks) {
+ // wait for tasks
+ while(!shouldStop && edtTasks.size()==0) {
+ try {
+ edtTasks.wait(defaultEDTPollGranularity);
+ } catch (InterruptedException e) {
+ e.printStackTrace();
}
}
- pumpMessages.run(); // event dispatch
+ // execute one task, if available
+ if(edtTasks.size()>0) {
+ Runnable task = (Runnable) edtTasks.remove(0);
+ task.run();
+ edtTasks.notifyAll();
+ }
}
- }
+ } while(!shouldStop || edtTasks.size()>0) ;
} catch (Throwable t) {
// handle errors ..
shouldStop = true;
throw new RuntimeException(t);
} finally {
- synchronized(this) {
+ // check for tasks
+ // sync for waitUntilStopped()
+ synchronized(edtLock) {
isRunning = !shouldStop;
- }
- if(!isRunning) {
- synchronized(edtLock) {
+ if(!isRunning) {
edtLock.notifyAll();
}
}
diff --git a/src/newt/classes/com/jogamp/newt/util/EDTUtil.java b/src/newt/classes/com/jogamp/newt/util/EDTUtil.java
index 1af102f43..91f35459b 100644
--- a/src/newt/classes/com/jogamp/newt/util/EDTUtil.java
+++ b/src/newt/classes/com/jogamp/newt/util/EDTUtil.java
@@ -44,6 +44,8 @@ public interface EDTUtil {
public static final long defaultEDTPollGranularity = 10; // 10ms, 1/100s
+ public void reset();
+
public void start();
public void stop();
@@ -52,6 +54,7 @@ public interface EDTUtil {
public boolean isRunning();
+ /** Shall start the thread if not running */
public void invoke(boolean wait, Runnable task);
public void waitUntilIdle();
diff --git a/src/newt/classes/com/jogamp/newt/util/MainThread.java b/src/newt/classes/com/jogamp/newt/util/MainThread.java
index ba886ade8..cb5c87a89 100644
--- a/src/newt/classes/com/jogamp/newt/util/MainThread.java
+++ b/src/newt/classes/com/jogamp/newt/util/MainThread.java
@@ -243,6 +243,10 @@ public class MainThread implements EDTUtil {
}
}
+ public void reset() {
+ // nop
+ }
+
public void start() {
// nop
}