Testing glfwSetErrorCallback(...) - glfw

I'm developing a 2D-graphics application using th LWJGL library, which uses GLFW.
Somewhere in my code I want to implement custom error handling using
glfwSetErrorCallback(...)
Now I want to trigger some kind of GLFW error to see if my approach works.
Are there any possible ways to do this?

Thanks to #httpdigest, here is a way to to trigger a GLFW error:
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 99);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 99);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwCreateWindow(width, height, "Test", NULL, NULL);
Setting only GLFW_CONTEXT_VERSION_MAJOR or only GLFW_CONTEXT_VERSION_MINOR to an invalid value is sufficient.

Related

Trouble Creating a GLFW OpenGL Window in C++

Here is the current bit of code I'm working on:
int main() {
glfwInit();
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
GLFWwindow *window = glfwCreateWindow(WIDTH, HEIGHT, "OpenGL", NULL, NULL);
if (nullptr == window) {
std::cout << "Failed to create GLFW Window" << std::endl;
glfwTerminate();
return EXIT_FAILURE;
}
At runtime, the window is not created, and I get the failure message. I am not understanding why window is a nullptr, when I defined it. Am I missing something?
According to the GLFW documentation, the value for the GLFW_OPENGL_PROFILE window hint must be GLFW_OPENGL_ANY_PROFILE if the requested OpenGL context version is less than 3.2 (and GLFW has a platform-independent check built-in whenever glfwCreateWindow is called).
See: https://www.glfw.org/docs/3.3/window_guide.html#GLFW_OPENGL_PROFILE_hint
GLFW_OPENGL_PROFILE specifies which OpenGL profile to create the context for. Possible values are one of GLFW_OPENGL_CORE_PROFILE or GLFW_OPENGL_COMPAT_PROFILE, or GLFW_OPENGL_ANY_PROFILE to not request a specific profile. If requesting an OpenGL version below 3.2, GLFW_OPENGL_ANY_PROFILE must be used. If OpenGL ES is requested, this hint is ignored.
In particular the part: "If requesting an OpenGL version below 3.2, GLFW_OPENGL_ANY_PROFILE must be used."
You will get a GLFW error in your case. In particular, exactly this one - regardless of the platform/OS, which you would see if you had setup a GLFW error handler function via glfwSetErrorCallback().

GLFW | What is a context?

I am trying to understand what's GLFW_CONTEXT_VERSION_MAJOR and GLFW_CONTEXT_VERSION_MINOR. And what exactly those functions do:
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
And it seems to me that first of all I must find out what is context. Documentation explanation looks too complicated and doesn't even give its definition, so I can't understand what it is and what's its purpose.
It states in the first sentence with the headline Context objects: "A window object encapsulates both a top-level window and an OpenGL or OpenGL ES context."
So it will be an OpenGL/OpenGL ES context. The functions set the OpenGL/OpenGL ES version requirement for that context the window will create when you create the window.
In your example above GLFW will try to create an OpenGL 3.3 context for that window.

What does glGenBuffers indicate by returning zero?

My program creates many vertex buffer just after startup as soon as vertex data is loaded over a network, and then occasionally deletes or create vertex buffers during hot loop. It works as expected almost always, but sometimes on some machines buffer creation in hot loop produces zero names.
It doesn't look like an invalid state, because it would fire much earlier. Also, documentation and spec is not clear enough about such type of errors. Does it mean that implementation run out of buffer names?
I also found this thread. Topicstarter says that initializing names before passing them to glGenBuffers fixed his problem. Is it necessary to initialize those values?
Since it seems to work on some machines, glGenBuffer returning 0 could be because of an improperly set up context. Here
davek20 had the same problem with glGenBuffers. He solved it by fixing his incorrect context setup.
As stated on here on GLFW 'Getting started' page, under 'Creating a window and context' they state
"If the required minimum version is not supported on the machine, context (and window) creation fails."
and these machines of yours might have correct drivers but probably doesn't support all or some versions of OpenGL, as the documentation states.
If you are using GLFW_CONTEXT_VERSION_MAJOR and GLFW_CONTEXT_VERSION_MINOR consider changing these. I also recommend checking the context creation for returning NULL (0).
Example from GLFW's documentation page:
GLFWwindow* window;
if (!glfwInit())
return -1;
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
window = glfwCreateWindow(960, 540, "OpenGL", NULL, NULL);
if (!window)
{
glfwTerminate();
return -1;
}

Commenting out glfwWindowHint() makes code functional (OpenGL with GLFW), why?

sorry I had a bit of trouble with the proper name for this question, however I've run into a roadblock and I'd like to at least be informed as to the source.
I've been trying to learn to learn openGL and I'm following this tutorial:
open.gl
Lines in question:
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
While following through the tutorial I got an access violation exception in my code. Only after I commented out the following lines was I able to get the program working as the tutorial says it should have worked the first time. The tutorial states the following about the commented out lines:
"You'll immediately notice the first three lines of code that are only relevant for this library. It is specified that we require the OpenGL context to support OpenGL 3.2 at the least. The GLFW_OPENGL_PROFILE option specifies that we want a context that only supports the new core functionality."
My thought was that perhaps my drivers do not support OpenGL 3.2 or higher since when I commented out the lines in question my program ran fine. However, I downloaded a software called GPU caps viewer. When the software scanned my hardware it said that both my NVIDIA GeForce GT 540M and HD Graphics 3000 support OpenGL 4.3. So I'm very confused as to the source of my problem, what I am doing wrong, or is this a hardware issue?
Here are snapshots of GPU CAPS and NVIDIA PORTAL: 2 pictures on imgur
Doesn't Work:
#include "stdafx.h" //necessary headers in here
int _tmain(int argc, _TCHAR* argv[])
{
glfwInit();
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
GLFWwindow* window = glfwCreateWindow(800, 600, "OpenGL", nullptr, nullptr); // Windowed
glfwMakeContextCurrent(window);
while (!glfwWindowShouldClose(window))
{
glfwSwapBuffers(window);
glfwPollEvents();
if (glfwGetKey(window, GLFW_KEY_ESCAPE) == GLFW_PRESS)
glfwSetWindowShouldClose(window, GL_TRUE);
}
glfwTerminate();
return 0;
}
Works:
#include "stdafx.h" //necessary headers in here
int _tmain(int argc, _TCHAR* argv[])
{
glfwInit();
/**
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
**/
GLFWwindow* window = glfwCreateWindow(800, 600, "OpenGL", nullptr, nullptr); // Windowed
glfwMakeContextCurrent(window);
while (!glfwWindowShouldClose(window))
{
glfwSwapBuffers(window);
glfwPollEvents();
if (glfwGetKey(window, GLFW_KEY_ESCAPE) == GLFW_PRESS)
glfwSetWindowShouldClose(window, GL_TRUE);
}
glfwTerminate();
return 0;
}
Header File
#pragma once
#define GLEW_STATIC
#include <glew.h>
#include "targetver.h"
#include <stdio.h>
#include <tchar.h>
#include <iostream>
#include <thread>
#define GLFW_INCLUDE_GLU
#include <glfw3.h>
One last thing that came to mind, when I go to my NVIDIA control panel it shows Visual Studio 2013 only as using Intel HD 3000 graphics card. It doesn't give me an option to use my GeForce graphics with it, could this be the issue?
EditOne:
I tried running my Visual Studio 2013 through windows explorer by right clicking on it and choosing "Run with graphics processor..." but to no avail.
I appreciate you looking through my question to help me solve it, and if you had this question yourself I hope it helped you solve your issue.
Actual cause of the problem (as confirmed by OP) were out-of-date and/or not fully featured drivers. This is yet again a reminder that in case of OpenGL problems the first course of action should always be to upgrade to the latest version of the graphics drivers, obtained directly from the GPU maker's download site.
Two reasons for this:
OEM drivers usually lag a significant amount of releases behind the GPU vendors.
much more important: The drivers installed through Windows update are stripped of propper OpenGL support by Microsoft for reasons only known by Microsoft.
To make a long story short: Your program is probably going to get an OpenGL context for the Intel HD graphics which lacks the requested OpenGL capabilities. Thus when setting these GLFW windows hints the window creation fails and since your program does not check for this error it will try to use that window, which of course will cause trouble.
What should you do? First and foremost add error checks!
Here's an example how you can deal with the window creation failing:
GLFWwindow* window = glfwCreateWindow(
800,
600,
"OpenGL",
nullptr,
nullptr);
if( !window ) {
print_some_error_message();
exit(-1);
}
glfwMakeContextCurrent(window);
Next you want to force the system to use the NVidia card. Don't do that "launch through explorer run on NVidia BS"; say you ship your program to someone else? Do you want to put that burden onto them? Or how about you, when you want to debug it?
Do it properly: Tell the system that you want to run on the NVidia hardware in a Optimus configuration. Simply link the following into your program:
extern "C" {
_declspec(dllexport) DWORD NvOptimusEnablement = 0x00000001;
}
The best place to put this would be right beside your program's main function, i.e. in your case
#include "stdafx.h" //necessary headers in here
extern "C" {
_declspec(dllexport) DWORD NvOptimusEnablement = 0x00000001;
}
int _tmain(int argc, _TCHAR* argv[])
{
…

glfwCreateWindow() does not work after setting window hints

I'm following a tutorial which uses glfwWindowHint() to set the version of GLFW that he is using. He's on OSX and I'm on Windows. I have the exact same code as his. When I do this:
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_COMPAT_PROFILE);
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
And then this:
GLFWwindow* window = glfwCreateWindow(640, 360, "Modern OpenGL", NULL, NULL);
It always returns NULL. But in the tutorial he said that setting the window hints was necessary to use the code that the program uses. When I take out the window hints the window is created sucessfully, but then it crashes (because of the other code that probably required the window hint changes).
I'm on Windows XP. How do I fix this?
Interestingly, this code should always return NULL on OSX, as OSX supports OpenGL >=3 only in core profiles, while this code requests a compatibility profile.
On Windows, a compatibility profile of that version might be supported. But this will depend on the GPU and the drivers you have installed. It might very well be the case that your system does simply not support GL3.2. Make sure you are using recent drivers. And check what GL version your GPU actually supports. One thing you could try though is setting the GLFW_OPENGL_FORWARD_COMPAT hint to GL_FALSE.