Ejemplo n.º 1
0
// newFBO will generate a new Frame Buffer Object for use with the canvas
func newFBO(texture gl.Texture) (gl.Framebuffer, uint32) {
	// get currently bound fbo to reset to it later
	current_fbo := gl.GetBoundFramebuffer()

	framebuffer := gl.CreateFramebuffer()
	gl.BindFramebuffer(gl.FRAMEBUFFER, framebuffer)
	if texture.Valid() {
		gl.FramebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, texture, 0)
		// Initialize the texture to transparent black.
		gl.ClearColor(0.0, 0.0, 0.0, 0.0)
		gl.Clear(gl.COLOR_BUFFER_BIT)
	}
	status := gl.CheckFramebufferStatus(gl.FRAMEBUFFER)

	// unbind framebuffer
	gl.BindFramebuffer(gl.FRAMEBUFFER, current_fbo)

	return framebuffer, uint32(status)
}
Ejemplo n.º 2
0
// StencilExt operates like stencil but with access to change the stencil action,
// value, and keepvalues.
//
// action: How to modify any stencil values of pixels that are touched by what's
// drawn in the stencil function.
//
// value: The new stencil value to use for pixels if the "replace" stencil action
// is used. Has no effect with other stencil actions. Must be between 0 and 255.
//
// keepvalues: True to preserve old stencil values of pixels, false to re-set
// every pixel's stencil value to 0 before executing the stencil function. Clear
// will also re-set all stencil values.
func StencilExt(stencil_func func(), action StencilAction, value int32, keepvalues bool) {
	gl_state.writingToStencil = true
	if !keepvalues {
		gl.Clear(gl.STENCIL_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)
	}
	if gl_state.currentCanvas != nil {
		gl_state.currentCanvas.checkCreateStencil()
	}
	gl.Enable(gl.STENCIL_TEST)
	gl.ColorMask(false, false, false, false)
	gl.StencilFunc(gl.ALWAYS, int(value), 0xFF)
	gl.StencilOp(gl.KEEP, gl.KEEP, gl.Enum(action))

	stencil_func()

	gl_state.writingToStencil = false
	SetColorMask(states.back().colorMask)
	SetStencilTest(states.back().stencilCompare, states.back().stencilTestValue)
}
Ejemplo n.º 3
0
// checkCreateStencil if a stencil is set on a canvas then we need to create
// some buffers to handle this.
func (canvas *Canvas) checkCreateStencil() bool {
	// Do nothing if we've already created the stencil buffer.
	if canvas.depth_stencil.Valid() {
		return true
	}

	if gl_state.currentCanvas != canvas {
		gl.BindFramebuffer(gl.FRAMEBUFFER, canvas.fbo)
	}

	format := gl.STENCIL_INDEX8
	attachment := gl.STENCIL_ATTACHMENT

	canvas.depth_stencil = gl.CreateRenderbuffer()
	gl.BindRenderbuffer(gl.RENDERBUFFER, canvas.depth_stencil)
	gl.RenderbufferStorage(gl.RENDERBUFFER, gl.Enum(format), int(canvas.width), int(canvas.height))

	// Attach the stencil buffer to the framebuffer object.
	gl.FramebufferRenderbuffer(gl.FRAMEBUFFER, gl.Enum(attachment), gl.RENDERBUFFER, canvas.depth_stencil)
	gl.BindRenderbuffer(gl.RENDERBUFFER, gl.Renderbuffer{})

	success := (gl.CheckFramebufferStatus(gl.FRAMEBUFFER) == gl.FRAMEBUFFER_COMPLETE)

	// We don't want the stencil buffer filled with garbage.
	if success {
		gl.Clear(gl.STENCIL_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)
	} else {
		gl.DeleteRenderbuffer(canvas.depth_stencil)
		canvas.depth_stencil = gl.Renderbuffer{}
	}

	if gl_state.currentCanvas != nil && gl_state.currentCanvas != canvas {
		gl.BindFramebuffer(gl.FRAMEBUFFER, gl_state.currentCanvas.fbo)
	} else if gl_state.currentCanvas == nil {
		gl.BindFramebuffer(gl.FRAMEBUFFER, getDefaultFBO())
	}

	return success
}
Ejemplo n.º 4
0
// Clear will clear everything already rendered to the screen and set is all to
// the *Color provided.
func ClearC(c *Color) {
	gl.ClearColor(c[0], c[1], c[2], c[3])
	gl.Clear(gl.COLOR_BUFFER_BIT | gl.STENCIL_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)
}