Sfoglia il codice sorgente

Add glfwInitHint

This allows setting hints that control how the library is initialized,
transforming more compile-time options into run-time ones.
Camilla Löwy 8 anni fa
parent
commit
6d9a58bfef
15 ha cambiato i file con 154 aggiunte e 77 eliminazioni
  1. 0 13
      CMakeLists.txt
  2. 5 0
      README.md
  3. 0 19
      docs/compile.dox
  4. 3 4
      docs/context.dox
  5. 37 0
      docs/intro.dox
  6. 8 0
      docs/news.dox
  7. 2 0
      examples/offscreen.c
  8. 42 4
      include/GLFW/glfw3.h
  9. 3 14
      src/cocoa_init.m
  10. 9 12
      src/cocoa_window.m
  11. 0 5
      src/glfw_config.h.in
  12. 26 4
      src/init.c
  13. 14 0
      src/internal.h
  14. 3 2
      src/window.c
  15. 2 0
      tests/glfwinfo.c

+ 0 - 13
CMakeLists.txt

@@ -40,11 +40,6 @@ if (WIN32)
     option(GLFW_USE_HYBRID_HPG "Force use of high-performance GPU on hybrid systems" OFF)
 endif()
 
-if (APPLE)
-    option(GLFW_USE_CHDIR "Make glfwInit chdir to Contents/Resources" ON)
-    option(GLFW_USE_MENUBAR "Populate the menu bar on first window creation" ON)
-endif()
-
 if (UNIX AND NOT APPLE)
     option(GLFW_USE_WAYLAND "Use Wayland for window creation" OFF)
     option(GLFW_USE_MIR     "Use Mir for window creation" OFF)
@@ -335,14 +330,6 @@ endif()
 #--------------------------------------------------------------------
 if (_GLFW_COCOA)
 
