Chromium Code Reviews| Index: src/gpu/gl/GrGpuGL.cpp |
| diff --git a/src/gpu/gl/GrGpuGL.cpp b/src/gpu/gl/GrGpuGL.cpp |
| index a01f7b74ff7a08a8369cc411535c55fc34fb40db..6179bf203244228def10b7954dbd7090b6014e86 100644 |
| --- a/src/gpu/gl/GrGpuGL.cpp |
| +++ b/src/gpu/gl/GrGpuGL.cpp |
| @@ -470,15 +470,16 @@ bool GrGpuGL::onWriteTexturePixels(GrTexture* texture, |
| GrGLTexture* glTex = static_cast<GrGLTexture*>(texture); |
| this->setScratchTextureUnit(); |
| - GL_CALL(BindTexture(GR_GL_TEXTURE_2D, glTex->textureID())); |
| GrGLTexture::Desc desc; |
| desc.fFlags = glTex->desc().fFlags; |
| desc.fWidth = glTex->width(); |
| desc.fHeight = glTex->height(); |
| + desc.fDepth = glTex->desc().fDepth; |
| desc.fConfig = glTex->config(); |
| desc.fSampleCnt = glTex->desc().fSampleCnt; |
| desc.fTextureID = glTex->textureID(); |
| desc.fOrigin = glTex->origin(); |
| + GL_CALL(BindTexture((desc.fDepth > 0) ? GR_GL_TEXTURE_3D : GR_GL_TEXTURE_2D, desc.fTextureID)); |
| bool success = false; |
| if (GrPixelConfigIsCompressed(desc.fConfig)) { |
| @@ -548,6 +549,11 @@ bool GrGpuGL::uploadTexData(const GrGLTexture::Desc& desc, |
| // If we're uploading compressed data then we should be using uploadCompressedTexData |
| SkASSERT(!GrPixelConfigIsCompressed(dataConfig)); |
| + bool is3DTexture = (desc.fDepth > 0); |
| + if (is3DTexture && !this->glCaps().has3DTexImageSupport()) { |
| + return false; |
| + } |
| + |
| size_t bpp = GrBytesPerPixel(dataConfig); |
| if (!adjust_pixel_ops_params(desc.fWidth, desc.fHeight, bpp, &left, &top, |
| &width, &height, &data, &rowBytes)) { |
| @@ -563,7 +569,7 @@ bool GrGpuGL::uploadTexData(const GrGLTexture::Desc& desc, |
| // MIP levels are all created when the texture is created. So for now we don't use |
| // texture storage. |
| bool useTexStorage = false && |
| - isNewTexture && |
| + isNewTexture && !is3DTexture && |
| this->glCaps().texStorageSupport(); |
|
bsalomon
2014/09/26 14:23:50
Is texture storage not supported for 3D?
|
| if (useTexStorage && kGL_GrGLStandard == this->glStandard()) { |
| @@ -575,8 +581,8 @@ bool GrGpuGL::uploadTexData(const GrGLTexture::Desc& desc, |
| } |
| GrGLenum internalFormat; |
| - GrGLenum externalFormat = 0x0; // suprress warning |
| - GrGLenum externalType = 0x0;// suprress warning |
| + GrGLenum externalFormat = 0x0; // suppress warning |
| + GrGLenum externalType = 0x0;// suppress warning |
| // glTexStorage requires sized internal formats on both desktop and ES. ES2 requires an unsized |
| // format for glTexImage, unlike ES3 and desktop. However, we allow the driver to decide the |
| @@ -658,6 +664,15 @@ bool GrGpuGL::uploadTexData(const GrGLTexture::Desc& desc, |
| 1, // levels |
| internalFormat, |
| desc.fWidth, desc.fHeight)); |
| + } else if (is3DTexture) { |
| + GL_ALLOC_CALL(this->glInterface(), |
| + TexImage3D(GR_GL_TEXTURE_3D, |
| + 0, // level |
| + internalFormat, |
| + desc.fWidth, desc.fHeight, desc.fDepth, |
| + 0, // border |
| + externalFormat, externalType, |
| + data)); |
| } else { |
| GL_ALLOC_CALL(this->glInterface(), |
| TexImage2D(GR_GL_TEXTURE_2D, |
| @@ -675,23 +690,43 @@ bool GrGpuGL::uploadTexData(const GrGLTexture::Desc& desc, |
| // if we have data and we used TexStorage to create the texture, we |
| // now upload with TexSubImage. |
| if (data && useTexStorage) { |
| - GL_CALL(TexSubImage2D(GR_GL_TEXTURE_2D, |
| - 0, // level |
| - left, top, |
| - width, height, |
| - externalFormat, externalType, |
| - data)); |
| + if (is3DTexture) { |
| + GL_CALL(TexSubImage3D(GR_GL_TEXTURE_3D, |
| + 0, // level, |
| + left, top, |
| + left, // FIXME: left used as Z offset |
| + desc.fWidth, desc.fHeight, desc.fDepth, |
| + externalFormat, externalType, |
| + data)); |
| + } else { |
| + GL_CALL(TexSubImage2D(GR_GL_TEXTURE_2D, |
| + 0, // level |
| + left, top, |
| + width, height, |
| + externalFormat, externalType, |
| + data)); |
| + } |
| } |
| } |
| } else { |
| if (swFlipY || glFlipY) { |
| top = desc.fHeight - (top + height); |
| } |
| - GL_CALL(TexSubImage2D(GR_GL_TEXTURE_2D, |
| - 0, // level |
| - left, top, |
| - width, height, |
| - externalFormat, externalType, data)); |
| + if (is3DTexture) { |
| + GL_CALL(TexSubImage3D(GR_GL_TEXTURE_3D, |
| + 0, // level, |
| + left, top, |
| + left, // FIXME: left used as Z offset |
| + desc.fWidth, desc.fHeight, desc.fDepth, |
| + externalFormat, externalType, |
| + data)); |
| + } else { |
| + GL_CALL(TexSubImage2D(GR_GL_TEXTURE_2D, |
| + 0, // level |
| + left, top, |
| + width, height, |
| + externalFormat, externalType, data)); |
| + } |
| } |
| if (restoreGLRowLength) { |
| @@ -742,7 +777,9 @@ bool GrGpuGL::uploadCompressedTexData(const GrGLTexture::Desc& desc, |
| // We only need the internal format for compressed 2D textures. |
| GrGLenum internalFormat = 0; |
| - if (!this->configToGLFormats(desc.fConfig, false, &internalFormat, NULL, NULL)) { |
| + if (!this->configToGLFormats(desc.fConfig, false, &internalFormat, NULL, NULL) || |
| + // Compressed 3D textures not supported |
| + (desc.fDepth > 0)) { |
| return false; |
| } |
| @@ -955,6 +992,7 @@ GrTexture* GrGpuGL::onCreateTexture(const GrTextureDesc& desc, |
| glTexDesc.fFlags = desc.fFlags; |
| glTexDesc.fWidth = desc.fWidth; |
| glTexDesc.fHeight = desc.fHeight; |
| + glTexDesc.fDepth = desc.fDepth; |
| glTexDesc.fConfig = desc.fConfig; |
| glTexDesc.fIsWrapped = false; |
| @@ -979,12 +1017,14 @@ GrTexture* GrGpuGL::onCreateTexture(const GrTextureDesc& desc, |
| if (renderTarget) { |
| int maxRTSize = this->caps()->maxRenderTargetSize(); |
| - if (glTexDesc.fWidth > maxRTSize || glTexDesc.fHeight > maxRTSize) { |
| + if (glTexDesc.fWidth > maxRTSize || glTexDesc.fHeight > maxRTSize || |
| + glTexDesc.fDepth > maxRTSize) { |
| return return_null_texture(); |
| } |
| } else { |
| int maxSize = this->caps()->maxTextureSize(); |
| - if (glTexDesc.fWidth > maxSize || glTexDesc.fHeight > maxSize) { |
| + if (glTexDesc.fWidth > maxSize || glTexDesc.fHeight > maxSize || |
| + glTexDesc.fDepth > maxSize) { |
| return return_null_texture(); |
| } |
| } |
| @@ -996,11 +1036,12 @@ GrTexture* GrGpuGL::onCreateTexture(const GrTextureDesc& desc, |
| } |
| this->setScratchTextureUnit(); |
| - GL_CALL(BindTexture(GR_GL_TEXTURE_2D, glTexDesc.fTextureID)); |
| + GrGLenum textureType = (glTexDesc.fDepth > 0) ? GR_GL_TEXTURE_3D : GR_GL_TEXTURE_2D; |
| + GL_CALL(BindTexture(textureType, glTexDesc.fTextureID)); |
| if (renderTarget && this->glCaps().textureUsageSupport()) { |
| // provides a hint about how this texture will be used |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_USAGE, |
| GR_GL_FRAMEBUFFER_ATTACHMENT)); |
| } |
| @@ -1015,18 +1056,23 @@ GrTexture* GrGpuGL::onCreateTexture(const GrTextureDesc& desc, |
| initialTexParams.fMagFilter = GR_GL_NEAREST; |
| initialTexParams.fWrapS = GR_GL_CLAMP_TO_EDGE; |
| initialTexParams.fWrapT = GR_GL_CLAMP_TO_EDGE; |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_MAG_FILTER, |
| initialTexParams.fMagFilter)); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_MIN_FILTER, |
| initialTexParams.fMinFilter)); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_WRAP_S, |
| initialTexParams.fWrapS)); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_WRAP_T, |
| initialTexParams.fWrapT)); |
| + if (GR_GL_TEXTURE_3D == textureType) { |
| + GL_CALL(TexParameteri(textureType, |
| + GR_GL_TEXTURE_WRAP_R, |
| + initialTexParams.fWrapT)); |
| + } |
| if (!this->uploadTexData(glTexDesc, true, 0, 0, |
| glTexDesc.fWidth, glTexDesc.fHeight, |
| desc.fConfig, srcData, rowBytes)) { |
| @@ -1037,7 +1083,7 @@ GrTexture* GrGpuGL::onCreateTexture(const GrTextureDesc& desc, |
| GrGLTexture* tex; |
| if (renderTarget) { |
| // unbind the texture from the texture unit before binding it to the frame buffer |
| - GL_CALL(BindTexture(GR_GL_TEXTURE_2D, 0)); |
| + GL_CALL(BindTexture(textureType, 0)); |
| if (!this->createRenderTargetObjects(glTexDesc.fWidth, |
| glTexDesc.fHeight, |
| @@ -1061,7 +1107,7 @@ GrTexture* GrGpuGL::onCreateTexture(const GrTextureDesc& desc, |
| GrTexture* GrGpuGL::onCreateCompressedTexture(const GrTextureDesc& desc, |
| const void* srcData) { |
| - if(SkToBool(desc.fFlags & kRenderTarget_GrTextureFlagBit)) { |
| + if(SkToBool(desc.fFlags & kRenderTarget_GrTextureFlagBit) || (desc.fDepth > 0)) { |
| return return_null_texture(); |
| } |
| @@ -2023,10 +2069,12 @@ void GrGpuGL::bindTexture(int unitIdx, const GrTextureParams& params, GrGLTextur |
| this->onResolveRenderTarget(texRT); |
| } |
| + GrGLenum textureType = (texture->desc().fDepth > 0) ? GR_GL_TEXTURE_3D : GR_GL_TEXTURE_2D; |
|
bsalomon
2014/09/26 14:23:51
Why don't we have GrGLTexture::textureType()? (Act
|
| + |
| uint32_t textureID = texture->getUniqueID(); |
| if (fHWBoundTextureUniqueIDs[unitIdx] != textureID) { |
| this->setTextureUnit(unitIdx); |
| - GL_CALL(BindTexture(GR_GL_TEXTURE_2D, texture->textureID())); |
| + GL_CALL(BindTexture(textureType, texture->textureID())); |
| fHWBoundTextureUniqueIDs[unitIdx] = textureID; |
| } |
| @@ -2054,7 +2102,7 @@ void GrGpuGL::bindTexture(int unitIdx, const GrTextureParams& params, GrGLTextur |
| if (GrTextureParams::kMipMap_FilterMode == filterMode && |
| texture->mipMapsAreDirty() && !GrPixelConfigIsCompressed(texture->config())) { |
| - GL_CALL(GenerateMipmap(GR_GL_TEXTURE_2D)); |
| + GL_CALL(GenerateMipmap(textureType)); |
| texture->dirtyMipMaps(false); |
| } |
| @@ -2065,27 +2113,32 @@ void GrGpuGL::bindTexture(int unitIdx, const GrTextureParams& params, GrGLTextur |
| sizeof(newTexParams.fSwizzleRGBA)); |
| if (setAll || newTexParams.fMagFilter != oldTexParams.fMagFilter) { |
| this->setTextureUnit(unitIdx); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_MAG_FILTER, |
| newTexParams.fMagFilter)); |
| } |
| if (setAll || newTexParams.fMinFilter != oldTexParams.fMinFilter) { |
| this->setTextureUnit(unitIdx); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_MIN_FILTER, |
| newTexParams.fMinFilter)); |
| } |
| if (setAll || newTexParams.fWrapS != oldTexParams.fWrapS) { |
| this->setTextureUnit(unitIdx); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_WRAP_S, |
| newTexParams.fWrapS)); |
| } |
| if (setAll || newTexParams.fWrapT != oldTexParams.fWrapT) { |
| this->setTextureUnit(unitIdx); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, |
| + GL_CALL(TexParameteri(textureType, |
| GR_GL_TEXTURE_WRAP_T, |
| newTexParams.fWrapT)); |
| + if (GR_GL_TEXTURE_3D == textureType) { |
|
bsalomon
2014/09/26 14:23:51
Do all ES contexts that support 3D textures also s
|
| + GL_CALL(TexParameteri(textureType, |
| + GR_GL_TEXTURE_WRAP_R, |
| + newTexParams.fWrapT)); |
| + } |
| } |
| if (this->glCaps().textureSwizzleSupport() && |
| (setAll || memcmp(newTexParams.fSwizzleRGBA, |
| @@ -2095,14 +2148,14 @@ void GrGpuGL::bindTexture(int unitIdx, const GrTextureParams& params, GrGLTextur |
| if (this->glStandard() == kGLES_GrGLStandard) { |
| // ES3 added swizzle support but not GL_TEXTURE_SWIZZLE_RGBA. |
| const GrGLenum* swizzle = newTexParams.fSwizzleRGBA; |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, GR_GL_TEXTURE_SWIZZLE_R, swizzle[0])); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, GR_GL_TEXTURE_SWIZZLE_G, swizzle[1])); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, GR_GL_TEXTURE_SWIZZLE_B, swizzle[2])); |
| - GL_CALL(TexParameteri(GR_GL_TEXTURE_2D, GR_GL_TEXTURE_SWIZZLE_A, swizzle[3])); |
| + GL_CALL(TexParameteri(textureType, GR_GL_TEXTURE_SWIZZLE_R, swizzle[0])); |
| + GL_CALL(TexParameteri(textureType, GR_GL_TEXTURE_SWIZZLE_G, swizzle[1])); |
| + GL_CALL(TexParameteri(textureType, GR_GL_TEXTURE_SWIZZLE_B, swizzle[2])); |
| + GL_CALL(TexParameteri(textureType, GR_GL_TEXTURE_SWIZZLE_A, swizzle[3])); |
| } else { |
| GR_STATIC_ASSERT(sizeof(newTexParams.fSwizzleRGBA[0]) == sizeof(GrGLint)); |
| const GrGLint* swizzle = reinterpret_cast<const GrGLint*>(newTexParams.fSwizzleRGBA); |
| - GL_CALL(TexParameteriv(GR_GL_TEXTURE_2D, GR_GL_TEXTURE_SWIZZLE_RGBA, swizzle)); |
| + GL_CALL(TexParameteriv(textureType, GR_GL_TEXTURE_SWIZZLE_RGBA, swizzle)); |
| } |
| } |
| texture->setCachedTexParams(newTexParams, this->getResetTimestamp()); |