Frame buffer object renders wrong to texture

My last topic didn’t go down too well so I’m going to start a new one. It makes sense because my code has changed a lot since last time. I seem to have made some progress with other parts of my game but the texture to texture rendering is still problematic.

I’m using python but OpenGL is pretty much done exactly the same way as in any other language.

The problem is that when I try to render a texture or a line to a texture by means of a frame buffer object, it is rendered upside down, too small in the bottom left corner. Very weird. A picture would best demonstrate the problem. I’ll upload one shortly.

The code is as follows with some comments to help along the way,

def texture_to_texture(target,surface,offset): #Target is an object of a class which contains texture data. This texture should be the target. Surface is the same but is the texture which should be drawn onto the target. offset is the offset where the surface texture will be drawn on the target texture.
	#This will create the textures if not already. It will create textures from image data or block colour. Seems to work fine as direct rendering of textures to the screen works brilliantly.
	if target.texture == None:
		create_texture(target)
	if surface.texture == None:
		create_texture(surface)
	frame_buffer =  glGenFramebuffersEXT(1)
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, frame_buffer)
	glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, target.texture, 0) #target.texture is the texture id from the object
	glPushAttrib(GL_VIEWPORT_BIT)
	glViewport(0,0,target.surface_size[0],target.surface_size[1])
	draw_texture(surface.texture,offset,surface.surface_size,[float(c)/255.0 for c in surface.colour]) #The last part changes the 0-255 colours to 0-1 The textures when drawn appear to have the correct colour. Don't worry about that.
	glPopAttrib()
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0)
	glDeleteFramebuffersEXT(1, [int(frame_buffer)]) #Requires the sequence of the integer conversion of the ctype variable, meaning [int(frame_buffer)] is the odd required way to pass the frame buffer id to the function.

What could be causing this erratic behaviour?

Thank you for any help.

This is how it looks,

www.godofgod.co.uk/my_files/Incorrect_operation.png

This is how it did look when I was using pygame instead. Pygame is too slow, I’ve learnt. My game would be unplayable without OpenGL’s speed. Ignore the curved corners. I haven’t implemented those in OpenGL yet. I need to solve this issue first.

www.godofgod.co.uk/my_files/Correct_operation.png

Oh, and this is the draw_texture function which works fine when done for the screen,

def draw_texture(texture,offset,size,c):
	glMatrixMode(GL_MODELVIEW)
	glLoadIdentity() #Loads model matrix
	glColor4fv(c)
	glBegin(GL_QUADS)
	glVertex2i(*offset) #Top Left
	glVertex2i(offset[0],offset[1] + size[1]) #Bottom Left
	glVertex2i(offset[0] + size[0],offset[1] + size[1]) #Bottom, Right
	glVertex2i(offset[0] + size[0],offset[1]) #Top, Right
	glEnd()
	glColor4fv((1,1,1,1))
	glBindTexture(GL_TEXTURE_2D, texture)
	glBegin(GL_QUADS)
	glTexCoord2f(0.0, 0.0)
	glVertex2i(*offset) #Top Left
	glTexCoord2f(0.0, 1.0)
	glVertex2i(offset[0],offset[1] + size[1]) #Bottom Left
	glTexCoord2f(1.0, 1.0)
	glVertex2i(offset[0] + size[0],offset[1] + size[1]) #Bottom, Right
	glTexCoord2f(1.0, 0.0)
	glVertex2i(offset[0] + size[0],offset[1]) #Top, Right
	glEnd()

It might help to know that I’m not using depth.

What if I used some other method? But what can I do?

I have more problems but the first problem has been solved. The problem was that I didn’t know I needed to reset the project matrix. Nothing told me to do that. I’m very annoyed about that. This is the texture_to_texture function at the moment,

def texture_to_texture(target,surface,offset):
	#Create textures if not done already
	if target.texture == None:
		create_texture(target)
	if surface.texture == None:
		create_texture(surface)
	#Render child to parent
	if target.frame_buffer == None:
		target.frame_buffer =  glGenFramebuffersEXT(1)
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, target.frame_buffer)
	glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, target.texture, 0)
	status = glCheckFramebufferStatusEXT (GL_FRAMEBUFFER_EXT);
	glPushAttrib(GL_VIEWPORT_BIT)
	glEnable(GL_LINE_SMOOTH,GL_FASTEST) #Create antialiased lines
	glEnable(GL_BLEND) #Enable alpha blending
	glEnable(GL_TEXTURE_2D) #Enable 2D Textures
	glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA) #The recomended blending functions.
	glViewport(0,0,target.surface_size[0],target.surface_size[1])
	glMatrixMode(GL_PROJECTION)
	glLoadIdentity() #Load the projection matrix
	gluOrtho2D(target.surface_size[0],0,0,target.surface_size[1])
	draw_texture(surface.texture,offset,surface.surface_size,[float(c)/255.0 for c in surface.colour])
	glPopAttrib()
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0)
	glMatrixMode(GL_PROJECTION)
	glLoadIdentity() #Load the projection matrix
	gluOrtho2D(0,1280,720,0) #Set an orthorgraphic view

You can see I use gluOrtho2D now.

But lines still fail,

def add_line(surface,c,a,b,w = 1):
	c = [float(sc)/255 for sc in c] #Divide colours by 255 because OpenGL uses 0-1
	if len(c) != 4:
		c.append(1) #Add a value for aplha transparency if needed
	#Create texture if not done already
	if surface.texture == None:
		create_texture(surface)
	#Render child to parent
	if surface.frame_buffer == None:
		surface.frame_buffer =  glGenFramebuffersEXT(1)
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, surface.frame_buffer)
	glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, surface.texture, 0)
	glPushAttrib(GL_VIEWPORT_BIT)
	glViewport(0,0,surface.surface_size[0],surface.surface_size[1])
	glMatrixMode(GL_PROJECTION)
	glLoadIdentity() #Load the projection matrix
	gluOrtho2D(surface.surface_size[0],0,0,surface.surface_size[1])
	glMatrixMode(GL_MODELVIEW)
	glLoadIdentity() #Loads model matrix
	glColor4fv(c)
	glLineWidth(w)
	glBegin(GL_LINES)
	glVertex2iv(a)
	glVertex2iv(b)
	glEnd()
	glPopAttrib()
	glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0)
	glMatrixMode(GL_PROJECTION)
	glLoadIdentity() #Load the projection matrix
	gluOrtho2D(0,1280,720,0) #Set an orthorgraphic view

What is supposed to be a gradient is showing as grey with little stripes in it. Nothing normal at all.