summaryrefslogtreecommitdiffstats
path: root/src/newt
diff options
context:
space:
mode:
authorSven Gothel <[email protected]>2012-01-13 16:13:40 +0100
committerSven Gothel <[email protected]>2012-01-13 16:13:40 +0100
commit48767a40c2461405dfce14e8d9eafbbab21d203e (patch)
tree3323739f3416eb5f8a00d6c10ac935ff6c6158b0 /src/newt
parentd23b08203e32f8f50991a48132eb3c2236b4efc0 (diff)
NEWT/OSX Performance Fix: Cache CGDisplayScreenSize() result, since it's ridiculous slow
Each call to CGDisplayScreenSize() took around 6ms (5ms .. 20ms, avrg 6ms) which added up to ~2s for ~400 Screen modes.
Diffstat (limited to 'src/newt')
-rw-r--r--src/newt/classes/jogamp/newt/driver/macosx/MacScreen.java26
-rw-r--r--src/newt/native/MacWindow.m62
2 files changed, 80 insertions, 8 deletions
diff --git a/src/newt/classes/jogamp/newt/driver/macosx/MacScreen.java b/src/newt/classes/jogamp/newt/driver/macosx/MacScreen.java
index 3204982be..b9c725fd4 100644
--- a/src/newt/classes/jogamp/newt/driver/macosx/MacScreen.java
+++ b/src/newt/classes/jogamp/newt/driver/macosx/MacScreen.java
@@ -38,16 +38,24 @@ import java.util.List;
import javax.media.nativewindow.DefaultGraphicsScreen;
import javax.media.nativewindow.util.Dimension;
+import javax.media.nativewindow.util.DimensionImmutable;
import javax.media.nativewindow.util.Point;
import jogamp.newt.ScreenImpl;
+import com.jogamp.common.util.IntObjectHashMap;
import com.jogamp.newt.ScreenMode;
import com.jogamp.newt.util.ScreenModeUtil;
public class MacScreen extends ScreenImpl {
+
+ // caching native CGDisplayScreenSize() results, since it's ridiculous slow (~6 ms each call)
+ private static IntObjectHashMap/*<int, DimensionImmutable>*/ scrnIdx2Dimension;
+
static {
MacDisplay.initSingleton();
+ scrnIdx2Dimension = new IntObjectHashMap();
+ scrnIdx2Dimension.setKeyNotFoundValue(null);
}
public MacScreen() {
@@ -63,7 +71,18 @@ public class MacScreen extends ScreenImpl {
private static native int getHeightImpl0(int scrn_idx);
private int[] getScreenModeIdx(int idx) {
- int[] modeProps = getScreenMode0(screen_idx, idx);
+ // caching native CGDisplayScreenSize() results, since it's ridiculous slow (~6 ms each call)
+ DimensionImmutable dim = (DimensionImmutable) scrnIdx2Dimension.get(screen_idx);
+ if(null == dim) {
+ int[] res = getScreenSizeMM0(screen_idx);
+ if(null == res || 0 == res.length) {
+ return null;
+ }
+ dim = new Dimension(res[0], res[1]);
+ scrnIdx2Dimension.put(screen_idx, dim);
+ }
+
+ int[] modeProps = getScreenMode0(screen_idx, idx, dim.getWidth(), dim.getHeight());
if (null == modeProps || 0 == modeProps.length) {
return null;
}
@@ -117,7 +136,8 @@ public class MacScreen extends ScreenImpl {
virtualSize.setWidth(getWidthImpl0(screen_idx));
virtualSize.setHeight(getHeightImpl0(screen_idx));
}
-
- private native int[] getScreenMode0(int screen_index, int mode_index);
+
+ private native int[] getScreenSizeMM0(int screen_idx);
+ private native int[] getScreenMode0(int screen_index, int mode_index, int widthMM, int heightMM);
private native boolean setScreenMode0(int screen_index, int mode_idx);
}
diff --git a/src/newt/native/MacWindow.m b/src/newt/native/MacWindow.m
index ddd59f0a1..c528ebb64 100644
--- a/src/newt/native/MacWindow.m
+++ b/src/newt/native/MacWindow.m
@@ -44,6 +44,10 @@
#import <stdio.h>
+#ifdef DBG_PERF
+ #include "timespec.h"
+#endif
+
static const char * const ClazzNamePoint = "javax/media/nativewindow/util/Point";
static const char * const ClazzAnyCstrName = "<init>";
static const char * const ClazzNamePointCstrSignature = "(II)V";
@@ -315,11 +319,60 @@ static long GetDictionaryLong(CFDictionaryRef theDict, const void* key)
/*
* Class: jogamp_newt_driver_macosx_MacScreen
+ * Method: getScreenSizeMM0
+ * Signature: (I)[I
+ */
+JNIEXPORT jintArray JNICALL Java_jogamp_newt_driver_macosx_MacScreen_getScreenSizeMM0
+ (JNIEnv *env, jobject obj, jint scrn_idx)
+{
+ NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
+
+#ifdef DBG_PERF
+ struct timespec t0, t1, td;
+ long td_ms;
+ timespec_now(&t0);
+#endif
+
+ NSScreen *screen = NewtScreen_getNSScreenByIndex((int)scrn_idx);
+#ifdef DBG_PERF
+ timespec_now(&t1); timespec_subtract(&td, &t1, &t0); td_ms = timespec_milliseconds(&td);
+ fprintf(stderr, "MacScreen_getScreenSizeMM0.1: %ld ms\n", td_ms); fflush(NULL);
+#endif
+
+ CGDirectDisplayID display = NewtScreen_getCGDirectDisplayIDByNSScreen(screen);
+#ifdef DBG_PERF
+ timespec_now(&t1); timespec_subtract(&td, &t1, &t0); td_ms = timespec_milliseconds(&td);
+ fprintf(stderr, "MacScreen_getScreenSizeMM0.2: %ld ms\n", td_ms); fflush(NULL);
+#endif
+
+ CGSize screenDim = CGDisplayScreenSize(display);
+#ifdef DBG_PERF
+ timespec_now(&t1); timespec_subtract(&td, &t1, &t0); td_ms = timespec_milliseconds(&td);
+ fprintf(stderr, "MacScreen_getScreenSizeMM0.3: %ld ms\n", td_ms); fflush(NULL);
+#endif
+
+ jint prop[ 2 ];
+ prop[0] = (jint) screenDim.width;
+ prop[1] = (jint) screenDim.height;
+
+ jintArray properties = (*env)->NewIntArray(env, 2);
+ if (properties == NULL) {
+ NewtCommon_throwNewRuntimeException(env, "Could not allocate int array of size 2");
+ }
+ (*env)->SetIntArrayRegion(env, properties, 0, 2, prop);
+
+ [pool release];
+
+ return properties;
+}
+
+/*
+ * Class: jogamp_newt_driver_macosx_MacScreen
* Method: getScreenMode0
- * Signature: (II)[I
+ * Signature: (IIII)[I
*/
JNIEXPORT jintArray JNICALL Java_jogamp_newt_driver_macosx_MacScreen_getScreenMode0
- (JNIEnv *env, jobject obj, jint scrn_idx, jint mode_idx)
+ (JNIEnv *env, jobject obj, jint scrn_idx, jint mode_idx, jint widthMM, jint heightMM)
{
NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
@@ -360,7 +413,6 @@ JNIEXPORT jintArray JNICALL Java_jogamp_newt_driver_macosx_MacScreen_getScreenMo
}
// mode = CGDisplayModeRetain(mode); // 10.6 on CGDisplayModeRef
- CGSize screenDim = CGDisplayScreenSize(display);
int mWidth = CGDDGetModeWidth(mode);
int mHeight = CGDDGetModeHeight(mode);
@@ -383,8 +435,8 @@ JNIEXPORT jintArray JNICALL Java_jogamp_newt_driver_macosx_MacScreen_getScreenMo
prop[propIndex++] = mWidth;
prop[propIndex++] = mHeight;
prop[propIndex++] = CGDDGetModeBitsPerPixel(mode);
- prop[propIndex++] = (jint) screenDim.width;
- prop[propIndex++] = (jint) screenDim.height;
+ prop[propIndex++] = widthMM;
+ prop[propIndex++] = heightMM;
prop[propIndex++] = CGDDGetModeRefreshRate(mode);
prop[propIndex++] = ccwRot;
prop[propIndex - NUM_SCREEN_MODE_PROPERTIES_ALL] = ( -1 < mode_idx ) ? propIndex-1 : propIndex ; // count == NUM_SCREEN_MODE_PROPERTIES_ALL