Why am I getting error: error: ‘glCreateShader’ was not declared in this scope?

Code:

#include <GL/gl.h>
#include <GL/glu.h>
#include <GLFW/glfw3.h>
#include <stdio.h>

GLuint LoadShader(GLenum type, const char *shaderSrc)
{
	GLuint shader;
	GLint compiled;
	
	// Create the shader object
	shader = glCreateShader(type);
	if(shader == 0)
	{
		return 0;
	}
	// Load the shader source
	glShaderSource(shader, 1, &shaderSrc, NULL);
	
	glCompileShader(shader);
	// Check the compile status
	glGetShaderiv(shader, GL_COMPILE_STATUS, &compiled);
	if(!compiled) 
	{
		GLint infoLen = 0;
		glGetShaderiv(shader, GL_INFO_LOG_LENGTH, &infoLen);
		
		if(infoLen > 1)
		{
			char* infoLog = (char*) malloc(sizeof(char) * infoLen);
			glGetShaderInfoLog(shader, infoLen, NULL, infoLog);
			printf("Error compiling shader:\n%s\n", infoLog);
			free(infoLog);
		}
		glDeleteShader(shader);
		return 0;
	}
	return shader;
}


GLuint programObject_;
GLuint vertexBuffer_;
GLuint indexBuffer_;
GLuint vertexArray_;

/*
 *	Initialize the shader and program object.
 *	Initialize the triangle data buffers.
 */
bool Init(int width, int height)
{
	// Set the viewport
	glViewport(0, 0, width, height);

	GLchar vShaderStr[] =
		"#version 420\n"
		"in vec3 vPosition;\n"
		"out vec3 vertexColor;\n"
		"void main()\n"
		"{\n"
		"	vertexColor = vPosition + vec3(0.5, 0.5, 0.5) / 2;\n"
		"	gl_Position = vec4(vPosition, 1.0);\n"
		"}\n";
	
	GLchar fShaderStr[] =
		"#version 420\n"
		"in vec3 vertexColor;\n"
		"out vec4 finalColor;\n"
		""
		"void main()\n"
		"{\n"
		"  finalColor = vec4(vertexColor, 1.0);\n"
		"}\n";
	GLuint vertexShader;
	GLuint fragmentShader;
	GLuint programObject;
	GLint linked;
	// Load the vertex/fragment shaders
	vertexShader = LoadShader(GL_VERTEX_SHADER, vShaderStr);
	fragmentShader = LoadShader(GL_FRAGMENT_SHADER, fShaderStr);
	if (vertexShader == 0 || fragmentShader == 0)
	{
		return false;
	}
	programObject = glCreateProgram();

	glAttachShader(programObject, vertexShader);
	glAttachShader(programObject, fragmentShader);
	// Bind vPosition to attribute 0	
	glBindAttribLocation(programObject, 0, "vPosition");

	glLinkProgram(programObject);

	// Check the link status
	glGetProgramiv(programObject, GL_LINK_STATUS, &linked);
	if(!linked) 
	{
		GLint infoLen = 0;
		glGetProgramiv(programObject, GL_INFO_LOG_LENGTH, &infoLen);
		
		if(infoLen > 1)
		{
			char* infoLog = (char*) malloc(sizeof(char) * infoLen);
			glGetProgramInfoLog(programObject, infoLen, NULL, infoLog);
			printf("Error linking program:\n%s\n", infoLog);
			
			free(infoLog);
		}
		glDeleteProgram(programObject);
		return false;
	}
	programObject_ = programObject;

	// set the background color when clear
	glClearColor(0.0f, 0.4f, 0.6f, 1.0f);

	GLfloat vVertices[] = {
		0.0f, 0.5f, 0.0f, 
		-0.5f, -0.5f, 0.0f,
		0.5f, -0.5f,  0.0f
	};
	GLshort vIndices[] = {0, 1, 2};

	GLuint vertexBuffer;
	GLuint indexBuffer;
	glGenBuffers(1, &vertexBuffer);
	glGenBuffers(1, &indexBuffer);

	GLuint vertexArray;
	glGenVertexArrays(1, &vertexArray);

	// store the vertices of the triangle
	glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
	glBufferData(GL_ARRAY_BUFFER, sizeof(vVertices), vVertices, GL_STATIC_DRAW);
	
	// store the vertex indices of the triangle
	glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
	glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(vIndices), vIndices, GL_STATIC_DRAW);

	glBindVertexArray(vertexArray);
	// start to store vertex binding information into VertexArray

	glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
	// Specify the data format of attribute channel 0
	glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
	glEnableVertexAttribArray(0);
	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0);

	// end of storing vertex binding information into VertexArray
	glBindVertexArray(0);

	glDisableVertexAttribArray(0);

	vertexBuffer_ = vertexBuffer;
	indexBuffer_ = indexBuffer;
	vertexArray_ = vertexArray;

	return true;
}

/*
 *	Draw a triangle using the shader pair created in Init()
 */
void Draw()
{
	// Clear the color buffer
	glClear(GL_COLOR_BUFFER_BIT);
	// Use the program object
	glUseProgram(programObject_);
	
	// use the vertex bind information we bind previously
	glBindVertexArray(vertexArray_);
	// draw the triangle by index
	glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, 0);
	// unbind the vertex array to avoid it modified somewhere else
	glBindVertexArray(0);
	
	// CODE OMITTED: here are the code to swap buffers
}

int main() {
	GLFWwindow* window;
    if (!glfwInit())
        return -1;
    window = glfwCreateWindow(800, 600, "Hello World", NULL, NULL);
    if (!window)
    {
        glfwTerminate();
        return -1;
    }
    glfwMakeContextCurrent(window);
    while (!glfwWindowShouldClose(window))
    {
    	int width = 600;
		int height = 500;
    	if (!Init(width, height))
		{
			return 0;
		}
        glfwSwapBuffers(window);
        glfwPollEvents();
    }
    glfwTerminate();

	return 0;
}

Nowadays, <GL/gl.h> typically only includes prototypes for the OpenGL 1.x API. Depending upon the platform, the library may only export the 1.1 functions; in which case, any other function has to be accessed via a pointer obtained via a platform-specific function (wglGetProcAddress on Windows, glXGetProcAddress on Unix/X11). Typically you use a loader such as GLEW, GL3W, GLAD etc to handle this part; the loader will provide a header containing prototypes for the additional function.

On Linux, libGL typically exports the entire OpenGL API (for some version), so you don’t need a loader. In that case, you just need

#define GL_GLEXT_PROTOTYPES
#include <GL/glext.h>

Using a loader (or the platform’s *GetProcAddress function) may still be desirable if you want to support systems which don’t provide the latest OpenGL version. If you access the function directly, the program won’t start if the system’s libGL doesn’t export the function. If you obtain a function pointer at run time, the program will start regardless of whether the function is available, and you can choose to use an alternative mechanism or provide reduced functionality on systems where it isn’t.

This topic was automatically closed 183 days after the last reply. New replies are no longer allowed.