Resolved: GLUT multiple sub windows and GLSL

Problem: when using multiple sub windows in GLUT and GLSL shaders, GL errors were reporting “invalid value”.

I made a minimal version and found that this is because they are separate rendering contexts. The GL error was generated because I was trying to load a shader that does not exist for that rendering context.

Solution: initialising the shaders should be done again for all applicable sub windows.

I wrote up a minimalist version and ended up with the following code for my main function:


int main(int argc, char *argv[])
{
    /* Initialise GLUT and create a window */
	int xres = subwin_width;
	int yres = subwin_height;
	
    glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_ALPHA | GLUT_DEPTH);  
	
	switch(window_count) {
		case 1:
			glutInitWindowSize(xres,yres);
			break;
		case 2:
			glutInitWindowSize((xres*2)+GAP, yres);
			break;
		case 3:
			glutInitWindowSize((xres*3)+GAP*2, yres);
			break;
		case 4:
			glutInitWindowSize((xres*4)+GAP*3, yres);
			break;
		default:
			glutInitWindowSize(xres,yres);
	}
	main_window = glutCreateWindow("GLUT subwin GLSL test");
	
    /* Configure GLUT callback functions */
	glutDisplayFunc(main_display);  
	glutReshapeFunc(reshape);
	glutKeyboardFunc(keyPressed);
	
	window1 = glutCreateSubWindow(main_window, 0, 0, subwin_width, subwin_height);
	zprInit(); // VRML mouse
	glutReshapeFunc(zprReshape);
	glutDisplayFunc(display1);  
	glutKeyboardFunc(keyPressed);
	initShaders(1);
	
	if (window_count > 1)  // subwin 2
	{
		window2 = glutCreateSubWindow(main_window, subwin_width+GAP, 0, subwin_width, subwin_height);
		zprInit(); // VRML mouse
		glutReshapeFunc(zprReshape);
		glutDisplayFunc(display2);  
		glutKeyboardFunc(keyPressed);
		initShaders(2);
	}
	
	if (window_count > 2)  // subwin 3
	{
		window3 = glutCreateSubWindow(main_window, 2*subwin_width+2*GAP, 0, subwin_width, subwin_height);
		zprInit(); // VRML mouse
		glutReshapeFunc(zprReshape);
		glutDisplayFunc(display3);  
		glutKeyboardFunc(keyPressed);
		initShaders(3);
	}
	
	if (window_count > 3) // subwin 4
	{
		window4 = glutCreateSubWindow(main_window, 3*subwin_width+3*GAP, 0, subwin_width, subwin_height);
		zprInit(); // VRML mouse
		glutReshapeFunc(zprReshape);
		glutDisplayFunc(display4);  
		glutKeyboardFunc(keyPressed);
		initShaders(4);
	}
	
	glutMainLoop();
	
	return 0;
}

initShaders needs window specific identifiers:


GLhandleARB shaderId[5]; // one for each window
...
	shaderId[window] = glCreateProgramObjectARB();
	
	glAttachObjectARB(shaderId[window], vertexShaderHandle);
	glAttachObjectARB(shaderId[window], fragmentShaderHandle);
	glLinkProgramARB(shaderId[window]);

Finally when using in display routine:


	glUseProgramObjectARB(shaderId[win_id]);

I wrapped up all the files in the attachment for future reference, no make though. I hope others find this useful as I would have 1 hour ago :stuck_out_tongue: