From 56d60b36798fa8dae48bf2aa5e2de6f3178ab0d1 Mon Sep 17 00:00:00 2001
From: Sven Gothel
Date: Mon, 26 May 2014 18:54:27 +0200
Subject: Bug 741 HiDPI: Refine Monitor/Screen [virtual] Viewport Definition /
Add NEWT Support / Fix JAWT getPixelScale deadlock
- NativeWindow/Surface/NEWT API DOC: Define Coordinate System of Window and Screen
- OSXUtil: Add getPixelScale(..) via Screen index and 'windowOrView'
- JAWTWindow/JAWTUtil.getPixelScale(..): Use pre-fetched AWT GraphicsConfiguration to solve AWT-TreeLock (deadlock)
- [Virtual] Viewport of MonitorDevice and Screen:
- Properly calculate and expose [virtual] viewport in window and pixel units
- OSX Monitor viewports in pixel units are 'reconstructed'
- Window/Viewport to Monitor selection shall be perfomed via window units (unique)
- OSX NEWT Window create/init (native): Use given size and coordinates even in fullscreen mode
Don't override by quering NSScreen coordinates, trust given values.
- Fix test cases, i.e. usage of pixel- and window-units
---
.../classes/javax/media/opengl/awt/GLJPanel.java | 2 +-
.../com/jogamp/nativewindow/awt/JAWTWindow.java | 2 +-
.../javax/media/nativewindow/NativeSurface.java | 4 +-
.../javax/media/nativewindow/NativeWindow.java | 65 ++++++---
.../classes/jogamp/nativewindow/jawt/JAWTUtil.java | 20 +--
.../jogamp/nativewindow/macosx/OSXUtil.java | 10 ++
src/nativewindow/native/macosx/OSXmisc.m | 71 +++++++++-
.../classes/com/jogamp/newt/MonitorDevice.java | 97 ++++++++------
src/newt/classes/com/jogamp/newt/Screen.java | 52 +++++---
src/newt/classes/com/jogamp/newt/Window.java | 23 +++-
.../classes/jogamp/newt/MonitorDeviceImpl.java | 11 +-
src/newt/classes/jogamp/newt/MonitorModeProps.java | 19 ++-
src/newt/classes/jogamp/newt/ScreenImpl.java | 66 +++++----
src/newt/classes/jogamp/newt/WindowImpl.java | 26 ++--
.../jogamp/newt/driver/android/WindowDriver.java | 3 +-
.../classes/jogamp/newt/driver/awt/AWTCanvas.java | 6 +-
.../jogamp/newt/driver/awt/WindowDriver.java | 11 ++
.../jogamp/newt/driver/bcm/egl/ScreenDriver.java | 4 +-
.../jogamp/newt/driver/bcm/vc/iv/ScreenDriver.java | 4 +-
.../jogamp/newt/driver/bcm/vc/iv/WindowDriver.java | 6 +-
.../jogamp/newt/driver/intel/gdl/ScreenDriver.java | 4 +-
.../jogamp/newt/driver/kd/ScreenDriver.java | 4 +-
.../jogamp/newt/driver/macosx/ScreenDriver.java | 148 ++++++++++++++++-----
.../jogamp/newt/driver/macosx/WindowDriver.java | 117 +++++++++++++---
.../jogamp/newt/driver/windows/ScreenDriver.java | 26 ++--
.../jogamp/newt/driver/x11/ScreenDriver.java | 24 ++--
src/newt/native/MacWindow.m | 133 +++++++++++-------
src/newt/native/NewtMacWindow.h | 5 +
src/newt/native/NewtMacWindow.m | 39 +++++-
src/newt/native/ScreenMode.h | 3 +-
src/newt/native/WindowsWindow.c | 12 +-
src/newt/native/X11RandR13.c | 12 +-
.../opengl/test/android/MovieSimpleActivity1.java | 2 +-
.../test/junit/graph/demos/GPURegionNewtDemo.java | 20 ++-
.../test/junit/graph/demos/GPUTextNewtDemo.java | 20 ++-
.../test/junit/graph/demos/GPUUISceneNewtDemo.java | 19 ++-
.../test/junit/graph/demos/ui/UINewtDemo01.java | 2 +-
...estGLAutoDrawableDelegateOnOffscrnCapsNEWT.java | 113 ++++++++--------
...TestGLAutoDrawableGLCanvasOnOffscrnCapsAWT.java | 95 +++++++------
...estGLAutoDrawableGLWindowOnOffscrnCapsNEWT.java | 125 +++++++++--------
...LAutoDrawableNewtCanvasAWTOnOffscrnCapsAWT.java | 107 ++++++++-------
.../test/junit/jogl/acore/TestGPUMemSec01NEWT.java | 144 ++++++++++----------
.../jogl/awt/ManualHiDPIBufferedImage01AWT.java | 71 ++++++++++
.../test/junit/jogl/demos/es2/av/MovieCube.java | 2 +-
.../test/junit/jogl/demos/es2/av/MovieSimple.java | 2 +-
.../junit/jogl/demos/es2/awt/TestGearsES2AWT.java | 122 +++++++++++------
.../demos/es2/awt/TestGearsES2GLJPanelAWT.java | 38 +++++-
.../jogl/demos/es2/newt/TestGearsES2NEWT.java | 10 +-
.../demos/gl2/newt/TestGearsNewtAWTWrapper.java | 35 +++--
...TestSwingAWTRobotUsageBeforeJOGLInitBug411.java | 4 +-
.../junit/newt/TestDisplayLifecycle02NEWT.java | 4 +-
.../junit/newt/TestGLWindows02NEWTAnimated.java | 5 +-
.../junit/newt/mm/ManualScreenMode03aNEWT.java | 31 +++--
.../test/junit/newt/mm/TestScreenMode00aNEWT.java | 45 ++++---
.../test/junit/newt/mm/TestScreenMode00cNEWT.java | 81 +++++++----
.../test/junit/newt/mm/TestScreenMode01aNEWT.java | 100 +++++++++-----
.../test/junit/newt/mm/TestScreenMode01bNEWT.java | 24 ++--
.../test/junit/newt/mm/TestScreenMode01cNEWT.java | 47 ++++---
.../test/junit/newt/mm/TestScreenMode01dNEWT.java | 44 +++---
.../junit/newt/parenting/TestParenting02NEWT.java | 8 +-
60 files changed, 1550 insertions(+), 799 deletions(-)
create mode 100644 src/test/com/jogamp/opengl/test/junit/jogl/awt/ManualHiDPIBufferedImage01AWT.java
(limited to 'src')
diff --git a/src/jogl/classes/javax/media/opengl/awt/GLJPanel.java b/src/jogl/classes/javax/media/opengl/awt/GLJPanel.java
index 65b61d3aa..c8102973f 100644
--- a/src/jogl/classes/javax/media/opengl/awt/GLJPanel.java
+++ b/src/jogl/classes/javax/media/opengl/awt/GLJPanel.java
@@ -563,7 +563,7 @@ public class GLJPanel extends JPanel implements AWTGLAutoDrawable, WindowClosing
super.addNotify();
awtWindowClosingProtocol.addClosingListener();
{
- final int s = JAWTUtil.getPixelScale(this);
+ final int s = JAWTUtil.getPixelScale(getGraphicsConfiguration());
pixelScale = 0 < s ? s : 1;
}
if (DEBUG) {
diff --git a/src/nativewindow/classes/com/jogamp/nativewindow/awt/JAWTWindow.java b/src/nativewindow/classes/com/jogamp/nativewindow/awt/JAWTWindow.java
index 24bc8fa51..d4f058201 100644
--- a/src/nativewindow/classes/com/jogamp/nativewindow/awt/JAWTWindow.java
+++ b/src/nativewindow/classes/com/jogamp/nativewindow/awt/JAWTWindow.java
@@ -271,7 +271,7 @@ public abstract class JAWTWindow implements NativeWindow, OffscreenLayerSurface,
final Rectangle jb = new Rectangle(jawtBounds.getX(), jawtBounds.getY(), jawtBounds.getWidth(), jawtBounds.getHeight());
final int newPixelScale;
{
- final int s = JAWTUtil.getPixelScale(component);
+ final int s = JAWTUtil.getPixelScale(config.getAWTGraphicsConfiguration());
newPixelScale = 0 < s ? s : 1;
}
final boolean changedBounds = !bounds.equals(jb);
diff --git a/src/nativewindow/classes/javax/media/nativewindow/NativeSurface.java b/src/nativewindow/classes/javax/media/nativewindow/NativeSurface.java
index f8596bc74..8131ee283 100644
--- a/src/nativewindow/classes/javax/media/nativewindow/NativeSurface.java
+++ b/src/nativewindow/classes/javax/media/nativewindow/NativeSurface.java
@@ -32,8 +32,8 @@ package javax.media.nativewindow;
* Provides low-level information required for
* hardware-accelerated rendering using a surface in a platform-independent manner.
*
- * All values of this interface are represented in pixel units,
- * see {@link NativeWindow}.
+ * All values of this interface are represented in pixel units, if not stated otherwise.
+ * See {@link NativeWindow}.
*
*
* A NativeSurface created for a particular on- or offscreen component is
diff --git a/src/nativewindow/classes/javax/media/nativewindow/NativeWindow.java b/src/nativewindow/classes/javax/media/nativewindow/NativeWindow.java
index 242f25d43..63a643f3c 100644
--- a/src/nativewindow/classes/javax/media/nativewindow/NativeWindow.java
+++ b/src/nativewindow/classes/javax/media/nativewindow/NativeWindow.java
@@ -48,8 +48,18 @@ import javax.media.nativewindow.util.Point;
* information such as {@link #getWindowHandle() window-handle},
* {@link #getWindowWidth() window-size} and {@link #getX() window-position}.
*
- * All values of this interface are represented in window units.
- * see {@link NativeSurface}.
+ * All values of this interface are represented in window units, if not stated otherwise.
+ * See {@link NativeSurface}.
+ *
Abstract screen space has it's origin in the top-left corner, and may not be at 0/0.
+ *
Window origin is in it's top-left corner, see {@link #getX()} and {@link #getY()}.
+ *
Window client-area excludes {@link #getInsets() insets}, i.e. window decoration.
+ *
Window origin is relative to it's parent window if exist, or the screen position (top-level).
+ *
*
*
* A window toolkit such as the AWT may either implement this interface
@@ -111,18 +121,36 @@ public interface NativeWindow extends NativeSurface {
/** Returns the current x position of this window, relative to it's parent. */
/**
- * @return the current x position of the top-left corner
- * of the client area relative to it's parent in window units.
- * Since the position reflects the client area, it does not include the insets.
+ * Returns the x position of the top-left corner
+ * of the client area relative to it's parent in window units.
+ *
+ * If no parent exist (top-level window), this coordinate equals the screen coordinate.
+ *
+ *
+ * Since the position reflects the client area, it does not include the insets.
+ *
* @see #getInsets()
+ * @see #getLocationOnScreen(Point)
*/
public int getX();
/**
- * @return the current y position of the top-left corner
- * of the client area relative to it's parent in window units.
- * Since the position reflects the client area, it does not include the insets.
+ * Returns the current y position of the top-left corner
+ * of the client area relative to it's parent in window units.
+ *
+ * If no parent exist (top-level window), this coordinate equals the screen coordinate.
+ *
+ *
+ * Since the position reflects the client area, it does not include the insets.
+ *
* @see #getInsets()
+ * @see #getLocationOnScreen(Point)
*/
public int getY();
@@ -141,16 +169,23 @@ public interface NativeWindow extends NativeSurface {
public int getWindowHeight();
/**
- * Returns the current position of the top-left corner
- * of the client area in window units.
+ * Returns the window's top-left client-area position in the screen.
+ *
+ * If {@link Point} is not null, it is translated about the resulting screen position
+ * and returned.
+ *
* Since the position reflects the client area, it does not include the insets.
*
- * @param point if not null,
- * {@link javax.media.nativewindow.util.Point#translate(javax.media.nativewindow.util.Point)}
- * the passed {@link javax.media.nativewindow.util.Point} by this location on the screen and return it.
- * @return either the passed non null translated point by the screen location of this NativeWindow,
- * or a new instance with the screen location of this NativeWindow.
+ * @param point Optional {@link Point} storage.
+ * If not null, null, it is translated about the resulting screen position
+ * and returned.
+ * @see #getX()
+ * @see #getY()
+ * @see #getInsets()
*/
public Point getLocationOnScreen(Point point);
diff --git a/src/nativewindow/classes/jogamp/nativewindow/jawt/JAWTUtil.java b/src/nativewindow/classes/jogamp/nativewindow/jawt/JAWTUtil.java
index 387f40f89..92ec27b69 100644
--- a/src/nativewindow/classes/jogamp/nativewindow/jawt/JAWTUtil.java
+++ b/src/nativewindow/classes/jogamp/nativewindow/jawt/JAWTUtil.java
@@ -37,7 +37,6 @@
package jogamp.nativewindow.jawt;
-import java.awt.Component;
import java.awt.EventQueue;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
@@ -560,10 +559,9 @@ public class JAWTUtil {
}
/**
- * Returns the pixel scale factor of the given {@link Component}'s {@link GraphicsDevice}, if supported.
+ * Returns the pixel scale factor of the given {@link GraphicsConfiguration}'s {@link GraphicsDevice}, if supported.
*
- * If the component is not yet {@link Component#isDisplayable() displayable},
- * zero is returned.
+ * If the {@link GraphicsDevice} is null, zero is returned.
*
*
* If the component does not support pixel scaling the default
@@ -572,17 +570,21 @@ public class JAWTUtil {
*
* Note: Currently only supported on OSX since 1.7.0_40 for HiDPI retina displays
*
+ * All values of this interface are represented in pixel units, if not stated otherwise.
+ *
*/
public abstract class MonitorDevice {
protected final Screen screen; // backref
@@ -61,16 +64,18 @@ public abstract class MonitorDevice {
protected final ArrayHashSet supportedModes; // FIXME: May need to support mutable mode, i.e. adding modes on the fly!
protected MonitorMode currentMode;
protected boolean modeChanged;
- protected Rectangle viewport;
+ protected Rectangle viewportPU; // in pixel units
+ protected Rectangle viewportWU; // in window units
- protected MonitorDevice(Screen screen, int nativeId, DimensionImmutable sizeMM, Rectangle viewport, MonitorMode currentMode, ArrayHashSet supportedModes) {
+ protected MonitorDevice(Screen screen, int nativeId, DimensionImmutable sizeMM, Rectangle viewportPU, Rectangle viewportWU, MonitorMode currentMode, ArrayHashSet supportedModes) {
this.screen = screen;
this.nativeId = nativeId;
this.sizeMM = sizeMM;
this.originalMode = currentMode;
this.supportedModes = supportedModes;
this.currentMode = currentMode;
- this.viewport = viewport;
+ this.viewportPU = viewportPU;
+ this.viewportWU = viewportWU;
this.modeChanged = false;
}
@@ -170,11 +175,22 @@ public abstract class MonitorDevice {
/**
* Returns the {@link RectangleImmutable rectangular} portion
- * of the rotated virtual {@link Screen} size in pixel units
- * represented by this monitor.
+ * of the rotated virtual {@link Screen} size in pixel units
+ * represented by this monitor, i.e. top-left origin and size.
+ * @see Screen
*/
public final RectangleImmutable getViewport() {
- return viewport;
+ return viewportPU;
+ }
+
+ /**
+ * Returns the {@link RectangleImmutable rectangular} portion
+ * of the rotated virtual {@link Screen} size in window units
+ * represented by this monitor, i.e. top-left origin and size.
+ * @see Screen
+ */
+ public final RectangleImmutable getViewportInWindowUnits() {
+ return viewportWU;
}
/**
@@ -184,46 +200,45 @@ public abstract class MonitorDevice {
* @param y y-coord in pixel units
*/
public final boolean contains(final int x, final int y) {
- return x >= viewport.getX() &&
- x < viewport.getX() + viewport.getWidth() &&
- y >= viewport.getY() &&
- y < viewport.getY() + viewport.getHeight() ;
+ return x >= viewportPU.getX() &&
+ x < viewportPU.getX() + viewportPU.getWidth() &&
+ y >= viewportPU.getY() &&
+ y < viewportPU.getY() + viewportPU.getHeight() ;
}
/**
- * Returns the coverage of given rectangle in pixel units
- * w/ this {@link #getViewport() viewport}, i.e. between 0.0 and 1.0.
- *
Screen space has it's origin in the top-left corner, and may not be at 0/0.
+ *
{@link #getViewport() Virtual viewport} covers all {@link MonitorDevice}s {@link MonitorDevice#getViewport() viewports} and has it's origin in the top-left corner, and may not be at 0/0.
+ *
+ *
+*/
public abstract class Screen {
/**
@@ -131,11 +144,15 @@ public abstract class Screen {
public abstract int getIndex();
/**
+ * See Coordinate System.
+ *
* @return the x position of the virtual viewport's top-left origin in pixel units.
*/
public abstract int getX();
/**
+ * See Coordinate System.
+ *
* @return the y position of the virtual viewport's top-left origin in pixel units.
*/
public abstract int getY();
@@ -151,20 +168,20 @@ public abstract class Screen {
public abstract int getHeight();
/**
- * @return the rotated virtual viewport, i.e. origin and size in pixel units.
- * @see #getViewportInWindowUnits(Window)
+ * See Coordinate System.
+ *
+ * @return the rotated virtual viewport, i.e. top-left origin and size, in pixel units.
+ * @see #getViewportInWindowUnits()
*/
public abstract RectangleImmutable getViewport();
/**
- * Returns a newly created {@link Rectangle} containing the rotated virtual viewport
- * in window units of the given {@link Window} instance.
- * @return rotated viewport values, i.e. origin and size, in pixel units.
+ * See Coordinate System.
+ *
+ * @return the rotated virtual viewport, i.e. top-left origin and size, in window units.
* @see #getViewport()
*/
- public final Rectangle getViewportInWindowUnits(final Window win) {
- return win.convertToWindowUnits( (Rectangle) getViewport().cloneMutable() );
- }
+ public abstract RectangleImmutable getViewportInWindowUnits();
/**
* @return the associated Display
@@ -192,12 +209,12 @@ public abstract class Screen {
public abstract List getMonitorDevices();
/**
- * Returns the {@link MonitorDevice} with the highest {@link MonitorDevice#getViewport() viewport}
- * {@link MonitorDevice#coverage(RectangleImmutable) coverage} of the given rectangle in pixel units.
+ * Returns the {@link MonitorDevice} with the highest {@link MonitorDevice#getViewportInWindowUnits() viewport}
+ * {@link RectangleImmutable#coverage(RectangleImmutable) coverage} of the given rectangle in window units.
*
* If no coverage is detected the first {@link MonitorDevice} is returned.
*
- * @param r arbitrary rectangle in pixel units
+ * @param r arbitrary rectangle in window units
*/
public final MonitorDevice getMainMonitor(final RectangleImmutable r) {
MonitorDevice res = null;
@@ -205,7 +222,7 @@ public abstract class Screen {
final List monitors = getMonitorDevices();
for(int i=monitors.size()-1; i>=0; i--) {
final MonitorDevice monitor = monitors.get(i);
- final float coverage = monitor.coverage(r);
+ final float coverage = monitor.getViewportInWindowUnits().coverage(r);
if( coverage > maxCoverage ) {
maxCoverage = coverage;
res = monitor;
@@ -218,15 +235,16 @@ public abstract class Screen {
}
/**
- * Returns the union of all monitor's {@link MonitorDevice#getViewport() viewport} in pixel units.
+ * Calculates the union of all monitor's {@link MonitorDevice#getViewport() viewport} in pixel- and window units.
*
* Should be equal to {@link #getX()}, {@link #getY()}, {@link #getWidth()} and {@link #getHeight()},
* however, some native toolkits may choose a different virtual screen area.
*
- * @param result storage for result, will be returned
+ * @param viewport storage for result in pixel units, maybe null
+ * @param viewportInWindowUnits storage for result in window units, maybe null
*/
- public final Rectangle unionOfMonitorViewportSize(final Rectangle result) {
- return MonitorDevice.unionOfViewports(result, getMonitorDevices());
+ public final void unionOfMonitorViewports(final Rectangle viewport, final Rectangle viewportInWindowUnits) {
+ MonitorDevice.unionOfViewports(viewport, viewportInWindowUnits, getMonitorDevices());
}
/**
diff --git a/src/newt/classes/com/jogamp/newt/Window.java b/src/newt/classes/com/jogamp/newt/Window.java
index 872d67087..57fcb626d 100644
--- a/src/newt/classes/com/jogamp/newt/Window.java
+++ b/src/newt/classes/com/jogamp/newt/Window.java
@@ -46,7 +46,6 @@ import javax.media.nativewindow.CapabilitiesChooser;
import javax.media.nativewindow.CapabilitiesImmutable;
import javax.media.nativewindow.NativeWindow;
import javax.media.nativewindow.WindowClosingProtocol;
-import javax.media.nativewindow.util.Point;
import javax.media.nativewindow.util.Rectangle;
import javax.media.nativewindow.util.RectangleImmutable;
@@ -65,6 +64,20 @@ import javax.media.nativewindow.util.RectangleImmutable;
* window operation to an instance of this interface while providing OpenGL
* functionality.
*
+ *
+ * All values of this interface are represented in window units, if not stated otherwise.
+ *
* Custom window icons can be defined via system property newt.window.icons,
@@ -108,8 +121,8 @@ public interface Window extends NativeWindow, WindowClosingProtocol {
Screen getScreen();
/**
- * Returns the {@link MonitorDevice} which {@link MonitorDevice#getViewport() viewport}
- * {@link MonitorDevice#coverage(RectangleImmutable) covers} this window the most.
+ * Returns the {@link MonitorDevice} with the highest {@link MonitorDevice#getViewportInWindowUnits() viewport}
+ * {@link RectangleImmutable#coverage(RectangleImmutable) coverage} of this window.
*
* If no coverage is detected the first {@link MonitorDevice} is returned.
*
@@ -242,6 +255,10 @@ public interface Window extends NativeWindow, WindowClosingProtocol {
/**
* Returns a newly created {@link Rectangle} containing the scaled window origin, {@link #getX()} & {@link #getY()},
* and size, {@link #getSurfaceWidth()} & {@link #getSurfaceHeight()}, in pixel units.
+ *
+ * @deprecated The returned position in pixel units might be erroneous in case of multiple monitor setup where a mixed pixel-scale exist,
+ * since this method currently does not take the monitor viewport and each of it's pixel-scale into account (expensive).
+ * Either we fix this issue or remove this method at a later time.
*/
Rectangle getSurfaceBounds();
diff --git a/src/newt/classes/jogamp/newt/MonitorDeviceImpl.java b/src/newt/classes/jogamp/newt/MonitorDeviceImpl.java
index 9e10879c4..e9e41a0ef 100644
--- a/src/newt/classes/jogamp/newt/MonitorDeviceImpl.java
+++ b/src/newt/classes/jogamp/newt/MonitorDeviceImpl.java
@@ -38,8 +38,8 @@ import com.jogamp.newt.Screen;
public class MonitorDeviceImpl extends MonitorDevice {
- public MonitorDeviceImpl(ScreenImpl screen, int nativeId, DimensionImmutable sizeMM, Rectangle viewport, MonitorMode currentMode, ArrayHashSet supportedModes) {
- super(screen, nativeId, sizeMM, viewport, currentMode, supportedModes);
+ public MonitorDeviceImpl(ScreenImpl screen, int nativeId, DimensionImmutable sizeMM, Rectangle viewportPU, Rectangle viewportWU, MonitorMode currentMode, ArrayHashSet supportedModes) {
+ super(screen, nativeId, sizeMM, viewportPU, viewportWU, currentMode, supportedModes);
}
@Override
@@ -136,11 +136,10 @@ public class MonitorDeviceImpl extends MonitorDevice {
this.currentMode = currentMode;
}
- /* pp */ final void setViewportValue(Rectangle viewport) {
- this.viewport = viewport;
- }
+ /* pp */ final Rectangle getMutuableViewportPU() { return viewportPU; }
+ /* pp */ final Rectangle getMutuableViewportWU() { return viewportWU; }
- /* pp */ ArrayHashSet getSupportedModesImpl() {
+ /* pp */ final ArrayHashSet getSupportedModesImpl() {
return supportedModes;
}
diff --git a/src/newt/classes/jogamp/newt/MonitorModeProps.java b/src/newt/classes/jogamp/newt/MonitorModeProps.java
index 9d8f4919c..55cbf77f3 100644
--- a/src/newt/classes/jogamp/newt/MonitorModeProps.java
+++ b/src/newt/classes/jogamp/newt/MonitorModeProps.java
@@ -81,9 +81,10 @@ public class MonitorModeProps {
;
/** WARNING: must be synchronized with ScreenMode.h, native implementation
- * 10: count + id, ScreenSizeMM[width, height], rotated Viewport[x, y, width, height], currentMonitorModeId, rotation, supportedModeId+
+ * 15: count + id, ScreenSizeMM[width, height], rotated Viewport pixel-units, rotated viewport window-units, currentMonitorModeId, rotation, supportedModeId+
+ * Viewport := [x, y, width, height] (4 elements)
*/
- public static final int MIN_MONITOR_DEVICE_PROPERTIES = 11;
+ public static final int MIN_MONITOR_DEVICE_PROPERTIES = 15;
public static final int IDX_MONITOR_DEVICE_VIEWPORT = 1 // count
+ 1 // native mode
@@ -223,7 +224,8 @@ public class MonitorModeProps {
final List allMonitorModes = cache.monitorModes.getData();
final int id = monitorProperties[offset++];
final DimensionImmutable sizeMM = streamInResolution(monitorProperties, offset); offset+=NUM_RESOLUTION_PROPERTIES;
- final Rectangle viewport = new Rectangle(monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++]);
+ final Rectangle viewportPU = new Rectangle(monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++]);
+ final Rectangle viewportWU = new Rectangle(monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++]);
final MonitorMode currentMode;
{
final int modeId = monitorProperties[offset++];
@@ -240,7 +242,7 @@ public class MonitorModeProps {
}
}
}
- MonitorDevice monitorDevice = new MonitorDeviceImpl(screen, id, sizeMM, viewport, currentMode, supportedModes);
+ MonitorDevice monitorDevice = new MonitorDeviceImpl(screen, id, sizeMM, viewportPU, viewportWU, currentMode, supportedModes);
if(null!=cache) {
monitorDevice = cache.monitorDevices.getOrAdd(monitorDevice);
}
@@ -296,8 +298,9 @@ public class MonitorModeProps {
offset++;
final int id = monitorProperties[offset++];
final DimensionImmutable sizeMM = streamInResolution(monitorProperties, offset); offset+=NUM_RESOLUTION_PROPERTIES;
- final Rectangle viewport = new Rectangle(monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++]);
- MonitorDevice monitorDevice = new MonitorDeviceImpl(screen, id, sizeMM, viewport, currentMode, supportedModes);
+ final Rectangle viewportPU = new Rectangle(monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++]);
+ final Rectangle viewportWU = new Rectangle(monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++], monitorProperties[offset++]);
+ MonitorDevice monitorDevice = new MonitorDeviceImpl(screen, id, sizeMM, viewportPU, viewportWU, currentMode, supportedModes);
if(null!=cache) {
monitorDevice = cache.monitorDevices.getOrAdd(monitorDevice);
}
@@ -328,6 +331,10 @@ public class MonitorModeProps {
data[idx++] = monitorDevice.getViewport().getY();
data[idx++] = monitorDevice.getViewport().getWidth();
data[idx++] = monitorDevice.getViewport().getHeight();
+ data[idx++] = monitorDevice.getViewportInWindowUnits().getX();
+ data[idx++] = monitorDevice.getViewportInWindowUnits().getY();
+ data[idx++] = monitorDevice.getViewportInWindowUnits().getWidth();
+ data[idx++] = monitorDevice.getViewportInWindowUnits().getHeight();
data[idx++] = monitorDevice.getCurrentMode().getId();
data[idx++] = monitorDevice.getCurrentMode().getRotation();
final List supportedModes = monitorDevice.getSupportedModes();
diff --git a/src/newt/classes/jogamp/newt/ScreenImpl.java b/src/newt/classes/jogamp/newt/ScreenImpl.java
index d7e6c641c..949e7fa3b 100644
--- a/src/newt/classes/jogamp/newt/ScreenImpl.java
+++ b/src/newt/classes/jogamp/newt/ScreenImpl.java
@@ -81,10 +81,11 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
protected int hashCode;
protected AbstractGraphicsScreen aScreen;
protected int refCount; // number of Screen references by Window
- protected Rectangle vOriginSize = new Rectangle(0, 0, 0, 0); // virtual rotated screen origin and size
+ protected Rectangle virtViewportPU = new Rectangle(0, 0, 0, 0); // virtual rotated viewport in pixel units
+ protected Rectangle virtViewportWU = new Rectangle(0, 0, 0, 0); // virtual rotated viewport in window units
protected static Dimension usrSize = null; // property values: newt.ws.swidth and newt.ws.sheight
protected static volatile boolean usrSizeQueried = false;
- private ArrayList refMonitorModeListener = new ArrayList();
+ private final ArrayList refMonitorModeListener = new ArrayList();
private long tCreated; // creationTime
@@ -130,6 +131,7 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
screen.screen_idx = idx;
screen.fqname = display.getFQName()+"-s"+idx;
screen.hashCode = screen.fqname.hashCode();
+ screen.instantiationFinished();
Screen.addScreen2List(screen);
if(DEBUG) {
System.err.println("Screen.create() NEW: "+screen+" "+Display.getThreadName());
@@ -141,6 +143,14 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
}
}
+ /**
+ * Notifies the driver impl. that the instantiation is finished,
+ * ie. instance created and all fields set.
+ */
+ protected void instantiationFinished() {
+ // nop
+ }
+
@Override
public boolean equals(Object obj) {
if (obj == null) {
@@ -260,19 +270,20 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
protected abstract int validateScreenIndex(int idx);
/**
- * Stores the virtual origin and virtual rotated screen size.
+ * Calculates the virtual rotated viewport in pixel- and window units.
*
* This method is called after the MonitorMode has been set or changed,
* hence you may utilize it.
*
*
* Default implementation uses the union of all monitor's viewport,
- * calculated via {@link #unionOfMonitorViewportSize()}.
+ * calculated via {@link #unionOfMonitorViewportSize()}, however driver impl. may chose a different methodology.
*
- * @param vOriginSize storage for result
+ * @param viewport storage for result in pixel units
+ * @param viewportInWindowUnits storage for result in window units
*/
- protected void calcVirtualScreenOriginAndSize(final Rectangle vOriginSize) {
- unionOfMonitorViewportSize(vOriginSize);
+ protected void calcVirtualScreenOriginAndSize(final Rectangle viewport, final Rectangle viewportInWindowUnits) {
+ unionOfMonitorViewports(viewport, viewportInWindowUnits);
}
@Override
@@ -281,18 +292,19 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
}
/**
- * Updates the rotated virtual ScreenSize using the native impl.
+ * Updates the rotated virtual viewport, may use native impl.
*/
protected void updateVirtualScreenOriginAndSize() {
if(null != usrSize ) {
- vOriginSize.set(0, 0, usrSize.getWidth(), usrSize.getHeight());
+ virtViewportPU.set(0, 0, usrSize.getWidth(), usrSize.getHeight());
+ virtViewportWU.set(0, 0, usrSize.getWidth(), usrSize.getHeight());
if(DEBUG) {
- System.err.println("Update user virtual screen viewport @ "+Thread.currentThread().getName()+": "+vOriginSize);
+ System.err.println("Update user virtual screen viewport @ "+Thread.currentThread().getName()+": "+virtViewportPU);
}
} else {
- calcVirtualScreenOriginAndSize(vOriginSize);
+ calcVirtualScreenOriginAndSize(virtViewportPU, virtViewportWU);
if(DEBUG) {
- System.err.println("Updated virtual screen viewport @ "+Thread.currentThread().getName()+": "+vOriginSize);
+ System.err.println("Updated virtual screen viewport @ "+Thread.currentThread().getName()+": "+virtViewportPU+" [pixel], "+virtViewportWU+" [window]");
}
}
}
@@ -318,19 +330,21 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
}
@Override
- public final int getX() { return vOriginSize.getX(); }
+ public final int getX() { return virtViewportPU.getX(); }
@Override
- public final int getY() { return vOriginSize.getY(); }
+ public final int getY() { return virtViewportPU.getY(); }
@Override
- public final int getWidth() { return vOriginSize.getWidth(); }
+ public final int getWidth() { return virtViewportPU.getWidth(); }
@Override
- public final int getHeight() { return vOriginSize.getHeight(); }
+ public final int getHeight() { return virtViewportPU.getHeight(); }
@Override
- public final RectangleImmutable getViewport() { return vOriginSize; }
+ public final RectangleImmutable getViewport() { return virtViewportPU; }
+ @Override
+ public final RectangleImmutable getViewportInWindowUnits() { return virtViewportWU; }
@Override
public String toString() {
- return "NEWT-Screen["+getFQName()+", idx "+screen_idx+", refCount "+refCount+", vsize "+vOriginSize+", "+aScreen+", "+display+
+ return "NEWT-Screen["+getFQName()+", idx "+screen_idx+", refCount "+refCount+", vsize "+virtViewportPU+" [pixels], "+virtViewportWU+" [window], "+aScreen+", "+display+
", monitors: "+getMonitorDevices()+"]";
}
@@ -357,7 +371,10 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
*/
protected abstract void collectNativeMonitorModesAndDevicesImpl(MonitorModeProps.Cache cache);
- protected Rectangle getNativeMonitorDeviceViewportImpl(MonitorDevice monitor) { return null; }
+ protected boolean updateNativeMonitorDeviceViewportImpl(final MonitorDevice monitor,
+ final Rectangle viewportPU, final Rectangle viewportWU) {
+ return false;
+ }
/**
* To be implemented by the native specification.
@@ -402,7 +419,7 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
System.err.println("monitorModeChangeNotify @ "+Thread.currentThread().getName()+": "+me);
}
for(int i=0; i monitors = getMonitorDevices();
for(int i=monitors.size()-1; i>=0; i--) {
final MonitorDeviceImpl monitor = (MonitorDeviceImpl) monitors.get(i);
- final Rectangle newViewport = getNativeMonitorDeviceViewportImpl(monitor);
+ final boolean viewportUpdated = updateNativeMonitorDeviceViewportImpl(monitor, monitor.getMutuableViewportPU(), monitor.getMutuableViewportWU());
if( DEBUG ) {
- System.err.println("Screen.updateMonitorViewport["+i+"] @ "+Thread.currentThread().getName()+": "+monitor.getViewport()+" -> "+newViewport);
- }
- if( null != newViewport ) {
- monitor.setViewportValue(newViewport);
+ System.err.println("Screen.updateMonitorViewport["+i+"] @ "+Thread.currentThread().getName()+": updated: "+viewportUpdated+", PU "+monitor.getViewport()+", WU "+monitor.getViewportInWindowUnits());
}
}
}
@@ -430,7 +444,7 @@ public abstract class ScreenImpl extends Screen implements MonitorModeListener {
System.err.println("monitorModeChangeNotify @ "+Thread.currentThread().getName()+": success "+success+", "+me);
}
for(int i=0; i 1 || sviewport.compareTo(viewport) > 0 ) ) {
fs_span_flag = FLAG_IS_FULLSCREEN_SPAN;
@@ -2620,7 +2624,7 @@ public abstract class WindowImpl implements Window, NEWTEventConsumer
// Native MouseEvents pre-processed to be enqueued or consumed directly
//
- public void sendMouseEvent(final short eventType, final int modifiers,
+ public final void sendMouseEvent(final short eventType, final int modifiers,
final int x, final int y, final short button, final float rotation) {
doMouseEvent(false, false, eventType, modifiers, x, y, button, MouseEvent.getRotationXYZ(rotation, modifiers), 1f);
}
diff --git a/src/newt/classes/jogamp/newt/driver/android/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/android/WindowDriver.java
index 7a571318b..5671a05e4 100644
--- a/src/newt/classes/jogamp/newt/driver/android/WindowDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/android/WindowDriver.java
@@ -286,8 +286,7 @@ public class WindowDriver extends jogamp.newt.WindowImpl implements Callback2 {
if( isFullscreen() ) {
final MonitorDevice mainMonitor = getMainMonitor();
- final RectangleImmutable screenRect = mainMonitor.getViewport();
- final RectangleImmutable winRect = this.convertToWindowUnits((Rectangle)screenRect.cloneMutable());
+ final RectangleImmutable winRect = mainMonitor.getViewportInWindowUnits();
definePosition(winRect.getX(), winRect.getY());
defineSize(winRect.getWidth(), winRect.getHeight());
}
diff --git a/src/newt/classes/jogamp/newt/driver/awt/AWTCanvas.java b/src/newt/classes/jogamp/newt/driver/awt/AWTCanvas.java
index f7722c91c..5dab64e39 100644
--- a/src/newt/classes/jogamp/newt/driver/awt/AWTCanvas.java
+++ b/src/newt/classes/jogamp/newt/driver/awt/AWTCanvas.java
@@ -65,7 +65,7 @@ public class AWTCanvas extends Canvas {
private AWTGraphicsConfiguration awtConfig;
private volatile JAWTWindow jawtWindow=null; // the JAWTWindow presentation of this AWT Canvas, bound to the 'drawable' lifecycle
private CapabilitiesChooser chooser=null;
- private CapabilitiesImmutable capabilities;
+ private final CapabilitiesImmutable capabilities;
private boolean displayConfigChanged=false;
@@ -152,6 +152,10 @@ public class AWTCanvas extends Canvas {
}
}
+ public int getPixelScale() {
+ final JAWTWindow _jawtWindow = jawtWindow;
+ return (null != _jawtWindow) ? _jawtWindow.getPixelScale() : 1;
+ }
public NativeWindow getNativeWindow() {
final JAWTWindow _jawtWindow = jawtWindow;
return (null != _jawtWindow) ? _jawtWindow : null;
diff --git a/src/newt/classes/jogamp/newt/driver/awt/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/awt/WindowDriver.java
index f99476851..1f0ba6f09 100644
--- a/src/newt/classes/jogamp/newt/driver/awt/WindowDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/awt/WindowDriver.java
@@ -98,6 +98,17 @@ public class WindowDriver extends WindowImpl {
}
}
+ @Override
+ protected final int getPixelScaleX() {
+ final AWTCanvas _awtCanvas = awtCanvas;
+ return null != _awtCanvas ? _awtCanvas.getPixelScale() : 1;
+ }
+
+ @Override
+ protected final int getPixelScaleY() {
+ return getPixelScaleX();
+ }
+
@Override
protected void createNativeImpl() {
if(0!=getParentWindowHandle()) {
diff --git a/src/newt/classes/jogamp/newt/driver/bcm/egl/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/bcm/egl/ScreenDriver.java
index d3231557f..64bc87a41 100644
--- a/src/newt/classes/jogamp/newt/driver/bcm/egl/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/bcm/egl/ScreenDriver.java
@@ -104,8 +104,8 @@ public class ScreenDriver extends jogamp.newt.ScreenImpl {
}
@Override
- protected void calcVirtualScreenOriginAndSize(Rectangle vOriginSize) {
- vOriginSize.set(0, 0, fixedWidth, fixedHeight); // FIXME
+ protected void calcVirtualScreenOriginAndSize(Rectangle viewport, Rectangle viewportInWindowUnits) {
+ viewport.set(0, 0, fixedWidth, fixedHeight); // FIXME
}
//----------------------------------------------------------------------
diff --git a/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/ScreenDriver.java
index dc2a8459a..e0228c10f 100644
--- a/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/ScreenDriver.java
@@ -97,8 +97,8 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected void calcVirtualScreenOriginAndSize(Rectangle vOriginSize) {
- vOriginSize.set(0, 0, cachedWidth, cachedHeight);
+ protected void calcVirtualScreenOriginAndSize(Rectangle viewport, Rectangle viewportInWindowUnits) {
+ viewport.set(0, 0, cachedWidth, cachedHeight);
}
/** Called from {@link #initNative()}. */
diff --git a/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/WindowDriver.java
index 1c927acc4..188e5b964 100644
--- a/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/WindowDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/bcm/vc/iv/WindowDriver.java
@@ -170,13 +170,13 @@ public class WindowDriver extends WindowImpl {
}
@Override
- public final void sendMouseEvent(final short eventType, final int modifiers,
- final int x, final int y, final short button, final float rotation) {
+ protected final void doMouseEvent(final boolean enqueue, final boolean wait, final short eventType, final int modifiers,
+ final int x, final int y, final short button, final float[] rotationXYZ, final float rotationScale) {
if( MouseEvent.EVENT_MOUSE_MOVED == eventType ) {
final DisplayDriver display = (DisplayDriver) getScreen().getDisplay();
display.moveActivePointerIcon(x, y);
}
- super.sendMouseEvent(eventType, modifiers, x, y, button, rotation);
+ super.doMouseEvent(enqueue, wait, eventType, modifiers, x, y, button, rotationXYZ, rotationScale);
}
@Override
diff --git a/src/newt/classes/jogamp/newt/driver/intel/gdl/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/intel/gdl/ScreenDriver.java
index 44802e348..20c60565a 100644
--- a/src/newt/classes/jogamp/newt/driver/intel/gdl/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/intel/gdl/ScreenDriver.java
@@ -106,8 +106,8 @@ public class ScreenDriver extends jogamp.newt.ScreenImpl {
}
@Override
- protected void calcVirtualScreenOriginAndSize(Rectangle vOriginSize) {
- vOriginSize.set(0, 0, cachedWidth, cachedHeight);
+ protected void calcVirtualScreenOriginAndSize(Rectangle viewport, Rectangle viewportInWindowUnits) {
+ viewport.set(0, 0, cachedWidth, cachedHeight);
}
//----------------------------------------------------------------------
diff --git a/src/newt/classes/jogamp/newt/driver/kd/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/kd/ScreenDriver.java
index 9ebe2629a..541576250 100644
--- a/src/newt/classes/jogamp/newt/driver/kd/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/kd/ScreenDriver.java
@@ -102,8 +102,8 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected void calcVirtualScreenOriginAndSize(Rectangle vOriginSize) {
- vOriginSize.set(0, 0, cachedWidth, cachedHeight);
+ protected void calcVirtualScreenOriginAndSize(Rectangle viewport, Rectangle viewportInWindowUnits) {
+ viewport.set(0, 0, cachedWidth, cachedHeight);
}
protected void sizeChanged(int w, int h) {
diff --git a/src/newt/classes/jogamp/newt/driver/macosx/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/macosx/ScreenDriver.java
index 4f3cc691b..5f458e2c9 100644
--- a/src/newt/classes/jogamp/newt/driver/macosx/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/macosx/ScreenDriver.java
@@ -35,13 +35,16 @@
package jogamp.newt.driver.macosx;
import javax.media.nativewindow.DefaultGraphicsScreen;
+import javax.media.nativewindow.util.Rectangle;
+import jogamp.nativewindow.macosx.OSXUtil;
import jogamp.newt.MonitorModeProps;
import jogamp.newt.ScreenImpl;
import com.jogamp.common.util.ArrayHashSet;
import com.jogamp.newt.MonitorDevice;
import com.jogamp.newt.MonitorMode;
+import com.jogamp.opengl.math.FloatUtil;
public class ScreenDriver extends ScreenImpl {
@@ -60,7 +63,7 @@ public class ScreenDriver extends ScreenImpl {
@Override
protected void closeNativeImpl() { }
- private MonitorMode getMonitorModeImpl(MonitorModeProps.Cache cache, int crt_idx, int mode_idx) {
+ private MonitorMode getMonitorModeImpl(final MonitorModeProps.Cache cache, final int crt_idx, final int mode_idx) {
final int[] modeProps = getMonitorMode0(crt_idx, mode_idx);
final MonitorMode res;
if (null == modeProps || 0 >= modeProps.length) {
@@ -71,56 +74,133 @@ public class ScreenDriver extends ScreenImpl {
return res;
}
- @Override
- protected final void collectNativeMonitorModesAndDevicesImpl(MonitorModeProps.Cache cache) {
- int crtIdx = 0;
- int modeIdx = 0;
- ArrayHashSet supportedModes = new ArrayHashSet();
- do {
- final MonitorMode mode = getMonitorModeImpl(cache, crtIdx, modeIdx);
- if( null != mode ) {
- supportedModes.getOrAdd(mode);
- // next mode on same monitor
- modeIdx++;
- } else if( 0 < modeIdx ) {
- // end of monitor modes - got at least one mode
- final MonitorMode currentMode = getMonitorModeImpl(cache, crtIdx, -1);
- if ( null == currentMode ) {
- throw new InternalError("Could not gather current mode of device "+crtIdx+", but gathered "+modeIdx+" modes");
+ private class CrtProps {
+ CrtProps() {
+ count = getMonitorCount0();
+ pixelScaleArray = new int[count];
+ propsOrigArray = new int[count][];
+ propsFixedArray = new int[count][];
+
+ //
+ // Gather whole topology of monitors (NSScreens)
+ //
+ for(int crtIdx=0; crtIdx fixed
+ final int propsLen = propsOrigArray[crtIdx].length;
+ propsFixedArray[crtIdx] = new int[propsLen];
+ System.arraycopy(propsOrigArray[crtIdx], 0, propsFixedArray[crtIdx], 0, propsLen);
+ }
+
+ //
+ // Fix scaled viewport w/ pixelScale of each monitorProps,
+ // i.e. size by its own pixelScale and x/y offset by querying it's neighbors.
+ //
+ for(int crtIdx=0; crtIdx();
- crtIdx++;
- modeIdx=0;
- } else {
- // end of monitor
- break;
}
- } while ( true );
+ }
+ final int count;
+ final int[] pixelScaleArray;
+ final int[][] propsOrigArray;
+ final int[][] propsFixedArray;
+ }
+
+ @Override
+ protected final void collectNativeMonitorModesAndDevicesImpl(final MonitorModeProps.Cache cache) {
+ final CrtProps crtProps = new CrtProps();
+
+ //
+ // Collect all monitorModes for all monitorDevices
+ //
+ for(int crtIdx=0; crtIdx supportedModes = new ArrayHashSet();
+ int modeIdx = 0;
+ {
+ // Get all supported modes for this monitorDevice
+ MonitorMode mode;
+ while( true ) {
+ mode = getMonitorModeImpl(cache, crtIdx, modeIdx);
+ if( null != mode ) {
+ if( mode.getSurfaceSize().getBitsPerPixel() >= 24 ) { // drop otherwise
+ supportedModes.getOrAdd(mode);
+ }
+ modeIdx++; // next mode on same monitor
+ } else {
+ break; // done with modes on this monitor
+ }
+ }
+ }
+ if( 0 >= modeIdx ) {
+ throw new InternalError("Could not gather single mode of device "+crtIdx+"/"+crtProps.count);
+ }
+ final MonitorMode currentMode = getMonitorModeImpl(cache, crtIdx, -1);
+ if ( null == currentMode ) {
+ throw new InternalError("Could not gather current mode of device "+crtIdx+"/"+crtProps.count+", but gathered "+modeIdx+" modes");
+ }
+ // merge monitor-props + supported modes
+ MonitorModeProps.streamInMonitorDevice(null, cache, this, supportedModes, currentMode, crtProps.propsFixedArray[crtIdx], 0);
+ }
+ }
+
+ @Override
+ protected boolean updateNativeMonitorDeviceViewportImpl(final MonitorDevice monitor, final Rectangle viewportPU, final Rectangle viewportWU) {
+ final CrtProps crtProps = new CrtProps();
+ final int crtIdx = monitor.getId();
+ if( 0 > crtIdx || crtIdx >= crtProps.count ) {
+ throw new IndexOutOfBoundsException("monitor id "+crtIdx+" not withon [0.."+(crtProps.count-1)+"]");
+ }
+ final int[] fixedMonitorProps = crtProps.propsFixedArray[crtIdx];
+ int offset = MonitorModeProps.IDX_MONITOR_DEVICE_VIEWPORT;
+ viewportPU.set(fixedMonitorProps[offset++], fixedMonitorProps[offset++], fixedMonitorProps[offset++], fixedMonitorProps[offset++]);
+ viewportWU.set(fixedMonitorProps[offset++], fixedMonitorProps[offset++], fixedMonitorProps[offset++], fixedMonitorProps[offset++]);
+ return true;
}
@Override
- protected MonitorMode queryCurrentMonitorModeImpl(MonitorDevice monitor) {
+ protected MonitorMode queryCurrentMonitorModeImpl(final MonitorDevice monitor) {
return getMonitorModeImpl(null, monitor.getId(), -1);
}
@Override
- protected boolean setCurrentMonitorModeImpl(MonitorDevice monitor, MonitorMode mode) {
+ protected boolean setCurrentMonitorModeImpl(final MonitorDevice monitor, final MonitorMode mode) {
return setMonitorMode0(monitor.getId(), mode.getId(), mode.getRotation());
}
@Override
- protected int validateScreenIndex(int idx) {
+ protected int validateScreenIndex(final int idx) {
return 0; // big-desktop w/ multiple monitor attached, only one screen available
}
+ private native int getMonitorCount0();
private native int[] getMonitorProps0(int crt_idx);
private native int[] getMonitorMode0(int crt_index, int mode_idx);
private native boolean setMonitorMode0(int crt_index, int nativeId, int rot);
diff --git a/src/newt/classes/jogamp/newt/driver/macosx/WindowDriver.java b/src/newt/classes/jogamp/newt/driver/macosx/WindowDriver.java
index eebf280de..540186f2e 100644
--- a/src/newt/classes/jogamp/newt/driver/macosx/WindowDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/macosx/WindowDriver.java
@@ -46,12 +46,15 @@ import javax.media.nativewindow.util.PointImmutable;
import jogamp.nativewindow.macosx.OSXUtil;
import jogamp.newt.PointerIconImpl;
+import jogamp.newt.ScreenImpl;
import jogamp.newt.WindowImpl;
import jogamp.newt.driver.DriverClearFocus;
import jogamp.newt.driver.DriverUpdatePosition;
import com.jogamp.newt.event.InputEvent;
import com.jogamp.newt.event.KeyEvent;
+import com.jogamp.newt.event.MonitorEvent;
+import com.jogamp.opengl.math.FloatUtil;
public class WindowDriver extends WindowImpl implements MutableSurface, DriverClearFocus, DriverUpdatePosition {
@@ -59,7 +62,81 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
DisplayDriver.initSingleton();
}
+ private int pixelScale;
+
public WindowDriver() {
+ pixelScale = 1;
+ }
+
+ private boolean updatePixelScale(final boolean sendEvent, final boolean defer, final float newPixelScaleRaw) {
+ final int newPixelScaleSafe = FloatUtil.isZero(newPixelScaleRaw, FloatUtil.EPSILON) ? 1 : (int) newPixelScaleRaw;
+ final boolean changed = pixelScale != newPixelScaleSafe;
+ if( DEBUG_IMPLEMENTATION ) {
+ System.err.println("WindowDriver.updatePixelScale.X: "+pixelScale+" -> "+newPixelScaleSafe+" (raw "+newPixelScaleRaw+") - changed "+changed);
+ }
+ if( changed ) {
+ pixelScale = newPixelScaleSafe;
+ if( sendEvent ) {
+ super.sizeChanged(defer, getWindowWidth(), getWindowHeight(), true);
+ } else {
+ defineSize(getWindowWidth(), getWindowHeight());
+ }
+ }
+ return changed;
+ }
+
+ private boolean updatePixelScaleByScreenIdx(final boolean sendEvent) {
+ final float newPixelScaleRaw = (float) OSXUtil.GetPixelScale(getScreen().getIndex());
+ if( DEBUG_IMPLEMENTATION ) {
+ System.err.println("WindowDriver.updatePixelScale.1: "+pixelScale+" -> "+newPixelScaleRaw);
+ }
+ return updatePixelScale(sendEvent, true /* defer */, newPixelScaleRaw);
+ }
+
+ private boolean updatePixelScaleByWindowHandle(final boolean sendEvent) {
+ final long wh = getWindowHandle();
+ if( 0 != wh ) {
+ final float newPixelScaleRaw = (float)OSXUtil.GetPixelScale(wh);
+ if( DEBUG_IMPLEMENTATION ) {
+ System.err.println("WindowDriver.updatePixelScale.2: "+pixelScale+" -> "+newPixelScaleRaw);
+ }
+ return updatePixelScale(sendEvent, true /* defer */, newPixelScaleRaw);
+ } else {
+ return false;
+ }
+ }
+
+ /** Called from native code */
+ protected void updatePixelScale(final boolean defer, final float newPixelScaleRaw) {
+ final long handle = getWindowHandle();
+ if( 0 != handle ) {
+ if( DEBUG_IMPLEMENTATION ) {
+ System.err.println("WindowDriver.updatePixelScale.3: "+pixelScale+" -> "+newPixelScaleRaw);
+ }
+ updatePixelScale(true /* sendEvent*/, defer, newPixelScaleRaw);
+ }
+ }
+
+ @Override
+ protected final void instantiationFinished() {
+ updatePixelScaleByScreenIdx(false /* sendEvent*/);
+ }
+
+ @Override
+ protected void setScreen(ScreenImpl newScreen) { // never null !
+ super.setScreen(newScreen);
+ updatePixelScaleByScreenIdx(false /* sendEvent*/); // caller (reparent, ..) will send reshape event
+ }
+
+
+ @Override
+ protected final int getPixelScaleX() {
+ return pixelScale;
+ }
+
+ @Override
+ protected final int getPixelScaleY() {
+ return pixelScale;
}
@Override
@@ -209,16 +286,6 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
private boolean useParent(NativeWindow parent) { return null != parent && 0 != parent.getWindowHandle(); }
- @Override
- protected final int getPixelScaleX() {
- return 1; // FIXME HiDPI: Use pixelScale
- }
-
- @Override
- protected final int getPixelScaleY() {
- return 1; // FIXME HiDPI: Use pixelScale
- }
-
@Override
public void updatePosition(int x, int y) {
final long handle = getWindowHandle();
@@ -263,11 +330,12 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
}
@Override
- protected boolean reconfigureWindowImpl(final int x, final int y, final int width, final int height, int flags) {
+ protected boolean reconfigureWindowImpl(int x, int y, final int width, final int height, int flags) {
final boolean _isOffscreenInstance = isOffscreenInstance(this, this.getParent());
isOffscreenInstance = 0 != sscSurfaceHandle || _isOffscreenInstance;
final PointImmutable pClientLevelOnSreen;
if( isOffscreenInstance ) {
+ x = 0; y = 0;
pClientLevelOnSreen = new Point(0, 0);
} else {
final NativeWindow parent = getParent();
@@ -313,9 +381,9 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
0 != ( FLAG_CHANGE_PARENTING & flags) ||
0 != ( FLAG_CHANGE_FULLSCREEN & flags) ) {
if(isOffscreenInstance) {
- createWindow(true, 0 != getWindowHandle(), pClientLevelOnSreen, 64, 64, false, setVisible, false);
+ createWindow(true, 0 != getWindowHandle(), pClientLevelOnSreen, x, y, 64, 64, false, setVisible, false);
} else {
- createWindow(false, 0 != getWindowHandle(), pClientLevelOnSreen, width, height,
+ createWindow(false, 0 != getWindowHandle(), pClientLevelOnSreen, x, y, width, height,
0 != ( FLAG_IS_FULLSCREEN & flags), setVisible, 0 != ( FLAG_IS_ALWAYSONTOP & flags));
}
} else {
@@ -329,7 +397,7 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
} // else offscreen size is realized via recreation
// no native event (fullscreen, some reparenting)
positionChanged(true, x, y);
- sizeChanged(true, width, height, false);
+ super.sizeChanged(true, width, height, false);
}
if( 0 != ( FLAG_CHANGE_VISIBILITY & flags) && setVisible ) {
if( !isOffscreenInstance ) {
@@ -439,10 +507,16 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
@Override
protected void warpPointerImpl(final int x, final int y) {
if( !isOffscreenInstance ) {
- warpPointer0(getWindowHandle(), x, y);
+ warpPointer0(getWindowHandle(), x / getPixelScaleX(), y / getPixelScaleY());
} // else may need offscreen solution ? FIXME
}
+ @Override
+ protected final void doMouseEvent(final boolean enqueue, final boolean wait, final short eventType, final int modifiers,
+ final int x, final int y, final short button, final float[] rotationXYZ, final float rotationScale) {
+ super.doMouseEvent(enqueue, wait, eventType, modifiers, x * getPixelScaleX(), y * getPixelScaleY(), button, rotationXYZ, rotationScale);
+ }
+
@Override
public final void sendKeyEvent(short eventType, int modifiers, short keyCode, short keySym, char keyChar) {
throw new InternalError("XXX: Adapt Java Code to Native Code Changes");
@@ -499,8 +573,8 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
//
private void createWindow(final boolean offscreenInstance, final boolean recreate,
- final PointImmutable pS, final int width, final int height,
- final boolean fullscreen, final boolean visible, final boolean alwaysOnTop) {
+ final PointImmutable pS, final int x, final int y,
+ final int width, final int height, final boolean fullscreen, final boolean visible, final boolean alwaysOnTop) {
final long parentWinHandle = getParentWindowHandle();
final long preWinHandle = getWindowHandle();
@@ -558,8 +632,12 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
setTitle0(newWin, getTitle());
setAlwaysOnTop0(getWindowHandle(), alwaysOnTop);
}
- visibleChanged(true, visible);
} } );
+ // no native event (fullscreen, some reparenting)
+ positionChanged(false, x, y);
+ updatePixelScaleByWindowHandle(false /* sendEvent */);
+ super.sizeChanged(false, width, height, true);
+ visibleChanged(false, visible);
} catch (Exception ie) {
ie.printStackTrace();
}
@@ -569,7 +647,8 @@ public class WindowDriver extends WindowImpl implements MutableSurface, DriverCl
private native long createView0(int x, int y, int w, int h, boolean fullscreen);
private native long createWindow0(int x, int y, int w, int h, boolean fullscreen, int windowStyle, int backingStoreType, long view);
/** Must be called on Main-Thread */
- private native void initWindow0(long parentWindow, long window, int x, int y, int w, int h, boolean opaque, boolean visible, long view);
+ private native void initWindow0(long parentWindow, long window, int x, int y, int w, int h,
+ boolean opaque, boolean visible, long view);
private native boolean lockSurface0(long window, long view);
private native boolean unlockSurface0(long window, long view);
/** Must be called on Main-Thread */
diff --git a/src/newt/classes/jogamp/newt/driver/windows/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/windows/ScreenDriver.java
index e789b995f..af265cfd3 100644
--- a/src/newt/classes/jogamp/newt/driver/windows/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/windows/ScreenDriver.java
@@ -65,14 +65,14 @@ public class ScreenDriver extends ScreenImpl {
protected void closeNativeImpl() {
}
- private final String getAdapterName(int crt_idx) {
+ private final String getAdapterName(final int crt_idx) {
return getAdapterName0(crt_idx);
}
- private final String getActiveMonitorName(String adapterName, int monitor_idx) {
+ private final String getActiveMonitorName(final String adapterName, final int monitor_idx) {
return getActiveMonitorName0(adapterName, monitor_idx);
}
- private final MonitorMode getMonitorModeImpl(MonitorModeProps.Cache cache, String adapterName, int crtModeIdx) {
+ private final MonitorMode getMonitorModeImpl(final MonitorModeProps.Cache cache, final String adapterName, final int crtModeIdx) {
if( null == adapterName ) {
return null;
}
@@ -85,7 +85,7 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected void collectNativeMonitorModesAndDevicesImpl(MonitorModeProps.Cache cache) {
+ protected void collectNativeMonitorModesAndDevicesImpl(final MonitorModeProps.Cache cache) {
int crtIdx = 0;
ArrayHashSet supportedModes = new ArrayHashSet();
String adapterName = getAdapterName(crtIdx);
@@ -118,26 +118,28 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected Rectangle getNativeMonitorDeviceViewportImpl(MonitorDevice monitor) {
+ protected boolean updateNativeMonitorDeviceViewportImpl(final MonitorDevice monitor, final Rectangle viewportPU, final Rectangle viewportWU) {
final String adapterName = getAdapterName(monitor.getId());
if( null != adapterName ) {
final String activeMonitorName = getActiveMonitorName(adapterName, 0);
if( null != activeMonitorName ) {
final int[] monitorProps = getMonitorDevice0(adapterName, monitor.getId());
int offset = MonitorModeProps.IDX_MONITOR_DEVICE_VIEWPORT;
- return new Rectangle(monitorProps[offset++], monitorProps[offset++], monitorProps[offset++], monitorProps[offset++]);
+ viewportPU.set(monitorProps[offset++], monitorProps[offset++], monitorProps[offset++], monitorProps[offset++]);
+ viewportWU.set(monitorProps[offset++], monitorProps[offset++], monitorProps[offset++], monitorProps[offset++]);
+ return true;
}
}
- return null;
+ return false;
}
@Override
- protected MonitorMode queryCurrentMonitorModeImpl(MonitorDevice monitor) {
+ protected MonitorMode queryCurrentMonitorModeImpl(final MonitorDevice monitor) {
return getMonitorModeImpl(null, getAdapterName(monitor.getId()), -1);
}
@Override
- protected boolean setCurrentMonitorModeImpl(MonitorDevice monitor, MonitorMode mode) {
+ protected boolean setCurrentMonitorModeImpl(final MonitorDevice monitor, final MonitorMode mode) {
return setMonitorMode0(monitor.getId(),
-1, -1, // no fixed position!
mode.getSurfaceSize().getResolution().getWidth(),
@@ -149,13 +151,13 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected int validateScreenIndex(int idx) {
+ protected int validateScreenIndex(final int idx) {
return 0; // big-desktop w/ multiple monitor attached, only one screen available
}
@Override
- protected void calcVirtualScreenOriginAndSize(Rectangle vOriginSize) {
- vOriginSize.set(getVirtualOriginX0(), getVirtualOriginY0(), getVirtualWidthImpl0(), getVirtualHeightImpl0());
+ protected void calcVirtualScreenOriginAndSize(final Rectangle viewport, Rectangle viewportInWindowUnits) {
+ viewport.set(getVirtualOriginX0(), getVirtualOriginY0(), getVirtualWidthImpl0(), getVirtualHeightImpl0());
}
// Native calls
diff --git a/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java b/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java
index bef7f60ec..2d7c6509d 100644
--- a/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java
+++ b/src/newt/classes/jogamp/newt/driver/x11/ScreenDriver.java
@@ -111,7 +111,7 @@ public class ScreenDriver extends ScreenImpl {
private RandR rAndR;
@Override
- protected final void collectNativeMonitorModesAndDevicesImpl(MonitorModeProps.Cache cache) {
+ protected final void collectNativeMonitorModesAndDevicesImpl(final MonitorModeProps.Cache cache) {
if( null == rAndR ) { return; }
final AbstractGraphicsDevice device = getDisplay().getGraphicsDevice();
device.lock();
@@ -165,12 +165,14 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected Rectangle getNativeMonitorDeviceViewportImpl(MonitorDevice monitor) {
+ protected boolean updateNativeMonitorDeviceViewportImpl(final MonitorDevice monitor, final Rectangle viewportPU, final Rectangle viewportWU) {
final AbstractGraphicsDevice device = getDisplay().getGraphicsDevice();
device.lock();
try {
int[] viewportProps = rAndR.getMonitorDeviceViewport(device.getHandle(), this, monitor.getId());
- return new Rectangle(viewportProps[0], viewportProps[1], viewportProps[2], viewportProps[3]);
+ viewportPU.set(viewportProps[0], viewportProps[1], viewportProps[2], viewportProps[3]);
+ viewportWU.set(viewportProps[0], viewportProps[1], viewportProps[2], viewportProps[3]); // equal window-units and pixel-units
+ return true;
} finally {
device.unlock();
}
@@ -207,7 +209,7 @@ public class ScreenDriver extends ScreenImpl {
return done;
}
- private DisplayImpl.DisplayRunnable xineramaEnabledQueryWithTemp = new DisplayImpl.DisplayRunnable() {
+ private final DisplayImpl.DisplayRunnable xineramaEnabledQueryWithTemp = new DisplayImpl.DisplayRunnable() {
@Override
public Boolean run(long dpy) {
return new Boolean(X11Util.XineramaIsEnabled(dpy));
@@ -225,8 +227,8 @@ public class ScreenDriver extends ScreenImpl {
}
@Override
- protected void calcVirtualScreenOriginAndSize(final Rectangle vOriginSize) {
- final RectangleImmutable ov = (RectangleImmutable) getViewport().cloneMutable();
+ protected void calcVirtualScreenOriginAndSize(final Rectangle viewport, Rectangle viewportInWindowUnits) {
+ final RectangleImmutable ov = DEBUG ? (RectangleImmutable) getViewport().cloneMutable() : null;
/**
if( null != rAndR && rAndR.getVersion().compareTo(RandR.version130) >= 0 && getMonitorDevices().size()>0 ) {
super.calcVirtualScreenOriginAndSize(vOriginSize);
@@ -242,11 +244,11 @@ public class ScreenDriver extends ScreenImpl {
runWithLockedDisplayDevice( new DisplayImpl.DisplayRunnable