diff --git a/src/java/org/lwjgl/opengl/MacOSX.java b/src/java/org/lwjgl/opengl/MacOSX.java deleted file mode 100644 index 426b4032..00000000 --- a/src/java/org/lwjgl/opengl/MacOSX.java +++ /dev/null @@ -1,111 +0,0 @@ -/* - * Copyright (c) 2002 Lightweight Java Game Library Project - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: - * - * * Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * - * * Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * * Neither the name of 'Light Weight Java Game Library' nor the names of - * its contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED - * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR - * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF - * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -package org.lwjgl.opengl; - -import java.lang.reflect.*; - -import org.lwjgl.Sys; - -/** - * $Id$ - * - * Mac OS X specific hacks - * - * @author elias_naur - * @author Brian Matzon - * @version $Revision$ - */ -class MacOSX { - /** - * Initializes the Mac OS X specific hack - */ - public static void initMacOSX() { - - java.awt.Toolkit.getDefaultToolkit(); - - // Add ourselves to quit requested, using reflection to allow - // compiling on other platforms - try { - Class appClass = Class.forName("com.apple.eawt.Application"); - Class listenerClass = Class.forName("com.apple.eawt.ApplicationListener"); - Object appInstance = appClass.newInstance(); - // create proxy for adapter - Object proxyInvoker = Proxy.newProxyInstance(listenerClass.getClassLoader(), new Class[]{listenerClass}, new Invokee()); - Method addApplicationListener = appClass.getMethod("addApplicationListener", new Class[]{listenerClass}); - addApplicationListener.invoke(appInstance, new Object[]{proxyInvoker}); - } catch (Exception e) { - // validate success - if (Sys.DEBUG) { - System.out.println("Unable to invoke 'addApplicationListener' method because of " + e); - } - } - } - - /** - * Even more hackish proxy class for allowing mac os x to be compiled on all platforms - * - * @author Brian Matzon - */ - static private class Invokee implements InvocationHandler { - /** - * Called when the actual method of the proxied class is called - * - * @param proxy Object being proxied - * @param method Method being invoked - * @param args Arguments for that specific method - */ - public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { - try { - // Return if we were not called through handleQuit - Class applicationEventClass = Class.forName("com.apple.eawt.ApplicationEvent"); - Class applicationListenerClass = Class.forName("com.apple.eawt.ApplicationListener"); - Method handleQuitMethod = applicationListenerClass.getMethod("handleQuit", new Class[]{applicationEventClass}); - if (!method.equals(handleQuitMethod)) - return null; - // invoke setHandled(false); - Method setHandled = args[0].getClass().getMethod("setHandled", new Class[] {boolean.class}); - setHandled.invoke(args[0], new Object[]{new Boolean(false)}); - // just call setQuitRequested - setQuitRequested(); - } catch (Exception e) { - if (Sys.DEBUG) { - System.out.println("Unable to invoke 'setHandled' because of " + e); - } - } - return null; - } - } - - /** Notifies the native implementation that a quit event has been received */ - private static native void setQuitRequested(); -} diff --git a/src/java/org/lwjgl/opengl/Window.java b/src/java/org/lwjgl/opengl/Window.java index 471c2616..52cc8436 100644 --- a/src/java/org/lwjgl/opengl/Window.java +++ b/src/java/org/lwjgl/opengl/Window.java @@ -30,32 +30,6 @@ public final class Window { static { System.loadLibrary(Sys.getLibraryName()); - /* - * elias: Mac OS X hacks. We need to fetch the toolkit to acquire a Dock icon, a system menu - * and to make windows behave normally. We also need to intercept the quit event from - * Swing. Luckily, Swing can be assumed to be present on Mac OS X. Because some of this - * is apple extensions to java, we need stub files to successfully compile on other platforms. - * - * Additionally, because of the way swing works, applications now need to do an - * explicit System.exit() to quit. Returning from the main thread is not enough any - * more. - * - * I've wasted a significant amount of time searching for an acceptable solution, without - * finding a way to avoid Swing. AFAIK, - * - * 1. There's no way to acquire the Dock icon, system menu and normal window behaviour. - * For that, you either need a proper bundled, native application or initialize Swing. - * 2. Even if there were a way around it, Swing is automatically started anyway if you - * use Java Web Start. - * 3. Swing gains total control over the main event loop, so the native library need to - * work around by maintaining an internal event queue. That's really boring stuff, indeed. - * - * I have posted a bug report to apple regarding the behaviour. - * - */ - if (Display.getPlatform() == Display.PLATFORM_AGL) { - MacOSX.initMacOSX(); - } } /** Whether the window is currently created, ie. has a native peer */ diff --git a/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java b/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java index 41eba308..84289039 100644 --- a/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java +++ b/src/java/org/lwjgl/test/opengl/FullScreenWindowedTest.java @@ -140,6 +140,7 @@ public class FullScreenWindowedTest { } } } + Display.resetDisplayMode(); } /** @@ -292,7 +293,7 @@ public class FullScreenWindowedTest { for (int i = 0; i < modes.length; i++) { if (modes[i].width == width && modes[i].height == height - && modes[i].bpp >= bpp) { + && modes[i].bpp >= bpp && modes[i].freq <= 60) { return modes[i]; } } diff --git a/src/native/common/extal.cpp b/src/native/common/extal.cpp index 8a2f28f8..1ff000b8 100644 --- a/src/native/common/extal.cpp +++ b/src/native/common/extal.cpp @@ -127,7 +127,8 @@ HMODULE handleOAL; void* handleOAL; #endif #ifdef _AGL -#include +#include +#include OSStatus oalInitEntryPoints (void); void oalDellocEntryPoints (void); CFBundleRef handleOAL = NULL; diff --git a/src/native/configure.in b/src/native/configure.in index 3f259720..d0a435c9 100644 --- a/src/native/configure.in +++ b/src/native/configure.in @@ -30,7 +30,7 @@ AC_CANONICAL_HOST case "$host_os" in darwin*) _BUILD_FLAGS="-D_AGL -fpascal-strings" - LDFLAGS="-Xlinker -framework -Xlinker Carbon -Xlinker -framework -Xlinker QuickTime -Xlinker -framework -Xlinker JavaVM" + LDFLAGS="-Xlinker -framework -Xlinker JavaVM -Xlinker -framework -Xlinker ApplicationServices -Xlinker -framework -Xlinker CoreServices" NATIVE_BUILD_DIR=macosx CXXFLAGS="$CXXFLAGS $DEBUG_FLAGS -Wall $_BUILD_FLAGS" CFLAGS="$CFLAGS $DEBUG_FLAGS -Wall $_BUILD_FLAGS" diff --git a/src/native/macosx/Makefile.am b/src/native/macosx/Makefile.am index 61a16f3d..03673bc9 100644 --- a/src/native/macosx/Makefile.am +++ b/src/native/macosx/Makefile.am @@ -8,8 +8,8 @@ NATIVE = \ org_lwjgl_Sys.cpp \ org_lwjgl_input_Controller.cpp \ org_lwjgl_input_Keyboard.cpp \ - org_lwjgl_opengl_MacOSX.cpp \ tools.cpp \ + hid.cpp \ org_lwjgl_input_Mouse.cpp \ org_lwjgl_input_Cursor.cpp \ org_lwjgl_opengl_Window.cpp diff --git a/src/native/macosx/Window.h b/src/native/macosx/Window.h index 0ad13ecc..4e4b1c07 100644 --- a/src/native/macosx/Window.h +++ b/src/native/macosx/Window.h @@ -43,10 +43,8 @@ #define _LWJGL_WINDOW_H_INCLUDED_ #include - #include extern void setQuitRequested(void); - extern bool registerKeyboardHandler(JNIEnv* env, WindowRef win_ref); -// extern bool registerMouseHandler(JNIEnv* env, WindowRef win_ref); - extern bool isMouseCreated(void); + extern void resetMode(JNIEnv *env); + extern void switchMode(JNIEnv *env, long width, long height, long bpp, long freq); #endif /* _LWJGL_WINDOW_H_INCLUDED_ */ diff --git a/src/native/macosx/hid.cpp b/src/native/macosx/hid.cpp new file mode 100644 index 00000000..36a9009a --- /dev/null +++ b/src/native/macosx/hid.cpp @@ -0,0 +1,237 @@ +/* + * Copyright (c) 2002 Light Weight Java Game Library Project + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * * Neither the name of 'Light Weight Java Game Library' nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/** + * $Id$ + * + * Mac OS X mouse handling. + * + * @author elias_naur + * @version $Revision$ + */ + +#include "hid.h" +#include "tools.h" + +static void searchDictionary(CFDictionaryRef dict, hid_device_t *hid_dev, int num_cookies, hid_cookie_t *hid_cookies); +static void searchObject(CFTypeRef object, hid_device_t *hid_dev, int num_cookies, hid_cookie_t *hid_cookies); + +/*static void printCFString(CFStringRef str) { + CFIndex buffer_size = CFStringGetLength(str) + 1; + char * buffer = (char *)malloc(buffer_size); + if (buffer != NULL) { + if (CFStringGetCString(str, buffer, buffer_size, CFStringGetSystemEncoding())) + printf("%s", buffer); + free(buffer); + } +} + +static void printCFNumber(CFNumberRef num) { + long number; + + if (CFNumberGetValue(num, kCFNumberLongType, &number)) + printf("0x%lx (%ld)", number, number); +} +*/ + +/*static void printProperty(CFDictionaryRef dict, CFStringRef key) { + CFTypeRef val = CFDictionaryGetValue(dict, key); + if (val != NULL) { + CFTypeID type = CFGetTypeID(val); + if (type == CFArrayGetTypeID()) printf("array\n"); + else if (type == CFBooleanGetTypeID()) printf("boolean\n"); + else if (type == CFDictionaryGetTypeID()) printf("dictionary\n"); + else if (type == CFNumberGetTypeID()) printCFNumber((CFNumberRef)val); + else if (type == CFStringGetTypeID()) printCFString((CFStringRef)val); + else printf("\n"); + } +} +*/ + +static void closeDeviceAndQueue(hid_device_t *hid_dev) { + (*hid_dev->device_queue)->dispose(hid_dev->device_queue); + (*hid_dev->device_queue)->Release(hid_dev->device_queue); + (*hid_dev->device_interface)->close(hid_dev->device_interface); +} + +static void closeDeviceAll(hid_device_t *hid_dev) { + closeDeviceAndQueue(hid_dev); + CFRelease(hid_dev->cookie_map); +} + +static IOHIDQueueInterface **allocDeviceQueue(IOHIDDeviceInterface **device_interface, int buffer_size) { + IOHIDQueueInterface **device_queue = (*device_interface)->allocQueue(device_interface); + if (device_queue == NULL) + return false; + HRESULT err = (*device_queue)->create(device_queue, 0, buffer_size); + if (err != S_OK) { + (*device_queue)->Release(device_queue); + return NULL; + } + return device_queue; +} + +static void searchArray(CFArrayRef array, hid_device_t *hid_dev, int num_cookies, hid_cookie_t *hid_cookies) { + int size = CFArrayGetCount(array); + for (int i = 0; i < size; i++) { + CFTypeRef value = (CFTypeRef)CFArrayGetValueAtIndex(array, i); + searchObject(value, hid_dev, num_cookies, hid_cookies); + } +} + +static void searchObject(CFTypeRef object, hid_device_t *hid_dev, int num_cookies, hid_cookie_t *hid_cookies) { + CFTypeID type = CFGetTypeID(object); + if (type == CFArrayGetTypeID()) searchArray((CFArrayRef)object, hid_dev, num_cookies, hid_cookies); + else if (type == CFDictionaryGetTypeID()) searchDictionary((CFDictionaryRef)object, hid_dev, num_cookies, hid_cookies); + else printf("\n"); +} + +static void searchDictionaryElement(CFDictionaryRef dict, CFStringRef key, hid_device_t *hid_dev, int num_cookies, hid_cookie_t *hid_cookies) { + CFTypeRef object = CFDictionaryGetValue(dict, key); + if (object != NULL) + searchObject(object, hid_dev, num_cookies, hid_cookies); +} + +static void addToDeviceQueue(hid_device_t *hid_dev, IOHIDElementCookie cookie, int index) { + HRESULT result = (*hid_dev->device_queue)->addElement(hid_dev->device_queue, cookie, 0); + if (result != S_OK) { +#ifdef _DEBUG + printf("Could not add cookie to queue\n"); +#endif + return; + } + CFDictionaryAddValue(hid_dev->cookie_map, cookie, (void *)index); +} + +static void searchDictionary(CFDictionaryRef dict, hid_device_t *hid_dev, int num_cookies, hid_cookie_t *hid_cookies) { + searchDictionaryElement(dict, CFSTR(kIOHIDElementKey), hid_dev, num_cookies, hid_cookies); + long cookie_num; + long usage; + long usage_page; + if (!getDictLong(dict, CFSTR(kIOHIDElementCookieKey), &cookie_num) || + !getDictLong(dict, CFSTR(kIOHIDElementUsageKey), &usage) || + !getDictLong(dict, CFSTR(kIOHIDElementUsagePageKey), &usage_page)) + return; + for (int i = 0; i < num_cookies; i++) { + if (hid_cookies[i].usage_page != kHIDPage_Undefined && hid_cookies[i].usage != kHIDUsage_Undefined && + usage_page == hid_cookies[i].usage_page && usage == hid_cookies[i].usage) { + addToDeviceQueue(hid_dev, (IOHIDElementCookie)cookie_num, i); + } + } +} + +static bool initDevice(hid_device_t *hid_dev, io_object_t hid_device, CFDictionaryRef dict, int num_cookies, hid_cookie_t *hid_cookies, int buffer_size) { + io_name_t class_name; + IOCFPlugInInterface **plugin_interface; + SInt32 score; + IOReturn io_err = IOObjectGetClass(hid_device, class_name); + if (io_err != kIOReturnSuccess) + return false; + io_err = IOCreatePlugInInterfaceForService(hid_device, kIOHIDDeviceUserClientTypeID, kIOCFPlugInInterfaceID, &plugin_interface, &score); + if (io_err != kIOReturnSuccess) + return false; + HRESULT plugin_err = (*plugin_interface)->QueryInterface(plugin_interface, CFUUIDGetUUIDBytes(kIOHIDDeviceInterfaceID), (LPVOID *)(&(hid_dev->device_interface))); + (*plugin_interface)->Release(plugin_interface); + if (plugin_err != S_OK) + return false; + io_err = (*hid_dev->device_interface)->open(hid_dev->device_interface, 0); + if (io_err != kIOReturnSuccess) + return false; + hid_dev->device_queue = allocDeviceQueue(hid_dev->device_interface, buffer_size); + if (hid_dev->device_queue == NULL) { + (*hid_dev->device_interface)->close(hid_dev->device_interface); + return false; + } + hid_dev->cookie_map = CFDictionaryCreateMutable(NULL, 0, NULL, NULL); + if (hid_dev->cookie_map == NULL) { + closeDeviceAndQueue(hid_dev); + return false; + } + searchDictionary(dict, hid_dev, num_cookies, hid_cookies); + HRESULT err = (*hid_dev->device_queue)->start(hid_dev->device_queue); + if (err != S_OK) { + closeDeviceAll(hid_dev); + return false; + } + return true; +} + +bool findDevice(hid_device_t *hid_dev, long device_usage_page, long device_usage, int num_cookies, hid_cookie_t *hid_cookies, int buffer_size) { + io_iterator_t device_iterator; + io_object_t hid_device; + kern_return_t kern_err; + bool success = false; + CFMutableDictionaryRef dev_props; + CFDictionaryRef matching_dic = IOServiceMatching(kIOHIDDeviceKey); + IOReturn err = IOServiceGetMatchingServices(kIOMasterPortDefault, matching_dic, &device_iterator); + if (err != kIOReturnSuccess) { +#ifdef _DEBUG + printf("Could not find matching devices\n"); +#endif + return false; + } + while (!success && (hid_device = IOIteratorNext(device_iterator)) != NULL) { + kern_err = IORegistryEntryCreateCFProperties(hid_device, &dev_props, kCFAllocatorDefault, kNilOptions); + if (kern_err == KERN_SUCCESS && dev_props != NULL) { + long usage; + long usage_page; + if (getDictLong(dev_props, CFSTR(kIOHIDPrimaryUsageKey), &usage) && + getDictLong(dev_props, CFSTR(kIOHIDPrimaryUsagePageKey), &usage_page) && + usage_page == device_usage_page && usage == device_usage) { + success = initDevice(hid_dev, hid_device, dev_props, num_cookies, hid_cookies, buffer_size); + } + CFRelease(dev_props); + } + IOObjectRelease(hid_device); + if (success) + break; + } + IOObjectRelease(device_iterator); + return success; +} + +void shutdownDevice(hid_device_t *hid_dev) { + (*hid_dev->device_queue)->stop(hid_dev->device_queue); + closeDeviceAll(hid_dev); +} + +bool nextDeviceEvent(hid_device_t *hid_dev, hid_event_t *hid_event) { + IOHIDEventStruct event; + AbsoluteTime zero_time = {0, 0}; + HRESULT err = (*hid_dev->device_queue)->getNextEvent(hid_dev->device_queue, &event, zero_time, 0); + if (err != S_OK) + return false; + const void *mapped_index = CFDictionaryGetValue(hid_dev->cookie_map, event.elementCookie); + hid_event->cookie_index = mapped_index; + hid_event->value = (int)event.value; + return true; +} diff --git a/src/native/macosx/org_lwjgl_opengl_MacOSX.cpp b/src/native/macosx/hid.h similarity index 67% rename from src/native/macosx/org_lwjgl_opengl_MacOSX.cpp rename to src/native/macosx/hid.h index 90df06d5..b83350c5 100644 --- a/src/native/macosx/org_lwjgl_opengl_MacOSX.cpp +++ b/src/native/macosx/hid.h @@ -33,13 +33,40 @@ /** * $Id$ * + * Mac OS X HID tools. + * * @author elias_naur * @version $Revision$ */ -#include "Window.h" -#include "org_lwjgl_opengl_MacOSX.h" +#ifndef _HID_H +#define _HID_H -JNIEXPORT void JNICALL Java_org_lwjgl_opengl_MacOSX_setQuitRequested(JNIEnv *, jclass) { - setQuitRequested(); -} +#include +#include +#include +#include +#include +#include + +typedef struct { + IOHIDDeviceInterface **device_interface; + IOHIDQueueInterface **device_queue; + CFMutableDictionaryRef cookie_map; +} hid_device_t; + +typedef struct { + long usage_page; + long usage; +} hid_cookie_t; + +typedef struct { + int cookie_index; + long value; +} hid_event_t; + +extern void shutdownDevice(hid_device_t *hid_dev); +extern bool findDevice(hid_device_t *hid_dev, long usage_page_match, long usage_match, int num_cookies, hid_cookie_t *device_cookies, int buffer_size); +extern bool nextDeviceEvent(hid_device_t *hid_dev, hid_event_t *hid_event); + +#endif diff --git a/src/native/macosx/org_lwjgl_Display.cpp b/src/native/macosx/org_lwjgl_Display.cpp index f014348c..bfbb338d 100644 --- a/src/native/macosx/org_lwjgl_Display.cpp +++ b/src/native/macosx/org_lwjgl_Display.cpp @@ -39,14 +39,24 @@ * @version $Revision$ */ +#include #include "org_lwjgl_Display.h" #include "common_tools.h" #include "tools.h" static CFDictionaryRef original_mode; +static bool initialized = false; -static void init(JNIEnv *env, jclass clazz) { - original_mode = CGDisplayCurrentMode(kCGDirectMainDisplay); +static void saveMode(JNIEnv *env, long width, long height, long bpp, long freq) { + jclass display_class = env->FindClass("org/lwjgl/Display"); + jclass jclass_DisplayMode = env->FindClass("org/lwjgl/DisplayMode"); + jmethodID ctor = env->GetMethodID(jclass_DisplayMode, "", "(IIII)V"); + jobject newMode = env->NewObject(jclass_DisplayMode, ctor, width, height, bpp, freq); + jfieldID fid_initialMode = env->GetStaticFieldID(display_class, "mode", "Lorg/lwjgl/DisplayMode;"); + env->SetStaticObjectField(display_class, fid_initialMode, newMode); +} + +static void saveOriginalMode(JNIEnv *env) { long width; long height; long bpp; @@ -55,15 +65,33 @@ static void init(JNIEnv *env, jclass clazz) { getDictLong(original_mode, kCGDisplayHeight, &height); getDictLong(original_mode, kCGDisplayBitsPerPixel, &bpp); getDictLong(original_mode, kCGDisplayRefreshRate, &freq); - jclass jclass_DisplayMode = env->FindClass("org/lwjgl/DisplayMode"); - jmethodID ctor = env->GetMethodID(jclass_DisplayMode, "", "(IIII)V"); - jobject newMode = env->NewObject(jclass_DisplayMode, ctor, width, height, bpp, freq); - jfieldID fid_initialMode = env->GetStaticFieldID(clazz, "mode", "Lorg/lwjgl/DisplayMode;"); - env->SetStaticObjectField(clazz, fid_initialMode, newMode); + saveMode(env, width, height, bpp, freq); +} + +static void init(JNIEnv *env) { + if (!initialized) { + initialized = true; + original_mode = CGDisplayCurrentMode(kCGDirectMainDisplay); + saveOriginalMode(env); + } +} + +void switchMode(JNIEnv *env, long width, long height, long bpp, long freq) { + init(env); + CGDisplayCapture(kCGDirectMainDisplay); + CFDictionaryRef displayMode = CGDisplayBestModeForParametersAndRefreshRate(kCGDirectMainDisplay, bpp, width, height, freq, NULL); + CGDisplaySwitchToMode(kCGDirectMainDisplay, displayMode); + saveMode(env, width, height, bpp, freq); +} + +void resetMode(JNIEnv *env) { + CGDisplaySwitchToMode(kCGDirectMainDisplay, original_mode); + CGDisplayRelease(kCGDirectMainDisplay); + saveOriginalMode(env); } JNIEXPORT void JNICALL Java_org_lwjgl_Display_init(JNIEnv * env, jclass clazz) { - init(env, clazz); + init(env); } JNIEXPORT void JNICALL Java_org_lwjgl_Display_setDisplayMode(JNIEnv * env, jclass clazz, jobject mode) { @@ -76,14 +104,7 @@ JNIEXPORT void JNICALL Java_org_lwjgl_Display_setDisplayMode(JNIEnv * env, jclas int height = env->GetIntField(mode, fid_height); int bpp = env->GetIntField(mode, fid_bpp); int freq = env->GetIntField(mode, fid_freq); - CGDisplayCapture(kCGDirectMainDisplay); - CFDictionaryRef displayMode = CGDisplayBestModeForParametersAndRefreshRate(kCGDirectMainDisplay, bpp, width, height, freq, NULL); - CGDisplaySwitchToMode(kCGDirectMainDisplay, displayMode); - - jmethodID ctor = env->GetMethodID(cls_displayMode, "", "(IIII)V"); - jobject newMode = env->NewObject(cls_displayMode, ctor, width, height, bpp, freq); - jfieldID fid_initialMode = env->GetStaticFieldID(clazz, "mode", "Lorg/lwjgl/DisplayMode;"); - env->SetStaticObjectField(clazz, fid_initialMode, newMode); + switchMode(env, width, height, bpp, freq); } JNIEXPORT jobjectArray JNICALL Java_org_lwjgl_Display_nGetAvailableDisplayModes(JNIEnv * env, jclass clazz) { @@ -130,9 +151,7 @@ JNIEXPORT jboolean JNICALL Java_org_lwjgl_Display_setGammaRamp(JNIEnv *env, jcla } JNIEXPORT void JNICALL Java_org_lwjgl_Display_resetDisplayMode(JNIEnv *env, jclass clazz) { - CGDisplaySwitchToMode(kCGDirectMainDisplay, original_mode); - CGDisplayRelease(kCGDirectMainDisplay); - init(env, clazz); + resetMode(env); } JNIEXPORT jstring JNICALL Java_org_lwjgl_Display_getAdapter(JNIEnv * , jclass) { diff --git a/src/native/macosx/org_lwjgl_input_Keyboard.cpp b/src/native/macosx/org_lwjgl_input_Keyboard.cpp index 532ab012..1049f43b 100644 --- a/src/native/macosx/org_lwjgl_input_Keyboard.cpp +++ b/src/native/macosx/org_lwjgl_input_Keyboard.cpp @@ -39,19 +39,20 @@ * @version $Revision$ */ +#include "org_lwjgl_input_Keyboard.h" #include "Window.h" #include "tools.h" -#include "org_lwjgl_input_Keyboard.h" #include "common_tools.h" +#include "hid.h" #define KEYBOARD_SIZE 256 #define UNICODE_BUFFER_SIZE 10 static unsigned char key_buf[KEYBOARD_SIZE]; -static unsigned char key_map[KEYBOARD_SIZE]; static bool buffer_enabled = false; static bool translation_enabled = false; static event_queue_t event_queue; +static hid_device_t hid_dev; static bool handleMappedKey(unsigned char mapped_code, unsigned char state) { unsigned char old_state = key_buf[mapped_code]; @@ -60,12 +61,13 @@ static bool handleMappedKey(unsigned char mapped_code, unsigned char state) { if (buffer_enabled) { putEventElement(&event_queue, mapped_code); putEventElement(&event_queue, state); - return true; + return translation_enabled; } } return false; } +/* static bool handleKey(UInt32 key_code, unsigned char state) { if (key_code >= KEYBOARD_SIZE) { #ifdef _DEBUG @@ -146,7 +148,6 @@ static pascal OSStatus doKeyDown(EventHandlerCallRef next_handler, EventRef even #endif return eventNotHandledErr; } - lock(); if (handleKey(key_code, 1)) { if (translation_enabled) { if (!handleUnicode(event)) { @@ -158,7 +159,6 @@ static pascal OSStatus doKeyDown(EventHandlerCallRef next_handler, EventRef even putEventElement(&event_queue, 0); } } - unlock(); return noErr; } @@ -171,12 +171,10 @@ static pascal OSStatus doKeyUp(EventHandlerCallRef next_handler, EventRef event, #endif return eventNotHandledErr; } - lock(); if (handleKey(key_code, 0)) { putEventElement(&event_queue, 0); putEventElement(&event_queue, 0); } - unlock(); return noErr; } @@ -211,13 +209,6 @@ static pascal OSStatus doKeyModifier(EventHandlerCallRef next_handler, EventRef return noErr; } -bool registerKeyboardHandler(JNIEnv* env, WindowRef win_ref) { - bool error = registerHandler(env, win_ref, doKeyUp, kEventClassKeyboard, kEventRawKeyUp); - error = error || registerHandler(env, win_ref, doKeyDown, kEventClassKeyboard, kEventRawKeyDown); - error = error || registerHandler(env, win_ref, doKeyModifier, kEventClassKeyboard, kEventRawKeyModifiersChanged); - return !error; -} - static void setupMappings(void) { memset(key_map, 0, KEYBOARD_SIZE*sizeof(unsigned char)); key_map[0x35] = org_lwjgl_input_Keyboard_KEY_ESCAPE; @@ -309,40 +300,195 @@ static void setupMappings(void) { key_map[0x7d] = org_lwjgl_input_Keyboard_KEY_DOWN; key_map[0x79] = org_lwjgl_input_Keyboard_KEY_NEXT; } +*/ + +static void initCookie(hid_cookie_t *hid_cookies, int index, long usage) { + hid_cookies[index].usage_page = kHIDPage_KeyboardOrKeypad; + hid_cookies[index].usage = usage; +} + +static void initCookies(hid_cookie_t *hid_cookies) { + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_ESCAPE, kHIDUsage_KeyboardEscape); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_1, kHIDUsage_Keyboard1); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_2, kHIDUsage_Keyboard2); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_3, kHIDUsage_Keyboard3); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_4, kHIDUsage_Keyboard4); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_5, kHIDUsage_Keyboard5); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_6, kHIDUsage_Keyboard6); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_7, kHIDUsage_Keyboard7); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_8, kHIDUsage_Keyboard8); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_9, kHIDUsage_Keyboard9); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_0, kHIDUsage_Keyboard0); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_MINUS, kHIDUsage_KeyboardHyphen); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_EQUALS, kHIDUsage_KeyboardEqualSign); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_BACK, kHIDUsage_KeyboardDeleteOrBackspace); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_TAB, kHIDUsage_KeyboardTab); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_Q, kHIDUsage_KeyboardQ); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_W, kHIDUsage_KeyboardW); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_E, kHIDUsage_KeyboardE); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_R, kHIDUsage_KeyboardR); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_T, kHIDUsage_KeyboardT); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_Y, kHIDUsage_KeyboardY); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_U, kHIDUsage_KeyboardU); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_I, kHIDUsage_KeyboardI); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_O, kHIDUsage_KeyboardO); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_P, kHIDUsage_KeyboardP); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_LBRACKET, kHIDUsage_KeyboardOpenBracket); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RBRACKET, kHIDUsage_KeyboardCloseBracket); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RETURN, kHIDUsage_KeyboardReturnOrEnter); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_LCONTROL, kHIDUsage_KeyboardLeftControl); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_A, kHIDUsage_KeyboardA); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_S, kHIDUsage_KeyboardS); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_D, kHIDUsage_KeyboardD); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F, kHIDUsage_KeyboardF); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_G, kHIDUsage_KeyboardG); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_H, kHIDUsage_KeyboardH); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_J, kHIDUsage_KeyboardJ); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_K, kHIDUsage_KeyboardK); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_L, kHIDUsage_KeyboardL); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SEMICOLON, kHIDUsage_KeyboardSemicolon); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_APOSTROPHE, kHIDUsage_KeyboardQuote); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_GRAVE, kHIDUsage_KeyboardGraveAccentAndTilde); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_LSHIFT, kHIDUsage_KeyboardLeftShift); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_BACKSLASH, kHIDUsage_KeyboardBackslash); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_Z, kHIDUsage_KeyboardZ); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_X, kHIDUsage_KeyboardX); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_C, kHIDUsage_KeyboardC); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_V, kHIDUsage_KeyboardV); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_B, kHIDUsage_KeyboardB); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_N, kHIDUsage_KeyboardN); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_M, kHIDUsage_KeyboardM); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_COMMA, kHIDUsage_KeyboardComma); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_PERIOD, kHIDUsage_KeyboardPeriod); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SLASH, kHIDUsage_KeyboardSlash); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RSHIFT, kHIDUsage_KeyboardRightShift); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_MULTIPLY, kHIDUsage_KeypadAsterisk); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_LMENU, kHIDUsage_KeyboardLeftGUI); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SPACE, kHIDUsage_KeyboardSpacebar); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_CAPITAL, kHIDUsage_KeyboardCapsLock); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F1, kHIDUsage_KeyboardF1); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F2, kHIDUsage_KeyboardF2); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F3, kHIDUsage_KeyboardF3); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F4, kHIDUsage_KeyboardF4); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F5, kHIDUsage_KeyboardF5); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F6, kHIDUsage_KeyboardF6); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F7, kHIDUsage_KeyboardF7); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F8, kHIDUsage_KeyboardF8); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F9, kHIDUsage_KeyboardF9); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F10, kHIDUsage_KeyboardF10); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMLOCK, kHIDUsage_KeypadNumLock); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SCROLL, kHIDUsage_KeyboardScrollLock); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD7, kHIDUsage_Keypad7); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD8, kHIDUsage_Keypad8); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD9, kHIDUsage_Keypad9); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SUBTRACT, kHIDUsage_KeypadHyphen); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD4, kHIDUsage_Keypad4); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD5, kHIDUsage_Keypad5); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD6, kHIDUsage_Keypad6); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_ADD, kHIDUsage_KeypadPlus); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD1, kHIDUsage_Keypad1); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD2, kHIDUsage_Keypad2); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD3, kHIDUsage_Keypad3); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPAD0, kHIDUsage_Keypad0); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_DECIMAL, kHIDUsage_KeypadPeriod); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F11, kHIDUsage_KeyboardF11); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F12, kHIDUsage_KeyboardF12); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F13, kHIDUsage_KeyboardF13); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F14, kHIDUsage_KeyboardF14); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_F15, kHIDUsage_KeyboardF15); +/* initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_KANA, kHIDUsage_KeyboardKANA); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_CONVERT, kHIDUsage_KeyboardCONVERT); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NOCONVERT, kHIDUsage_KeyboardNOCONVERT); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_YEN, kHIDUsage_KeyboardYEN); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPADEQUALS, kHIDUsage_KeyboardNUMPADEQUALS); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_CIRCUMFLEX, kHIDUsage_KeyboardCIRCUMFLEX); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_AT, kHIDUsage_KeyboardAT); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_COLON, kHIDUsage_KeyboardCOLON); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_UNDERLINE, kHIDUsage_KeyboardUNDERLINE); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_KANJI, kHIDUsage_KeyboardKANJI); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_STOP, kHIDUsage_KeyboardSTOP); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_AX, kHIDUsage_KeyboardAX); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_UNLABELED, kHIDUsage_KeyboardUNLABELED);*/ + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPADENTER, kHIDUsage_KeypadEnter); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RCONTROL, kHIDUsage_KeyboardRightControl); +// initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NUMPADCOMMA, kHIDUsage_KeyboardNUMPADCOMMA); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_DIVIDE, kHIDUsage_KeypadSlash); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SYSRQ, kHIDUsage_KeyboardSysReqOrAttention); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RMENU, kHIDUsage_KeyboardRightGUI); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_PAUSE, kHIDUsage_KeyboardPause); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_HOME, kHIDUsage_KeyboardHome); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_UP, kHIDUsage_KeyboardUpArrow); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_PRIOR, kHIDUsage_KeyboardPageUp); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_LEFT, kHIDUsage_KeyboardLeftArrow); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RIGHT, kHIDUsage_KeyboardRightArrow); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_END, kHIDUsage_KeyboardEnd); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_DOWN, kHIDUsage_KeyboardDownArrow); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_NEXT, kHIDUsage_KeyboardPageDown); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_INSERT, kHIDUsage_KeyboardInsert); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_DELETE, kHIDUsage_KeyboardDeleteForward); +/* initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_LWIN, kHIDUsage_KeyboardLWIN); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_RWIN, kHIDUsage_KeyboardRWIN);*/ + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_APPS, kHIDUsage_KeyboardApplication); + initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_POWER, kHIDUsage_KeyboardPower); + //initCookie(hid_cookies, org_lwjgl_input_Keyboard_KEY_SLEEP, kHIDUsage_KeyboardSleep); +} + +static void pollKeyboardDevice(void) { + hid_event_t event; + while (nextDeviceEvent(&hid_dev, &event)) { + if (event.cookie_index >= KEYBOARD_SIZE) { +#ifdef _DEBUG + printf("Uknown key code\n"); +#endif + return; + } + unsigned char key_code = (unsigned char)event.cookie_index; + unsigned char state = event.value != 0 ? 1 : 0; + if (handleMappedKey(key_code, state)) { + putEventElement(&event_queue, 0); + putEventElement(&event_queue, 0); + } + } +} JNIEXPORT void JNICALL Java_org_lwjgl_input_Keyboard_initIDs(JNIEnv * env, jclass clazz) { } JNIEXPORT void JNICALL Java_org_lwjgl_input_Keyboard_nCreate(JNIEnv * env, jclass clazz) { - lock(); buffer_enabled = false; translation_enabled = false; initEventQueue(&event_queue); memset(key_buf, 0, KEYBOARD_SIZE*sizeof(unsigned char)); - setupMappings(); - unlock(); + hid_cookie_t hid_cookies[KEYBOARD_SIZE]; + for (int i = 0; i < KEYBOARD_SIZE; i++) { + hid_cookies[i].usage_page = kHIDPage_Undefined; + hid_cookies[i].usage = kHIDUsage_Undefined; + } + initCookies(hid_cookies); + if (!findDevice(&hid_dev, kHIDPage_GenericDesktop, kHIDUsage_GD_Keyboard, KEYBOARD_SIZE, hid_cookies, EVENT_BUFFER_SIZE)) { + throwException(env, "Could not find a keyboard device"); + return; + } } JNIEXPORT void JNICALL Java_org_lwjgl_input_Keyboard_nDestroy(JNIEnv * env, jclass clazz) { + shutdownDevice(&hid_dev); } JNIEXPORT void JNICALL Java_org_lwjgl_input_Keyboard_nPoll(JNIEnv * env, jclass clazz, jobject buffer) { + pollKeyboardDevice(); unsigned char *new_keyboard_buffer = (unsigned char *)env->GetDirectBufferAddress(buffer); - lock(); memcpy(new_keyboard_buffer, key_buf, KEYBOARD_SIZE*sizeof(unsigned char)); - unlock(); } JNIEXPORT jint JNICALL Java_org_lwjgl_input_Keyboard_nRead(JNIEnv * env, jclass clazz) { int num_events = 0; - lock(); int event_size; if (translation_enabled) event_size = 4; else event_size = 2; num_events = copyEvents(&event_queue, event_size); - unlock(); return num_events; } diff --git a/src/native/macosx/org_lwjgl_input_Mouse.cpp b/src/native/macosx/org_lwjgl_input_Mouse.cpp index e91279f0..a7d16285 100644 --- a/src/native/macosx/org_lwjgl_input_Mouse.cpp +++ b/src/native/macosx/org_lwjgl_input_Mouse.cpp @@ -39,18 +39,15 @@ * @version $Revision$ */ -#include -#include -#include -#include -#include +#include +#include "org_lwjgl_input_Mouse.h" #include "Window.h" #include "tools.h" #include "common_tools.h" -#include "org_lwjgl_input_Mouse.h" -#include "common_tools.h" +#include "hid.h" -#define NUM_BUTTONS 7 +static const int NUM_BUTTONS = 7; +static const int NUM_COOKIES = NUM_BUTTONS + 3; static jfieldID fid_dx; static jfieldID fid_dy; @@ -58,237 +55,18 @@ static jfieldID fid_dwheel; static jfieldID fid_buttons; static unsigned char button_states[NUM_BUTTONS]; -/*static int last_x; -static int last_y;*/ -//static bool native_cursor; static bool created; static bool buffer_enabled; -static IOHIDDeviceInterface **device_interface; -static IOHIDQueueInterface **device_queue; -static IOHIDElementCookie x_axis_cookie; -static IOHIDElementCookie y_axis_cookie; -static IOHIDElementCookie z_axis_cookie; -static IOHIDElementCookie button_cookies[NUM_BUTTONS]; - +static int x_axis_index = NUM_BUTTONS; +static int y_axis_index = NUM_BUTTONS + 1; +static int z_axis_index = NUM_BUTTONS + 2; +static hid_device_t hid_dev; static event_queue_t event_queue; static int last_dx; static int last_dy; static int last_dz; -static void searchDictionary(CFDictionaryRef dict); -static void searchObject(CFTypeRef object); - -bool isMouseCreated(void) { - return created/* && !native_cursor*/; -} - -/*static pascal OSStatus doMouseMoved(EventHandlerCallRef next_handler, EventRef event, void *user_data) { -printf("Mouse moved\n"); - return eventNotHandledErr; // allow the event to propagate -} - -static pascal OSStatus doMouseDown(EventHandlerCallRef next_handler, EventRef event, void *user_data) { -printf("Mouse down\n"); - lock(); - unlock(); - return eventNotHandledErr; // allow the event to propagate -} - -static pascal OSStatus doMouseUp(EventHandlerCallRef next_handler, EventRef event, void *user_data) { -printf("Mouse up\n"); - lock(); - unlock(); - return eventNotHandledErr; // allow the event to propagate -} - -static pascal OSStatus doMouseWheel(EventHandlerCallRef next_handler, EventRef event, void *user_data) { -printf("Mouse wheel\n"); - lock(); - unlock(); - return noErr; -} - -bool registerMouseHandler(JNIEnv* env, WindowRef win_ref) { - bool error = registerHandler(env, win_ref, doMouseDown, kEventClassMouse, kEventMouseDown); - error = error || registerHandler(env, win_ref, doMouseUp, kEventClassMouse, kEventMouseUp); - //error = error || registerHandler(env, win_ref, doMouseMoved, kEventClassMouse, kEventMouseMoved); - error = error || registerHandler(env, win_ref, doMouseWheel, kEventClassMouse, kEventMouseWheelMoved); - return !error; -} -*/ -/*static void printCFString(CFStringRef str) { - CFIndex buffer_size = CFStringGetLength(str) + 1; - char * buffer = (char *)malloc(buffer_size); - if (buffer != NULL) { - if (CFStringGetCString(str, buffer, buffer_size, CFStringGetSystemEncoding())) - printf("%s", buffer); - free(buffer); - } -} - -static void printCFNumber(CFNumberRef num) { - long number; - - if (CFNumberGetValue(num, kCFNumberLongType, &number)) - printf("0x%lx (%ld)", number, number); -} -*/ - -/*static void printProperty(CFDictionaryRef dict, CFStringRef key) { - CFTypeRef val = CFDictionaryGetValue(dict, key); - if (val != NULL) { - CFTypeID type = CFGetTypeID(val); - if (type == CFArrayGetTypeID()) printf("array\n"); - else if (type == CFBooleanGetTypeID()) printf("boolean\n"); - else if (type == CFDictionaryGetTypeID()) printf("dictionary\n"); - else if (type == CFNumberGetTypeID()) printCFNumber((CFNumberRef)val); - else if (type == CFStringGetTypeID()) printCFString((CFStringRef)val); - else printf("\n"); - } -} -*/ -static void closeDevice(void) { - (*device_queue)->dispose(device_queue); - (*device_queue)->Release(device_queue); - (*device_interface)->close(device_interface); -} - -static void shutdownDevice(void) { - (*device_queue)->stop(device_queue); - closeDevice(); -} - -static bool allocDeviceQueue(void) { - device_queue = (*device_interface)->allocQueue(device_interface); - if (device_queue == NULL) - return false; - HRESULT err = (*device_queue)->create(device_queue, 0, EVENT_BUFFER_SIZE); - if (err != S_OK) { - (*device_queue)->Release(device_queue); - return false; - } - return true; -} - -static void searchArrayElement(const void * value, void * parameter) { - searchObject((CFTypeRef)value); -} - -static void searchArray(CFArrayRef array) { - CFRange range = {0, CFArrayGetCount(array)}; - CFArrayApplyFunction(array, range, searchArrayElement, 0); -} - -static void searchObject(CFTypeRef object) { - CFTypeID type = CFGetTypeID(object); - if (type == CFArrayGetTypeID()) searchArray((CFArrayRef)object); - else if (type == CFDictionaryGetTypeID()) searchDictionary((CFDictionaryRef)object); - else printf("\n"); -} - -static void searchDictionaryElement(CFDictionaryRef dict, CFStringRef key) { - CFTypeRef object = CFDictionaryGetValue(dict, key); - if (object != NULL) - searchObject(object); -} - -static void addToDeviceQueue(IOHIDElementCookie cookie) { - HRESULT result = (*device_queue)->addElement(device_queue, cookie, 0); - if (result != S_OK) { -#ifdef _DEBUG - printf("Could not add cookie to queue\n"); -#endif - } -} - -static void testCookie(long usage_page, long usage, IOHIDElementCookie cookie, IOHIDElementCookie *store_cookie, long desired_usage_page, long desired_usage) { - if (usage_page == desired_usage_page && usage == desired_usage && *store_cookie == NULL) { - *store_cookie = cookie; - addToDeviceQueue(cookie); - } -} - -static void searchDictionary(CFDictionaryRef dict) { - searchDictionaryElement(dict, CFSTR(kIOHIDElementKey)); - long cookie_num; - long usage; - long usage_page; - if (!getDictLong(dict, CFSTR(kIOHIDElementCookieKey), &cookie_num) || - !getDictLong(dict, CFSTR(kIOHIDElementUsageKey), &usage) || - !getDictLong(dict, CFSTR(kIOHIDElementUsagePageKey), &usage_page)) - return; - testCookie(usage_page, usage, (IOHIDElementCookie)cookie_num, &x_axis_cookie, kHIDPage_GenericDesktop, kHIDUsage_GD_X); - testCookie(usage_page, usage, (IOHIDElementCookie)cookie_num, &y_axis_cookie, kHIDPage_GenericDesktop, kHIDUsage_GD_Y); - testCookie(usage_page, usage, (IOHIDElementCookie)cookie_num, &z_axis_cookie, kHIDPage_GenericDesktop, kHIDUsage_GD_Wheel); - for (int i = 0; i < NUM_BUTTONS; i++) - testCookie(usage_page, usage, (IOHIDElementCookie)cookie_num, &button_cookies[i], kHIDPage_Button, i + 1); -} - -static bool initDevice(io_object_t hid_device, CFDictionaryRef dict) { - io_name_t class_name; - IOCFPlugInInterface **plugin_interface; - SInt32 score; - IOReturn io_err = IOObjectGetClass(hid_device, class_name); - if (io_err != kIOReturnSuccess) - return false; - io_err = IOCreatePlugInInterfaceForService(hid_device, kIOHIDDeviceUserClientTypeID, kIOCFPlugInInterfaceID, &plugin_interface, &score); - if (io_err != kIOReturnSuccess) - return false; - HRESULT plugin_err = (*plugin_interface)->QueryInterface(plugin_interface, CFUUIDGetUUIDBytes(kIOHIDDeviceInterfaceID), (LPVOID *)(&device_interface)); - (*plugin_interface)->Release(plugin_interface); - if (plugin_err != S_OK) - return false; - io_err = (*device_interface)->open(device_interface, 0); - if (io_err != kIOReturnSuccess) - return false; - if (!allocDeviceQueue()) { - (*device_interface)->close(device_interface); - return false; - } - searchDictionary(dict); - HRESULT err = (*device_queue)->start(device_queue); - if (err != S_OK) { - closeDevice(); - return false; - } - return true; -} - -static bool findDevice(void) { - io_iterator_t device_iterator; - io_object_t hid_device; - kern_return_t kern_err; - bool success = false; - CFMutableDictionaryRef dev_props; - CFMutableDictionaryRef matching_dic = IOServiceMatching(kIOHIDDeviceKey); - IOReturn err = IOServiceGetMatchingServices(kIOMasterPortDefault, matching_dic, &device_iterator); - if (err != kIOReturnSuccess) { -#ifdef _DEBUG - printf("Could not find matching devices\n"); -#endif - return false; - } - while (!success && (hid_device = IOIteratorNext(device_iterator)) != NULL) { - kern_err = IORegistryEntryCreateCFProperties(hid_device, &dev_props, kCFAllocatorDefault, kNilOptions); - if (kern_err == KERN_SUCCESS && dev_props != NULL) { - long usage; - long usage_page; - if (getDictLong(dev_props, CFSTR(kIOHIDPrimaryUsageKey), &usage) && - getDictLong(dev_props, CFSTR(kIOHIDPrimaryUsagePageKey), &usage_page) && - usage_page == kHIDPage_GenericDesktop && usage == kHIDUsage_GD_Mouse) { - success = initDevice(hid_device, dev_props); - } - CFRelease(dev_props); - } - IOObjectRelease(hid_device); - if (success) - break; - } - IOObjectRelease(device_iterator); - return success; -} - static void handleButton(unsigned char button_index, unsigned char state) { button_states[button_index] = state; if (buffer_enabled) { @@ -297,31 +75,30 @@ static void handleButton(unsigned char button_index, unsigned char state) { } } -static void pollDevice() { - IOHIDEventStruct event; - AbsoluteTime zero_time = {0, 0}; +static void pollMouseDevice() { + hid_event_t event; cont: - while ((*device_queue)->getNextEvent(device_queue, &event, zero_time, 0) == S_OK) { - IOHIDElementCookie cookie = event.elementCookie; - if (cookie == x_axis_cookie) { + while (nextDeviceEvent(&hid_dev, &event)) { + if (event.cookie_index == x_axis_index) { last_dx += event.value; continue; } - if (cookie == y_axis_cookie) { + else if (event.cookie_index == y_axis_index) { last_dy += event.value; continue; } - if (cookie == z_axis_cookie) { + else if (event.cookie_index == z_axis_index) { last_dz += event.value; continue; - } - for (int i = 0; i < NUM_BUTTONS; i++) { - if (cookie == button_cookies[i]) { - if (event.value != 0) - handleButton(i, 1); - else - handleButton(i, 0); - goto cont; + } else { + for (int i = 0; i < NUM_BUTTONS; i++) { + if (event.cookie_index == i) { + if (event.value != 0) + handleButton(i, 1); + else + handleButton(i, 0); + goto cont; + } } } #ifdef _DEBUG @@ -369,16 +146,23 @@ JNIEXPORT jint JNICALL Java_org_lwjgl_input_Mouse_nGetMaxCursorSize(JNIEnv *env, JNIEXPORT void JNICALL Java_org_lwjgl_input_Mouse_nCreate(JNIEnv * env, jclass clazz) { // native_cursor = false; buffer_enabled = false; - x_axis_cookie = NULL; - y_axis_cookie = NULL; - z_axis_cookie = NULL; resetDeltas(); for (int i = 0; i < NUM_BUTTONS; i++) { button_states[i] = 0; - button_cookies[i] = NULL; } initEventQueue(&event_queue); - if (!findDevice()) { + hid_cookie_t hid_cookies[NUM_COOKIES]; + for (int i = 0; i < NUM_BUTTONS; i++) { + hid_cookies[i].usage_page = kHIDPage_Button; + hid_cookies[i].usage = i + 1; + } + hid_cookies[x_axis_index].usage_page = kHIDPage_GenericDesktop; + hid_cookies[x_axis_index].usage = kHIDUsage_GD_X; + hid_cookies[y_axis_index].usage_page = kHIDPage_GenericDesktop; + hid_cookies[y_axis_index].usage = kHIDUsage_GD_Y; + hid_cookies[z_axis_index].usage_page = kHIDPage_GenericDesktop; + hid_cookies[z_axis_index].usage = kHIDUsage_GD_Wheel; + if (!findDevice(&hid_dev, kHIDPage_GenericDesktop, kHIDUsage_GD_Mouse, NUM_COOKIES, hid_cookies, EVENT_BUFFER_SIZE)) { throwException(env, "Could not find HID muse device"); return; } @@ -388,7 +172,7 @@ JNIEXPORT void JNICALL Java_org_lwjgl_input_Mouse_nCreate(JNIEnv * env, jclass c } JNIEXPORT void JNICALL Java_org_lwjgl_input_Mouse_nDestroy(JNIEnv * env, jclass clazz) { - shutdownDevice(); + shutdownDevice(&hid_dev); // if (!native_cursor) { CGAssociateMouseAndMouseCursorPosition(TRUE); CGDisplayShowCursor(CGMainDisplayID()); @@ -398,7 +182,7 @@ JNIEXPORT void JNICALL Java_org_lwjgl_input_Mouse_nDestroy(JNIEnv * env, jclass JNIEXPORT void JNICALL Java_org_lwjgl_input_Mouse_nPoll(JNIEnv * env, jclass clazz) { int dx, dy, dz; - pollDevice(); + pollMouseDevice(); dz = last_dz; //if (!native_cursor) { dx = last_dx; @@ -426,6 +210,6 @@ JNIEXPORT jobject JNICALL Java_org_lwjgl_input_Mouse_nEnableBuffer(JNIEnv *env, } JNIEXPORT jint JNICALL Java_org_lwjgl_input_Mouse_nRead(JNIEnv *env, jclass clazz) { - pollDevice(); + pollMouseDevice(); return copyEvents(&event_queue, 2); } diff --git a/src/native/macosx/org_lwjgl_opengl_MacOSX.h b/src/native/macosx/org_lwjgl_opengl_MacOSX.h deleted file mode 100644 index e57fb45e..00000000 --- a/src/native/macosx/org_lwjgl_opengl_MacOSX.h +++ /dev/null @@ -1,21 +0,0 @@ -/* DO NOT EDIT THIS FILE - it is machine generated */ -#include -/* Header for class org_lwjgl_opengl_MacOSX */ - -#ifndef _Included_org_lwjgl_opengl_MacOSX -#define _Included_org_lwjgl_opengl_MacOSX -#ifdef __cplusplus -extern "C" { -#endif -/* - * Class: org_lwjgl_opengl_MacOSX - * Method: setQuitRequested - * Signature: ()V - */ -JNIEXPORT void JNICALL Java_org_lwjgl_opengl_MacOSX_setQuitRequested - (JNIEnv *, jclass); - -#ifdef __cplusplus -} -#endif -#endif diff --git a/src/native/macosx/org_lwjgl_opengl_Window.cpp b/src/native/macosx/org_lwjgl_opengl_Window.cpp index 73eeba30..0ad99b1b 100644 --- a/src/native/macosx/org_lwjgl_opengl_Window.cpp +++ b/src/native/macosx/org_lwjgl_opengl_Window.cpp @@ -39,167 +39,27 @@ * @version $Revision$ */ -#include "Window.h" -#include #include #include "org_lwjgl_opengl_Window.h" +#include "Window.h" #include "extgl.h" #include "tools.h" #include "common_tools.h" -static WindowRef win_ref; -static AGLContext windowed_context; -static CGLContextObj fullscreen_context; -static bool close_requested; -static Ptr fullscreen_ptr; +static CGLContextObj context; +static bool vsync_enabled; static bool current_fullscreen; -static bool miniaturized; -static bool activated; -static int center_x; -static int center_y; -static void setWindowTitle(JNIEnv *env, jstring title_obj) { - const char* title = env->GetStringUTFChars(title_obj, NULL); - CFStringRef cf_title = CFStringCreateWithCString(NULL, title, kCFStringEncodingUTF8); - if (cf_title == NULL) { -#ifdef _DEBUG - printf("Could not set window title\n"); -#endif - return; - } - SetWindowTitleWithCFString(win_ref, cf_title); - CFRelease(cf_title); - env->ReleaseStringUTFChars(title_obj, title); +static void destroyMode(JNIEnv *env, jclass clazz) { + if (current_fullscreen); + resetMode(env); } -void setQuitRequested(void) { - lock(); - close_requested = true; - unlock(); -} - -static pascal OSStatus doMiniaturized(EventHandlerCallRef next_handler, EventRef event, void *user_data) { - lock(); - miniaturized = true; - unlock(); - return eventNotHandledErr; -} - -static pascal OSStatus doMaximize(EventHandlerCallRef next_handler, EventRef event, void *user_data) { - lock(); - miniaturized = false; - unlock(); - return eventNotHandledErr; -} - -static void warpCursorToCenter(void) { - CGPoint p = {center_x, center_y}; - CGWarpMouseCursorPosition(p); -} - -static pascal OSStatus doActivate(EventHandlerCallRef next_handler, EventRef event, void *user_data) { - lock(); - miniaturized = false; - activated = true; - if (isMouseCreated()) - warpCursorToCenter(); - unlock(); - return eventNotHandledErr; -} - -static pascal OSStatus doDeactivate(EventHandlerCallRef next_handler, EventRef event, void *user_data) { - lock(); - activated = false; - unlock(); - return eventNotHandledErr; -} - -static pascal OSStatus doQuit(EventHandlerCallRef next_handler, EventRef event, void *user_data) { - setQuitRequested(); - return noErr; -} - -static pascal OSStatus doBoundsChanged(EventHandlerCallRef next_handler, EventRef event, void *user_data) { - Rect rect; - OSStatus err = GetEventParameter(event, kEventParamCurrentBounds, typeQDRectangle, NULL, sizeof(rect), NULL, &rect); - if (err != noErr) { -#ifdef _DEBUG - printf("Could not get bounds from bounds changed event\n"); -#endif - return eventNotHandledErr; - } - lock(); - center_x = (rect.left + rect.right)/2; - center_y = (rect.top + rect.bottom)/2; - unlock(); - return noErr; -} - -static bool registerEventHandlers(JNIEnv *env) { - bool error; - error = registerHandler(env, win_ref, doQuit, kEventClassWindow, kEventWindowClose); - error = error || registerHandler(env, win_ref, doActivate, kEventClassWindow, kEventWindowActivated); - error = error || registerHandler(env, win_ref, doDeactivate, kEventClassWindow, kEventWindowDeactivated); - error = error || registerHandler(env, win_ref, doMiniaturized, kEventClassWindow, kEventWindowCollapsed); - error = error || registerHandler(env, win_ref, doMaximize, kEventClassWindow, kEventWindowExpanded); - error = error || registerHandler(env, win_ref, doBoundsChanged, kEventClassWindow, kEventWindowBoundsChanged); - return !error && registerKeyboardHandler(env, win_ref)/* && registerMouseHandler(env, win_ref)*/; -} - -static void destroyWindow(void) { - if (current_fullscreen) - EndFullScreen(fullscreen_ptr, 0); - else - DisposeWindow(win_ref); -} - -static void destroy(void) { - if (current_fullscreen) { - CGLSetCurrentContext(NULL); - CGLDestroyContext(fullscreen_context); - } else { - aglSetCurrentContext(NULL); - aglDestroyContext(windowed_context); - } - destroyWindow(); +static void destroy(JNIEnv *env, jclass clazz) { + CGLSetCurrentContext(NULL); + CGLDestroyContext(context); + destroyMode(env, clazz); extgl_Close(); - destroyLock(); -} - -static bool createWindowedContext(JNIEnv *env, jint bpp, jint alpha, jint depth, jint stencil) { - AGLDrawable drawable = GetWindowPort(win_ref); - SetPort(drawable); - GLint attrib[] = {AGL_RGBA, - AGL_DOUBLEBUFFER, - AGL_ACCELERATED, - AGL_MINIMUM_POLICY, - AGL_PIXEL_SIZE, bpp, - AGL_DEPTH_SIZE, depth, - AGL_ALPHA_SIZE, alpha, - AGL_STENCIL_SIZE, stencil, - AGL_NONE}; - AGLPixelFormat format = aglChoosePixelFormat(NULL, 0, attrib); - if (format == NULL) { - throwException(env, "Could not find matching pixel format"); - return false; - } - windowed_context = aglCreateContext (format, NULL); - aglDestroyPixelFormat(format); - if (windowed_context == NULL) { - throwException(env, "Could not create context"); - return false; - } - if (aglSetDrawable(windowed_context, drawable) == GL_FALSE) { - aglDestroyContext(windowed_context); - throwException(env, "Could not attach context"); - return false; - } - if (aglSetCurrentContext(windowed_context) == GL_FALSE) { - aglDestroyContext(windowed_context); - throwException(env, "Could not set current context"); - return false; - } - return true; } static bool createFullscreenContext(JNIEnv *env, jint bpp, jint alpha, jint depth, jint stencil) { @@ -226,39 +86,24 @@ static bool createFullscreenContext(JNIEnv *env, jint bpp, jint alpha, jint dept throwException(env, "Could not find matching pixel format"); return false; } - CGLCreateContext(pixel_format, NULL, &fullscreen_context); + CGLCreateContext(pixel_format, NULL, &context); CGLDestroyPixelFormat(pixel_format); - if (fullscreen_context == NULL) { + if (context == NULL) { throwException(env, "Could not create fullscreen context"); return false; } - CGLSetFullScreen(fullscreen_context); - CGLSetCurrentContext(fullscreen_context); + CGLSetFullScreen(context); + CGLSetCurrentContext(context); return true; } JNIEXPORT jboolean JNICALL Java_org_lwjgl_opengl_Window_nIsCloseRequested(JNIEnv *, jclass) { - bool saved; - lock(); - saved = close_requested; - close_requested = false; - unlock(); - return saved; + return JNI_FALSE; } JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_nCreate(JNIEnv *env, jclass clazz, jstring title, jint x, jint y, jint width, jint height, jboolean fullscreen, jint bpp, jint alpha, jint depth, jint stencil, jobject ext_set) { - Rect rect; - OSStatus status; - const WindowAttributes window_attr = kWindowCloseBoxAttribute| - kWindowCollapseBoxAttribute| - kWindowStandardHandlerAttribute; - SetRect(&rect, x, y, x + width, y + height); - center_x = x + width/2; - center_y = y + height/2; - current_fullscreen = fullscreen == JNI_TRUE; - miniaturized = false; - activated = true; - close_requested = false; + vsync_enabled = false; + current_fullscreen = fullscreen == JNI_FALSE; if (!extgl_Open()) { throwException(env, "Could not load gl library"); return; @@ -268,65 +113,27 @@ JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_nCreate(JNIEnv *env, jclass return; } if (current_fullscreen) - status = BeginFullScreen(&fullscreen_ptr, NULL, NULL, NULL, &win_ref, NULL, 0); - else - status = CreateNewWindow(kDocumentWindowClass, window_attr, &rect, &win_ref); - if (noErr != status) { - extgl_Close(); - throwException(env, "Could not create window"); - return; - } - if (!initLock(env)) { - destroyWindow(); - extgl_Close(); - return; - } - if (!registerEventHandlers(env)) { - destroyWindow(); - extgl_Close(); - return; - } - setWindowTitle(env, title); - const RGBColor background_color = {0, 0, 0}; - SetWindowContentColor(win_ref, &background_color); - bool success; - if (current_fullscreen) { - success = createFullscreenContext(env, bpp, alpha, depth, stencil); - } else { - success = createWindowedContext(env, bpp, alpha, depth, stencil); - } - if (!success) { - destroyLock(); - destroyWindow(); + switchMode(env, width, height, bpp, 60); + if (!createFullscreenContext(env, bpp, alpha, depth, stencil)) { + destroyMode(env, clazz); extgl_Close(); return; } if (!extgl_Initialize(env, ext_set)) { - destroy(); + destroy(env, clazz); throwException(env, "Could not load gl function pointers"); return; } - ShowWindow(win_ref); - SelectWindow(win_ref); - warpCursorToCenter(); - CGPoint p = {center_x, center_y}; - CGPostMouseEvent(p, FALSE, 1, TRUE); - CGPostMouseEvent(p, FALSE, 1, FALSE); } JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_nSetTitle(JNIEnv * env, jclass clazz, jstring title_obj) { - setWindowTitle(env, title_obj); } JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_update(JNIEnv *env, jclass clazz) { } JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_swapBuffers(JNIEnv * env, jclass clazz) { - if (current_fullscreen) { - CGLFlushDrawable(fullscreen_context); - } else { - aglSwapBuffers(windowed_context); - } + CGLFlushDrawable(context); } JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_minimize(JNIEnv *env, jclass clazz) { @@ -336,15 +143,11 @@ JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_restore(JNIEnv *env, jclass } JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_nDestroy(JNIEnv *env, jclass clazz) { - destroy(); + destroy(env, clazz); } JNIEXPORT jboolean JNICALL Java_org_lwjgl_opengl_Window_nIsFocused(JNIEnv *env, jclass clazz) { - bool result; - lock(); - result = activated; - unlock(); - return result; + return JNI_TRUE; } JNIEXPORT jboolean JNICALL Java_org_lwjgl_opengl_Window_nIsDirty(JNIEnv *env, jclass clazz) { @@ -352,9 +155,18 @@ JNIEXPORT jboolean JNICALL Java_org_lwjgl_opengl_Window_nIsDirty(JNIEnv *env, jc } JNIEXPORT jboolean JNICALL Java_org_lwjgl_opengl_Window_nIsMinimized(JNIEnv *env, jclass clazz) { - bool result; - lock(); - result = miniaturized; - unlock(); - return result; + return JNI_FALSE; +} + +JNIEXPORT jboolean JNICALL Java_org_lwjgl_opengl_Window_nIsVSyncEnabled(JNIEnv *env, jclass clazz) { + return vsync_enabled; +} + +JNIEXPORT void JNICALL Java_org_lwjgl_opengl_Window_nSetVSyncEnabled(JNIEnv *env, jclass clazz, jboolean enable) { + bool should_enable = enable == JNI_TRUE; + if (vsync_enabled != should_enable) { + vsync_enabled = should_enable; + long swap_interval = vsync_enabled ? 1 : 0; + CGLSetParameter(context, kCGLCPSwapInterval, &swap_interval); + } } diff --git a/src/native/macosx/tools.cpp b/src/native/macosx/tools.cpp index 65ddffb4..0e738ff6 100644 --- a/src/native/macosx/tools.cpp +++ b/src/native/macosx/tools.cpp @@ -14,53 +14,3 @@ bool getDictLong(CFDictionaryRef dict, CFStringRef key, long *key_value) { } return false; } - -bool registerHandler(JNIEnv* env, WindowRef win_ref, EventHandlerProcPtr func, UInt32 event_class, UInt32 event_kind) { - EventTypeSpec event_type; - EventHandlerUPP handler_upp = NewEventHandlerUPP(func); - event_type.eventClass = event_class; - event_type.eventKind = event_kind; - OSStatus err = InstallWindowEventHandler(win_ref, handler_upp, 1, &event_type, NULL, NULL); - DisposeEventHandlerUPP(handler_upp); - if (noErr != err) { - throwException(env, "Could not register window event handler"); - return true; - } - return false; -} - -bool initLock(JNIEnv* env) { - OSStatus err = MPCreateCriticalRegion(&critical_region); - if (err != noErr) { - throwException(env, "Could not init lock"); - return false; - } - return true; -} - -void destroyLock(void) { - OSStatus err = MPDeleteCriticalRegion(critical_region); - if (err != noErr) { -#ifdef _DEBUG - printf("Could not delete lock\n"); -#endif - } -} - -void lockLWJGL(void) { - OSStatus err = MPEnterCriticalRegion(critical_region, kDurationForever); - if (err != noErr) { -#ifdef _DEBUG - printf("Could not lock\n"); -#endif - } -} - -void unlockLWJGL(void) { - OSStatus err = MPExitCriticalRegion(critical_region); - if (err != noErr) { -#ifdef _DEBUG - printf("Could not unlock\n"); -#endif - } -} diff --git a/src/native/macosx/tools.h b/src/native/macosx/tools.h index f77c24ac..8d4c89b9 100644 --- a/src/native/macosx/tools.h +++ b/src/native/macosx/tools.h @@ -2,16 +2,11 @@ #define TOOLS_H #include -#include +#include #define lock() {lockLWJGL(); #define unlock() unlockLWJGL();} extern bool getDictLong(CFDictionaryRef dict, CFStringRef key, long *key_value); -extern bool registerHandler(JNIEnv* env, WindowRef win_ref, EventHandlerProcPtr func, UInt32 event_class, UInt32 event_kind); -extern bool initLock(JNIEnv* env); -extern void destroyLock(void); -extern void lockLWJGL(void); -extern void unlockLWJGL(void); #endif