diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 368f4d4d9a..3fef5bd8d8 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -2809,6 +2809,7 @@ void Application::initializeGL() { } // Build a shared canvas / context for the QML rendering +#if !defined(DISABLE_QML) { _qmlShareContext = new OffscreenGLCanvas(); _qmlShareContext->setObjectName("QmlShareContext"); @@ -2822,6 +2823,8 @@ void Application::initializeGL() { qCWarning(interfaceapp, "Unable to make window context current"); } } +#endif + _renderEventHandler = new RenderEventHandler(); diff --git a/libraries/gpu-gl/src/gpu/gl41/GL41BackendShader.cpp b/libraries/gpu-gl/src/gpu/gl41/GL41BackendShader.cpp index f162afc497..f33dd91d03 100644 --- a/libraries/gpu-gl/src/gpu/gl41/GL41BackendShader.cpp +++ b/libraries/gpu-gl/src/gpu/gl41/GL41BackendShader.cpp @@ -49,7 +49,7 @@ void GL41Backend::postLinkProgram(ShaderObject& programObject, const Shader& pro const auto resourceBufferUniforms = ::gl::Uniform::loadByName(glprogram, names); for (const auto& resourceBuffer : resourceBufferUniforms) { const auto& targetBinding = expectedResourceBuffers.at(resourceBuffer.name); - glProgramUniform1i(glprogram, resourceBuffer.binding, targetBinding + GL41Backend::RESOURCE_BUFFER_SLOT0_TEX_UNIT); + glProgramUniform1i(glprogram, resourceBuffer.binding, targetBinding); } } diff --git a/libraries/gpu-gles/src/gpu/gles/GLESBackend.h b/libraries/gpu-gles/src/gpu/gles/GLESBackend.h index 8ecdb2494b..aaa1be5892 100644 --- a/libraries/gpu-gles/src/gpu/gles/GLESBackend.h +++ b/libraries/gpu-gles/src/gpu/gles/GLESBackend.h @@ -28,6 +28,10 @@ class GLESBackend : public GLBackend { public: static const GLint RESOURCE_TRANSFER_TEX_UNIT { 32 }; + static const GLint RESOURCE_TRANSFER_EXTRA_TEX_UNIT { 33 }; + static const GLint RESOURCE_BUFFER_TEXBUF_TEX_UNIT { 34 }; + static const GLint RESOURCE_BUFFER_SLOT0_TEX_UNIT { 35 }; + explicit GLESBackend(bool syncCache) : Parent(syncCache) {} GLESBackend() : Parent() {} virtual ~GLESBackend() { diff --git a/libraries/gpu-gles/src/gpu/gles/GLESBackendBuffer.cpp b/libraries/gpu-gles/src/gpu/gles/GLESBackendBuffer.cpp index 5e4da4d1fe..8cadb1a43f 100644 --- a/libraries/gpu-gles/src/gpu/gles/GLESBackendBuffer.cpp +++ b/libraries/gpu-gles/src/gpu/gles/GLESBackendBuffer.cpp @@ -10,7 +10,6 @@ namespace gpu { namespace gles { - class GLESBuffer : public gpu::gl::GLBuffer { using Parent = gpu::gl::GLBuffer; static GLuint allocate() { @@ -19,11 +18,20 @@ namespace gpu { return result; } + ~GLESBuffer() { + if (_texBuffer) { + auto backend = _backend.lock(); + if (backend) { + backend->releaseTexture(_texBuffer, 0); + } + } + } + public: GLESBuffer(const std::weak_ptr& backend, const Buffer& buffer, GLESBuffer* original) : Parent(backend, buffer, allocate()) { - glBindBuffer(GL_ARRAY_BUFFER, _buffer); - glBufferData(GL_ARRAY_BUFFER, _size, nullptr, GL_DYNAMIC_DRAW); - glBindBuffer(GL_ARRAY_BUFFER, 0); + glBindBuffer(GL_COPY_WRITE_BUFFER, _buffer); + glBufferData(GL_COPY_WRITE_BUFFER, _size, nullptr, GL_DYNAMIC_DRAW); + glBindBuffer(GL_COPY_WRITE_BUFFER, 0); if (original && original->_size) { glBindBuffer(GL_COPY_WRITE_BUFFER, _buffer); @@ -37,20 +45,34 @@ namespace gpu { } void transfer() override { - glBindBuffer(GL_ARRAY_BUFFER, _buffer); + glBindBuffer(GL_COPY_WRITE_BUFFER, _buffer); (void)CHECK_GL_ERROR(); Size offset; Size size; Size currentPage { 0 }; auto data = _gpuObject._renderSysmem.readData(); while (_gpuObject._renderPages.getNextTransferBlock(offset, size, currentPage)) { - glBufferSubData(GL_ARRAY_BUFFER, offset, size, data + offset); + glBufferSubData(GL_COPY_WRITE_BUFFER, offset, size, data + offset); (void)CHECK_GL_ERROR(); } - glBindBuffer(GL_ARRAY_BUFFER, 0); + glBindBuffer(GL_COPY_WRITE_BUFFER, 0); (void)CHECK_GL_ERROR(); _gpuObject._renderPages._flags &= ~PageManager::DIRTY; } + + // REsource BUffer are implemented with TextureBuffer + GLuint _texBuffer { 0 }; + GLuint getTexBufferId() { + if (!_texBuffer) { + glGenTextures(1, &_texBuffer); + glActiveTexture(GL_TEXTURE0 + GLESBackend::RESOURCE_BUFFER_TEXBUF_TEX_UNIT); + glBindTexture(GL_TEXTURE_BUFFER, _texBuffer); + glTexBuffer(GL_TEXTURE_BUFFER, GL_RGBA32F, _buffer); + glBindTexture(GL_TEXTURE_BUFFER, 0); + (void)CHECK_GL_ERROR(); + } + return _texBuffer; + } }; } } @@ -68,14 +90,24 @@ GLuint GLESBackend::getBufferIDUnsynced(const Buffer& buffer) { return GLESBuffer::getIdUnsynced(*this, buffer); } +GLuint GLESBackend::getResourceBufferID(const Buffer& buffer) { + auto* object = GLESBuffer::sync(*this, buffer); + if (object) { + return object->getTexBufferId(); + } else { + return 0; + } +} + GLBuffer* GLESBackend::syncGPUObject(const Buffer& buffer) { return GLESBuffer::sync(*this, buffer); } bool GLESBackend::bindResourceBuffer(uint32_t slot, const BufferPointer& buffer) { - GLBuffer* object = syncGPUObject((*buffer)); - if (object) { - glBindBufferBase(GL_SHADER_STORAGE_BUFFER, slot, object->_id); + GLuint texBuffer = GLESBackend::getResourceBufferID((*buffer)); + if (texBuffer) { + glActiveTexture(GL_TEXTURE0 + GLESBackend::RESOURCE_BUFFER_SLOT0_TEX_UNIT + slot); + glBindTexture(GL_TEXTURE_BUFFER, texBuffer); (void)CHECK_GL_ERROR(); @@ -89,9 +121,10 @@ bool GLESBackend::bindResourceBuffer(uint32_t slot, const BufferPointer& buffer) void GLESBackend::releaseResourceBuffer(uint32_t slot) { auto& bufferReference = _resource._buffers[slot]; - if (valid(bufferReference)) { - glBindBufferBase(GL_SHADER_STORAGE_BUFFER, slot, 0); + auto buffer = acquire(bufferReference); + if (buffer) { + glActiveTexture(GL_TEXTURE0 + GLESBackend::RESOURCE_BUFFER_SLOT0_TEX_UNIT + slot); + glBindTexture(GL_TEXTURE_BUFFER, 0); reset(bufferReference); } } - diff --git a/libraries/gpu/src/gpu/ShaderConstants.h b/libraries/gpu/src/gpu/ShaderConstants.h index e9a1821ef4..1a37c69784 100644 --- a/libraries/gpu/src/gpu/ShaderConstants.h +++ b/libraries/gpu/src/gpu/ShaderConstants.h @@ -21,6 +21,12 @@ #define GPU_TEXTURE_TRANSFORM_OBJECT 31 + +#define GPU_RESOURCE_BUFFER_SLOT0_TEXTURE 35 +#define GPU_RESOURCE_BUFFER_SLOT1_TEXTURE 36 +#define GPU_RESOURCE_BUFFER_SLOT0_STORAGE 0 +#define GPU_RESOURCE_BUFFER_SLOT1_STORAGE 1 + // Mip creation #define GPU_TEXTURE_MIP_CREATION_INPUT 30 diff --git a/libraries/render-utils/src/Blendshape.slh b/libraries/render-utils/src/Blendshape.slh index 73a561c73f..f2c6bfe794 100644 --- a/libraries/render-utils/src/Blendshape.slh +++ b/libraries/render-utils/src/Blendshape.slh @@ -11,12 +11,12 @@ <@func declareBlendshape(USE_NORMAL, USE_TANGENT)@> #if !defined(GPU_SSBO_TRANSFORM_OBJECT) -LAYOUT(binding=0) uniform samplerBuffer blendshapeOffsetsBuffer; +LAYOUT(binding=GPU_RESOURCE_BUFFER_SLOT0_TEXTURE) uniform samplerBuffer blendshapeOffsetsBuffer; uvec4 getPackedBlendshapeOffset(int i) { return floatBitsToUint(texelFetch(blendshapeOffsetsBuffer, i)); } #else -LAYOUT_STD140(binding=0) buffer blendshapeOffsetsBuffer { +LAYOUT_STD140(binding=GPU_RESOURCE_BUFFER_SLOT0_STORAGE) buffer blendshapeOffsetsBuffer { uvec4 _packedBlendshapeOffsets[]; }; uvec4 getPackedBlendshapeOffset(int i) { diff --git a/libraries/render-utils/src/Highlight_aabox.slv b/libraries/render-utils/src/Highlight_aabox.slv index 17ef7b6e07..65b98355ae 100644 --- a/libraries/render-utils/src/Highlight_aabox.slv +++ b/libraries/render-utils/src/Highlight_aabox.slv @@ -23,7 +23,7 @@ struct ItemBound { }; #if !defined(GPU_SSBO_TRANSFORM_OBJECT) -LAYOUT(binding=0) uniform samplerBuffer ssbo0Buffer; +LAYOUT(binding=GPU_RESOURCE_BUFFER_SLOT0_TEXTURE) uniform samplerBuffer ssbo0Buffer; ItemBound getItemBound(int i) { int offset = 2 * i; ItemBound bound; @@ -32,7 +32,7 @@ ItemBound getItemBound(int i) { return bound; } #else -LAYOUT_STD140(binding=0) buffer ssbo0Buffer { +LAYOUT_STD140(binding=GPU_RESOURCE_BUFFER_SLOT0_STORAGE) buffer ssbo0Buffer { ItemBound bounds[]; }; ItemBound getItemBound(int i) { diff --git a/libraries/render-utils/src/MeshPartPayload.cpp b/libraries/render-utils/src/MeshPartPayload.cpp index b493780aff..ca2e56862d 100644 --- a/libraries/render-utils/src/MeshPartPayload.cpp +++ b/libraries/render-utils/src/MeshPartPayload.cpp @@ -239,7 +239,7 @@ ModelMeshPartPayload::ModelMeshPartPayload(ModelPointer model, int meshIndex, in initCache(model); -#ifdef Q_OS_MAC +#if defined(Q_OS_MAC) || defined(Q_OS_ANDROID) // On mac AMD, we specifically need to have a _meshBlendshapeBuffer bound when using a deformed mesh pipeline // it cannot be null otherwise we crash in the drawcall using a deformed pipeline with a skinned only (not blendshaped) mesh if (_isBlendShaped) { diff --git a/libraries/render-utils/src/WorkloadResource.slh b/libraries/render-utils/src/WorkloadResource.slh index ed23abd5ae..14fa33a12e 100644 --- a/libraries/render-utils/src/WorkloadResource.slh +++ b/libraries/render-utils/src/WorkloadResource.slh @@ -26,7 +26,7 @@ struct WorkloadProxy { }; #if !defined(GPU_SSBO_TRANSFORM_OBJECT) -LAYOUT(binding=0) uniform samplerBuffer workloadProxiesBuffer; +LAYOUT(binding=GPU_RESOURCE_BUFFER_SLOT0_TEXTURE) uniform samplerBuffer workloadProxiesBuffer; WorkloadProxy getWorkloadProxy(int i) { int offset = 2 * i; WorkloadProxy proxy; @@ -35,7 +35,7 @@ WorkloadProxy getWorkloadProxy(int i) { return proxy; } #else -LAYOUT_STD140(binding=0) buffer workloadProxiesBuffer { +LAYOUT_STD140(binding=GPU_RESOURCE_BUFFER_SLOT0_STORAGE) buffer workloadProxiesBuffer { WorkloadProxy _proxies[]; }; WorkloadProxy getWorkloadProxy(int i) { @@ -58,7 +58,7 @@ struct WorkloadView { }; #if !defined(GPU_SSBO_TRANSFORM_OBJECT) -LAYOUT(binding=1) uniform samplerBuffer workloadViewsBuffer; +LAYOUT(binding=GPU_RESOURCE_BUFFER_SLOT1_TEXTURE) uniform samplerBuffer workloadViewsBuffer; WorkloadView getWorkloadView(int i) { int offset = 8 * i; WorkloadView view; @@ -73,7 +73,7 @@ WorkloadView getWorkloadView(int i) { return view; } #else -LAYOUT_STD140(binding=1) buffer workloadViewsBuffer { +LAYOUT_STD140(binding=GPU_RESOURCE_BUFFER_SLOT1_STORAGE) buffer workloadViewsBuffer { WorkloadView _views[]; }; WorkloadView getWorkloadView(int i) { diff --git a/libraries/render/src/render/drawItemBounds.slv b/libraries/render/src/render/drawItemBounds.slv index 0a9615c9c2..bb8e6a2886 100644 --- a/libraries/render/src/render/drawItemBounds.slv +++ b/libraries/render/src/render/drawItemBounds.slv @@ -35,7 +35,7 @@ struct ItemBound { }; #if !defined(GPU_SSBO_TRANSFORM_OBJECT) -LAYOUT(binding=0) uniform samplerBuffer ssbo0Buffer; +LAYOUT(binding=GPU_RESOURCE_BUFFER_SLOT0_TEXTURE) uniform samplerBuffer ssbo0Buffer; ItemBound getItemBound(int i) { int offset = 2 * i; ItemBound bound; @@ -44,7 +44,7 @@ ItemBound getItemBound(int i) { return bound; } #else -LAYOUT_STD140(binding=0) buffer ssbo0Buffer { +LAYOUT_STD140(binding=GPU_RESOURCE_BUFFER_SLOT0_STORAGE) buffer ssbo0Buffer { ItemBound bounds[]; }; ItemBound getItemBound(int i) {