-    if (GLFW_USE_MENUBAR)
-        set(_GLFW_USE_MENUBAR 1)
-    endif()
-
-    if (GLFW_USE_CHDIR)
-        set(_GLFW_USE_CHDIR 1)
-    endif()
-
     list(APPEND glfw_LIBRARIES
         "-framework Cocoa"
         "-framework IOKit"

+ 5 - 0
README.md

@@ -127,6 +127,7 @@ information on what to include when reporting a bug.
 - Added `glfwSetWindowMaximizeCallback` and `GLFWwindowmaximizefun` for
   receiving window maximization events (#778)
 - Added `glfwSetWindowAttrib` function for changing window attributes (#537)
+- Added `glfwInitHint` function for setting library initialization hints
 - Added headless [OSMesa](http://mesa3d.org/osmesa.html) backend (#850)
 - Added definition of `GLAPIENTRY` to public header
 - Added `GLFW_CENTER_CURSOR` window hint for controlling cursor centering
@@ -134,10 +135,14 @@ information on what to include when reporting a bug.
 - Added macOS specific `GLFW_COCOA_RETINA_FRAMEBUFFER` window hint
 - Added macOS specific `GLFW_COCOA_FRAME_AUTOSAVE` window hint (#195)
 - Added macOS specific `GLFW_COCOA_GRAPHICS_SWITCHING` window hint (#377,#935)
+- Added macOS specific `GLFW_COCOA_CHDIR_RESOURCES` init hint
+- Added macOS specific `GLFW_COCOA_MENUBAR` init hint
 - Added `GLFW_INCLUDE_ES32` for including the OpenGL ES 3.2 header
 - Added `GLFW_OSMESA_CONTEXT_API` for creating OpenGL contexts with
   [OSMesa](https://www.mesa3d.org/osmesa.html) (#281)
 - Removed `GLFW_USE_RETINA` compile-time option
+- Removed `GLFW_USE_CHDIR` compile-time option
+- Removed `GLFW_USE_MENUBAR` compile-time option
 - Bugfix: Calling `glfwMaximizeWindow` on a full screen window was not ignored
 - Bugfix: `GLFW_INCLUDE_VULKAN` could not be combined with the corresponding
           OpenGL and OpenGL ES header macros

+ 0 - 19
docs/compile.dox

@@ -219,17 +219,6 @@ __GLFW_VULKAN_STATIC__ determines whether to use the Vulkan loader linked
 statically into the application.
 
 
-@subsubsection compile_options_osx macOS specific CMake options
-
-@anchor GLFW_USE_CHDIR
-__GLFW_USE_CHDIR__ determines whether @ref glfwInit changes the current
-directory of bundled applications to the `Contents/Resources` directory.
-
-@anchor GLFW_USE_MENUBAR
-__GLFW_USE_MENUBAR__ determines whether the first call to @ref glfwCreateWindow
-sets up a minimal menu bar.
-
-
 @subsubsection compile_options_win32 Windows specific CMake options
 
 @anchor USE_MSVC_RUNTIME_LIBRARY_DLL
@@ -281,14 +270,6 @@ For the EGL context creation API, the following options are available:
  - @b _GLFW_USE_EGLPLATFORM_H to use `EGL/eglplatform.h` for native handle
    definitions (fallback)
 
-If you are using the Cocoa window creation API, the following options are
-available:
-
- - @b _GLFW_USE_CHDIR to `chdir` to the `Resources` subdirectory of the
-   application bundle during @ref glfwInit (recommended)
- - @b _GLFW_USE_MENUBAR to create and populate the menu bar when the first window
-   is created (recommended)
-
 @note None of the @ref build_macros may be defined during the compilation of
 GLFW.  If you define any of these in your build files, make sure they are not
 applied to the GLFW sources.

+ 3 - 4
docs/context.dox

@@ -84,10 +84,9 @@ objects are recommended for rendering with such contexts.
 You should still [process events](@ref events) as long as you have at least one
 window, even if none of them are visible.
 
-@macos The first time a window is created the menu bar is populated with
-common commands like Hide, Quit and About.  This is not desirable for example
-when writing a command-line only application.  The menu bar setup can be
-disabled with a [compile-time option](@ref compile_options_osx).
+@macos The first time a window is created the menu bar is created.  This is not
+desirable for example when writing a command-line only application.  Menu bar
+creation can be disabled with the @ref GLFW_COCOA_MENUBAR init hint.
 
 
 @subsection context_less Windows without contexts

+ 37 - 0
docs/intro.dox

@@ -31,6 +31,7 @@ successfully initialized, and only from the main thread.
  - @ref glfwGetVersion
  - @ref glfwGetVersionString
  - @ref glfwSetErrorCallback
+ - @ref glfwInitHint
  - @ref glfwInit
  - @ref glfwTerminate
 
@@ -61,6 +62,42 @@ allocated by programs that simply exit, but GLFW sometimes has to change global
 system settings and these might not be restored without termination.
 
 
+@subsection init_hints Initialization hints
+
+There are a number of hints that can be set before initialization, that affect
+how the library behaves.
+
+The values you set are not affected by initialization or termination, but they
+are only read during initialization.  Once GLFW has been initialized, setting
+new hint values will not affect behavior until the next time it is terminated
+and initialized.
+
+Some hints are platform specific.  These are always valid to set on any
+platform but they will only affect their specific platform.  Other platforms
+will simply ignore them.  Setting these hints requires no platform specific
+headers or calls.
+
+
+@subsubsection init_hints_osx macOS specific hints
+
+@anchor GLFW_COCOA_CHDIR_RESOURCES
+__GLFW_COCOA_CHDIR_RESOURCES__ specifies whether to set the current directory to
+the application to the `Contents/Resources` subdirectory of the application's
+bundle, if present. 
+
+@anchor GLFW_COCOA_MENUBAR
+__GLFW_COCOA_MENUBAR__ specifies whether to create a basic menu bar when the
+first window is created, which is when AppKit is initialized.
+
+
+@subsubsection init_hints_values Supported and default values
+
+Init hint                       | Default value | Supported values
+------------------------------- | ------------- | ----------------
+@ref GLFW_COCOA_CHDIR_RESOURCES | `GLFW_TRUE`   | `GLFW_TRUE` or `GLFW_FALSE`
+@ref GLFW_COCOA_MENUBAR         | `GLFW_TRUE`   | `GLFW_TRUE` or `GLFW_FALSE`
+
+
 @subsection intro_init_terminate Terminating GLFW
 
 Before your application exits, you should terminate the GLFW library if it has

+ 8 - 0
docs/news.dox

@@ -25,6 +25,14 @@ GLFW now supports changing the [GLFW_DECORATED](@ref GLFW_DECORATED_attrib),
 windows with @ref glfwSetWindowAttrib.
 
 
+@subsection news_33_inithint Support for initialization hints
+
+GLFW now supports setting library initialization hints with @ref glfwInitHint.
+Currently the macOS specific @ref
+GLFW_COCOA_CHDIR_RESOURCES and @ref GLFW_COCOA_MENUBAR init hints are supported,
+replacing the corresponding compile-time options.
+
+
 @subsection news_33_centercursor Cursor centering window hint
 
 GLFW now supports controlling whether the cursor is centered over newly created

+ 2 - 0
examples/offscreen.c

@@ -87,6 +87,8 @@ int main(void)
 
     glfwSetErrorCallback(error_callback);
 
+    glfwInitHint(GLFW_COCOA_MENUBAR, GLFW_FALSE);
+
     if (!glfwInit())
         exit(EXIT_FAILURE);
 

+ 42 - 4
include/GLFW/glfw3.h

@@ -926,6 +926,12 @@ extern "C" {
 #define GLFW_CONNECTED              0x00040001
 #define GLFW_DISCONNECTED           0x00040002
 
+/*! @addtogroup init
+ *  @{ */
+#define GLFW_COCOA_CHDIR_RESOURCES  0x00051001
+#define GLFW_COCOA_MENUBAR          0x00051002
+/*! @} */
+
 #define GLFW_DONT_CARE              -1
 
 
@@ -1445,8 +1451,8 @@ typedef struct GLFWimage
  *
  *  @remark @macos This function will change the current directory of the
  *  application to the `Contents/Resources` subdirectory of the application's
- *  bundle, if present.  This can be disabled with a
- *  [compile-time option](@ref compile_options_osx).
+ *  bundle, if present.  This can be disabled with the @ref
+ *  GLFW_COCOA_CHDIR_RESOURCES init hint.
  *
  *  @thread_safety This function must only be called from the main thread.
  *
@@ -1491,6 +1497,39 @@ GLFWAPI int glfwInit(void);
  */
 GLFWAPI void glfwTerminate(void);
 
+/*! @brief Sets the specified init hint to the desired value.
+ *
+ *  This function sets hints for the next initialization of GLFW.
+ *
+ *  The values you set are not affected by initialization or termination, but
+ *  they are only read during initialization.  Once GLFW has been initialized,
+ *  setting new hint values will not affect behavior until the next time the
+ *  library is terminated and initialized.
+ *
+ *  Some hints are platform specific.  These are always valid to set on any
+ *  platform but they will only affect their specific platform.  Other platforms
+ *  will simply ignore them.  Setting these hints requires no platform specific
+ *  headers or calls.
+ *
+ *  @param[in] hint The [init hint](@ref init_hints) to set.
+ *  @param[in] value The new value of the init hint.
+ *
+ *  @errors Possible errors include @ref GLFW_INVALID_ENUM and @ref
+ *  GLFW_INVALID_VALUE.
+ *
+ *  @remarks This function may be called before @ref glfwInit.
+ *
+ *  @thread_safety This function must only be called from the main thread.
+ *
+ *  @sa init_hints
+ *  @sa glfwInit
+ *
+ *  @since Added in version 3.3.
+ *
+ *  @ingroup init
+ */
+GLFWAPI void glfwInitHint(int hint, int value);
+
 /*! @brief Retrieves the version of the GLFW library.
  *
  *  This function retrieves the major, minor and revision numbers of the GLFW
@@ -2049,8 +2088,7 @@ GLFWAPI void glfwWindowHint(int hint, int value);
  *  @remark @macos The first time a window is created the menu bar is populated
  *  with common commands like Hide, Quit and About.  The About entry opens
  *  a minimal about dialog with information from the application's bundle.  The
- *  menu bar can be disabled with a
- *  [compile-time option](@ref compile_options_osx).
+ *  menu bar can be disabled with the @ref GLFW_COCOA_MENUBAR init hint.
  *
  *  @remark @macos On OS X 10.10 and later the window frame will not be rendered
  *  at full resolution on Retina displays unless the

+ 3 - 14
src/cocoa_init.m

@@ -28,8 +28,6 @@
 #include <sys/param.h> // For MAXPATHLEN
 
 
-#if defined(_GLFW_USE_CHDIR)
-
 // Change to our application bundle's resources directory, if present
 //
 static void changeToResourcesDirectory(void)
@@ -66,8 +64,6 @@ static void changeToResourcesDirectory(void)
     chdir(resourcesPath);
 }
 
-#endif /* _GLFW_USE_CHDIR */
-
 // Create key code translation tables
 //
 static void createKeyTables(void)
@@ -294,6 +290,9 @@ int _glfwPlatformInit(void)
 {
     _glfw.ns.autoreleasePool = [[NSAutoreleasePool alloc] init];
 
+    if (_glfw.hints.init.ns.chdir)
+        changeToResourcesDirectory();
+
     _glfw.ns.listener = [[GLFWLayoutListener alloc] init];
     [[NSNotificationCenter defaultCenter]
         addObserver:_glfw.ns.listener
@@ -301,10 +300,6 @@ int _glfwPlatformInit(void)
                name:NSTextInputContextKeyboardSelectionDidChangeNotification
              object:nil];
 
-#if defined(_GLFW_USE_CHDIR)
-    changeToResourcesDirectory();
-#endif
-
     createKeyTables();
 
     _glfw.ns.eventSource = CGEventSourceCreate(kCGEventSourceStateHIDSystemState);
@@ -376,12 +371,6 @@ void _glfwPlatformTerminate(void)
 const char* _glfwPlatformGetVersionString(void)
 {
     return _GLFW_VERSION_NUMBER " Cocoa NSGL"
-#if defined(_GLFW_USE_CHDIR)
-        " chdir"
-#endif
-#if defined(_GLFW_USE_MENUBAR)
-        " menubar"
-#endif
 #if defined(_GLFW_BUILD_DLL)
         " dynamic"
 #endif

+ 9 - 12
src/cocoa_window.m

@@ -811,8 +811,6 @@ static const NSRange kEmptyRange = { NSNotFound, 0 };
 }
 @end
 
-#if defined(_GLFW_USE_MENUBAR)
-
 // Try to figure out what the calling application is called
 //
 static NSString* findAppName(void)
@@ -922,8 +920,6 @@ static void createMenuBar(void)
     [NSApp performSelector:setAppleMenuSelector withObject:appMenu];
 }
 
-#endif /* _GLFW_USE_MENUBAR */
-
 // Initialize the Cocoa Application Kit
 //
 static GLFWbool initializeAppKit(void)
@@ -939,15 +935,16 @@ static GLFWbool initializeAppKit(void)
                              toTarget:NSApp
                            withObject:nil];
 
-    // In case we are unbundled, make us a proper UI application
-    [NSApp setActivationPolicy:NSApplicationActivationPolicyRegular];
+    if (_glfw.hints.init.ns.menubar)
+    {
+        // In case we are unbundled, make us a proper UI application
+        [NSApp setActivationPolicy:NSApplicationActivationPolicyRegular];
 
-#if defined(_GLFW_USE_MENUBAR)
-    // Menu bar setup must go between sharedApplication above and
-    // finishLaunching below, in order to properly emulate the behavior
-    // of NSApplicationMain
-    createMenuBar();
-#endif
+        // Menu bar setup must go between sharedApplication above and
+        // finishLaunching below, in order to properly emulate the behavior
+        // of NSApplicationMain
+        createMenuBar();
+    }
 
     // There can only be one application delegate, but we allocate it the
     // first time a window is created to keep all window code in this file

+ 0 - 5
src/glfw_config.h.in

@@ -55,8 +55,3 @@
 // Define this to 1 to force use of high-performance GPU on hybrid systems
 #cmakedefine _GLFW_USE_HYBRID_HPG
 
-// Define this to 1 if glfwInit should change the current directory
-#cmakedefine _GLFW_USE_CHDIR
-// Define this to 1 if glfwCreateWindow should populate the menu bar
-#cmakedefine _GLFW_USE_MENUBAR
-

+ 26 - 4
src/init.c

@@ -40,11 +40,17 @@
 //
 _GLFWlibrary _glfw = { GLFW_FALSE };
 
-// This is outside of _glfw so it can be initialized and usable before
-// glfwInit is called, which lets that function report errors
+// These are outside of _glfw so they can be used before initialization and
+// after termination
 //
-static GLFWerrorfun _glfwErrorCallback = NULL;
-
+static GLFWerrorfun _glfwErrorCallback;
+static _GLFWinitconfig _glfwInitHints =
+{
+    {
+        GLFW_TRUE, // menubar
+        GLFW_TRUE  // chdir
+    }
+};
 
 // Returns a generic string representation of the specified error
 //
@@ -153,6 +159,7 @@ GLFWAPI int glfwInit(void)
         return GLFW_TRUE;
 
     memset(&_glfw, 0, sizeof(_glfw));
+    _glfw.hints.init = _glfwInitHints;
 
     if (!_glfwPlatformInit())
     {
@@ -177,6 +184,21 @@ GLFWAPI void glfwTerminate(void)
     terminate();
 }
 
+GLFWAPI void glfwInitHint(int hint, int value)
+{
+    switch (hint)
+    {
+        case GLFW_COCOA_CHDIR_RESOURCES:
+            _glfwInitHints.ns.chdir = value;
+            return;
+        case GLFW_COCOA_MENUBAR:
+            _glfwInitHints.ns.menubar = value;
+            return;
+    }
+
+    _glfwInputError(GLFW_INVALID_ENUM, "Invalid init hint %i", hint);
+}
+
 GLFWAPI void glfwGetVersion(int* major, int* minor, int* rev)
 {
     if (major != NULL)

+ 14 - 0
src/internal.h

@@ -59,6 +59,7 @@
 
 typedef int GLFWbool;
 
+typedef struct _GLFWinitconfig  _GLFWinitconfig;
 typedef struct _GLFWwndconfig   _GLFWwndconfig;
 typedef struct _GLFWctxconfig   _GLFWctxconfig;
 typedef struct _GLFWfbconfig    _GLFWfbconfig;
@@ -259,6 +260,18 @@ typedef void (APIENTRY * PFN_vkVoidFunction)(void);
 // Platform-independent structures
 //========================================================================
 
+/*! @brief Initialization configuration.
+ *
+ *  Parameters relating to the initialization of the library.
+ */
+struct _GLFWinitconfig
+{
+    struct {
+        GLFWbool  menubar;
+        GLFWbool  chdir;
+    } ns;
+};
+
 /*! @brief Window configuration.
  *
  *  Parameters relating to the creation of the window but not directly related
@@ -476,6 +489,7 @@ struct _GLFWlibrary
     GLFWbool            initialized;
 
     struct {
+        _GLFWinitconfig init;
         _GLFWfbconfig   framebuffer;
         _GLFWwndconfig  window;
         _GLFWctxconfig  context;

+ 3 - 2
src/window.c

@@ -237,15 +237,15 @@ void glfwDefaultWindowHints(void)
 {
     _GLFW_REQUIRE_INIT();
 
-    memset(&_glfw.hints, 0, sizeof(_glfw.hints));
-
     // The default is OpenGL with minimum version 1.0
+    memset(&_glfw.hints.context, 0, sizeof(_glfw.hints.context));
     _glfw.hints.context.client = GLFW_OPENGL_API;
     _glfw.hints.context.source = GLFW_NATIVE_CONTEXT_API;
     _glfw.hints.context.major  = 1;
     _glfw.hints.context.minor  = 0;
 
     // The default is a focused, visible, resizable window with decorations
+    memset(&_glfw.hints.window, 0, sizeof(_glfw.hints.window));
     _glfw.hints.window.resizable   = GLFW_TRUE;
     _glfw.hints.window.visible     = GLFW_TRUE;
     _glfw.hints.window.decorated   = GLFW_TRUE;
@@ -254,6 +254,7 @@ void glfwDefaultWindowHints(void)
 
     // The default is 24 bits of color, 24 bits of depth and 8 bits of stencil,
     // double buffered
+    memset(&_glfw.hints.framebuffer, 0, sizeof(_glfw.hints.framebuffer));
     _glfw.hints.framebuffer.redBits      = 8;
     _glfw.hints.framebuffer.greenBits    = 8;
     _glfw.hints.framebuffer.blueBits     = 8;

+ 2 - 0
tests/glfwinfo.c

@@ -411,6 +411,8 @@ int main(int argc, char** argv)
 
     glfwSetErrorCallback(error_callback);
 
+    glfwInitHint(GLFW_COCOA_MENUBAR, GLFW_FALSE);
+
     if (!glfwInit())
         exit(EXIT_FAILURE);