📄 intel_fbo.c
字号:
irb->Base.BlueBits = 5; irb->Base.DataType = GL_UNSIGNED_BYTE; cpp = 2; break; case GL_RGBA8: irb->Base._ActualFormat = GL_RGBA8; irb->Base._BaseFormat = GL_RGBA; irb->Base.RedBits = 8; irb->Base.GreenBits = 8; irb->Base.BlueBits = 8; irb->Base.AlphaBits = 8; irb->Base.DataType = GL_UNSIGNED_BYTE; cpp = 4; break; case GL_STENCIL_INDEX8_EXT: irb->Base._ActualFormat = GL_STENCIL_INDEX8_EXT; irb->Base._BaseFormat = GL_STENCIL_INDEX; irb->Base.StencilBits = 8; irb->Base.DataType = GL_UNSIGNED_BYTE; cpp = 1; break; case GL_DEPTH_COMPONENT16: irb->Base._ActualFormat = GL_DEPTH_COMPONENT16; irb->Base._BaseFormat = GL_DEPTH_COMPONENT; irb->Base.DepthBits = 16; irb->Base.DataType = GL_UNSIGNED_SHORT; cpp = 2; break; case GL_DEPTH_COMPONENT24: irb->Base._ActualFormat = GL_DEPTH24_STENCIL8_EXT; irb->Base._BaseFormat = GL_DEPTH_COMPONENT; irb->Base.DepthBits = 24; irb->Base.DataType = GL_UNSIGNED_INT; cpp = 4; break; case GL_DEPTH24_STENCIL8_EXT: irb->Base._ActualFormat = GL_DEPTH24_STENCIL8_EXT; irb->Base._BaseFormat = GL_DEPTH_STENCIL_EXT; irb->Base.DepthBits = 24; irb->Base.StencilBits = 8; irb->Base.DataType = GL_UNSIGNED_INT_24_8_EXT; cpp = 4; break; default: _mesa_problem(NULL, "Unexpected intFormat in intel_create_renderbuffer"); return NULL; } irb->Base.InternalFormat = intFormat; /* intel-specific methods */ irb->Base.Delete = intel_delete_renderbuffer; irb->Base.AllocStorage = intel_alloc_window_storage; irb->Base.GetPointer = intel_get_pointer; /* This sets the Get/PutRow/Value functions */ intel_set_span_functions(&irb->Base); irb->pfMap = map; irb->pfPitch = pitch;#if 00 irb->region = intel_region_create_static(intel, DRM_MM_TT, offset, map, cpp, width, height);#endif return irb;}/** * Create a new renderbuffer object. * Typically called via glBindRenderbufferEXT(). */static struct gl_renderbuffer *intel_new_renderbuffer(GLcontext *ctx, GLuint name){ /*struct intel_context *intel = intel_context(ctx);*/ struct intel_renderbuffer *irb; irb = CALLOC_STRUCT(intel_renderbuffer); if (!irb) { _mesa_error(ctx, GL_OUT_OF_MEMORY, "creating renderbuffer"); return NULL; } _mesa_init_renderbuffer(&irb->Base, name); irb->Base.ClassID = INTEL_RB_CLASS; /* intel-specific methods */ irb->Base.Delete = intel_delete_renderbuffer; irb->Base.AllocStorage = intel_alloc_renderbuffer_storage; irb->Base.GetPointer = intel_get_pointer; /* span routines set in alloc_storage function */ return &irb->Base;}/** * Called via glBindFramebufferEXT(). */static voidintel_bind_framebuffer(GLcontext *ctx, GLenum target, struct gl_framebuffer *fb){ /* _mesa_debug(ctx, "%s %d\n", __FUNCTION__, fb->Name); */ /* XXX FBO: putting this flush here fixes a rendering offset bug. * Not sure why this is needed when _mesa_BindFrameBuffer does * a FLUSH_VERTICES(). */ intelFlush(ctx); if (target == GL_FRAMEBUFFER_EXT || target == GL_DRAW_FRAMEBUFFER_EXT) { intel_draw_buffer(ctx, fb); /* Integer depth range depends on depth buffer bits */ ctx->Driver.DepthRange(ctx, ctx->Viewport.Near, ctx->Viewport.Far); } else { /* don't need to do anything if target == GL_READ_FRAMEBUFFER_EXT */ }}/** * Called via glFramebufferRenderbufferEXT(). */static voidintel_framebuffer_renderbuffer(GLcontext *ctx, struct gl_framebuffer *fb, GLenum attachment, struct gl_renderbuffer *rb){ /* _mesa_debug(ctx, "Intel FramebufferRenderbuffer %u %u\n", fb->Name, rb ? rb->Name : 0); */ intelFlush(ctx); _mesa_framebuffer_renderbuffer(ctx, fb, attachment, rb); intel_draw_buffer(ctx, fb);}/** * When glFramebufferTexture[123]D is called this function sets up the * gl_renderbuffer wrapp around the texture image. * This will have the region info needed for hardware rendering. */static struct intel_renderbuffer *intel_wrap_texture(GLcontext *ctx, struct gl_texture_image *texImage){ const GLuint name = ~0; /* not significant, but distinct for debugging */ struct intel_renderbuffer *irb; /* make an intel_renderbuffer to wrap the texture image */ irb = CALLOC_STRUCT(intel_renderbuffer); if (!irb) { _mesa_error(ctx, GL_OUT_OF_MEMORY, "glFramebufferTexture"); return NULL; } _mesa_init_renderbuffer(&irb->Base, name); irb->Base.ClassID = INTEL_RB_CLASS; if (texImage->TexFormat == &_mesa_texformat_argb8888) { irb->Base._ActualFormat = GL_RGBA8; irb->Base._BaseFormat = GL_RGBA; _mesa_debug(ctx, "Render to RGBA8 texture OK\n"); } else if (texImage->TexFormat == &_mesa_texformat_rgb565) { irb->Base._ActualFormat = GL_RGB5; irb->Base._BaseFormat = GL_RGB; _mesa_debug(ctx, "Render to RGB5 texture OK\n"); } else if (texImage->TexFormat == &_mesa_texformat_depth_component16) { irb->Base._ActualFormat = GL_DEPTH_COMPONENT16; irb->Base._BaseFormat = GL_DEPTH_COMPONENT; _mesa_debug(ctx, "Render to DEPTH16 texture OK\n"); } else { _mesa_debug(ctx, "Render to texture BAD FORMAT %d\n", texImage->TexFormat->MesaFormat); _mesa_free(irb); return NULL; } irb->Base.InternalFormat = irb->Base._ActualFormat; irb->Base.Width = texImage->Width; irb->Base.Height = texImage->Height; irb->Base.DataType = GL_UNSIGNED_BYTE; /* FBO XXX fix */ irb->Base.RedBits = texImage->TexFormat->RedBits; irb->Base.GreenBits = texImage->TexFormat->GreenBits; irb->Base.BlueBits = texImage->TexFormat->BlueBits; irb->Base.AlphaBits = texImage->TexFormat->AlphaBits; irb->Base.DepthBits = texImage->TexFormat->DepthBits; irb->Base.Delete = intel_delete_renderbuffer; irb->Base.AllocStorage = intel_nop_alloc_storage; intel_set_span_functions(&irb->Base); irb->RenderToTexture = GL_TRUE; return irb;}/** * Called by glFramebufferTexture[123]DEXT() (and other places) to * prepare for rendering into texture memory. This might be called * many times to choose different texture levels, cube faces, etc * before intel_finish_render_texture() is ever called. */static voidintel_render_texture(GLcontext *ctx, struct gl_framebuffer *fb, struct gl_renderbuffer_attachment *att){ struct gl_texture_image *newImage = att->Texture->Image[att->CubeMapFace][att->TextureLevel]; struct intel_renderbuffer *irb = intel_renderbuffer(att->Renderbuffer); struct intel_texture_image *intel_image; GLuint imageOffset; (void) fb; ASSERT(newImage); if (!irb) { irb = intel_wrap_texture(ctx, newImage); if (irb) { /* bind the wrapper to the attachment point */ att->Renderbuffer = &irb->Base; } else { /* fallback to software rendering */ _mesa_render_texture(ctx, fb, att); return; } } /* _mesa_debug(ctx, "Begin render texture tex=%u w=%d h=%d refcount=%d\n", att->Texture->Name, newImage->Width, newImage->Height, irb->Base.RefCount); */ /* point the renderbufer's region to the texture image region */ intel_image = intel_texture_image(newImage); if (irb->region != intel_image->mt->region) intel_region_reference(&irb->region, intel_image->mt->region); /* compute offset of the particular 2D image within the texture region */ imageOffset = intel_miptree_image_offset(intel_image->mt, att->CubeMapFace, att->TextureLevel); if (att->Texture->Target == GL_TEXTURE_3D) { GLuint imgStride = intel_miptree_depth_image_stride(intel_image->mt, att->CubeMapFace, att->TextureLevel); imageOffset += imgStride * att->Zoffset; } /* store that offset in the region */ intel_image->mt->region->draw_offset = imageOffset; /* update drawing region, etc */ intel_draw_buffer(ctx, fb);}/** * Called by Mesa when rendering to a texture is done. */static voidintel_finish_render_texture(GLcontext *ctx, struct gl_renderbuffer_attachment *att){ struct intel_context *intel = intel_context(ctx); struct intel_renderbuffer *irb = intel_renderbuffer(att->Renderbuffer); /* _mesa_debug(ctx, "End render texture (tid %u) tex %u\n", _glthread_GetID(), att->Texture->Name); */ if (irb) { /* just release the region */ intel_region_release(intel, &irb->region); } else if (att->Renderbuffer) { /* software fallback */ _mesa_finish_render_texture(ctx, att); /* XXX FBO: Need to unmap the buffer (or in intelSpanRenderStart???) */ }}/** * Do one-time context initializations related to GL_EXT_framebuffer_object. * Hook in device driver functions. */voidintel_fbo_init( struct intel_context *intel ){ intel->ctx.Driver.NewFramebuffer = intel_new_framebuffer; intel->ctx.Driver.NewRenderbuffer = intel_new_renderbuffer; intel->ctx.Driver.BindFramebuffer = intel_bind_framebuffer; intel->ctx.Driver.FramebufferRenderbuffer = intel_framebuffer_renderbuffer; intel->ctx.Driver.RenderTexture = intel_render_texture; intel->ctx.Driver.FinishRenderTexture = intel_finish_render_texture;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -