Updating object transform code

This commit is contained in:
Brad Davis 2016-08-01 12:04:52 -07:00
parent 64ece05f40
commit 2340afc48e
21 changed files with 106 additions and 103 deletions

View file

@ -218,6 +218,8 @@ private:
OpenGLDisplayPlugin::OpenGLDisplayPlugin() {
}
extern QThread* RENDER_THREAD;
bool OpenGLDisplayPlugin::activate() {
if (!_cursorsData.size()) {
auto& cursorManager = Cursor::Manager::instance();

View file

@ -2,11 +2,13 @@
#include <mutex>
#include <QtCore/QThread>
#include <QtCore/QRegularExpression>
#include <QtCore/QProcessEnvironment>
#include <QtGui/QSurfaceFormat>
#include <QtOpenGL/QGL>
#include <QOpenGLContext>
#include <QtCore/QRegularExpression>
#include <QtCore/QProcessEnvironment>
#ifdef DEBUG
static bool enableDebug = true;
#else
@ -72,3 +74,10 @@ QJsonObject getGLContextData() {
{ "renderer", glRenderer },
};
}
QThread* RENDER_THREAD = nullptr;
bool isRenderThread() {
return QThread::currentThread() == RENDER_THREAD;
}

View file

@ -29,4 +29,6 @@ const QGLFormat& getDefaultGLFormat();
QJsonObject getGLContextData();
int glVersionToInteger(QString glVersion);
bool isRenderThread();
#endif

View file

@ -161,17 +161,17 @@ public:
virtual void do_setStateBlendFactor(Batch& batch, size_t paramOffset) final;
virtual void do_setStateScissorRect(Batch& batch, size_t paramOffset) final;
virtual GLuint getFramebufferID(const FramebufferPointer& framebuffer) = 0;
virtual GLuint getTextureID(const TexturePointer& texture, bool needTransfer = true) = 0;
virtual GLuint getFramebufferID(const FramebufferPointer& framebuffer) const = 0;
virtual GLuint getTextureID(const TexturePointer& texture, bool needTransfer = true) const = 0;
protected:
virtual GLFramebuffer* syncGPUObject(const Framebuffer& framebuffer) = 0;
virtual GLFramebuffer* syncGPUObject(const Framebuffer& framebuffer) const = 0;
virtual GLuint getBufferID(const Buffer& buffer) = 0;
virtual GLBuffer* syncGPUObject(const Buffer& buffer) = 0;
virtual GLuint getBufferID(const Buffer& buffer) const = 0;
virtual GLBuffer* syncGPUObject(const Buffer& buffer) const = 0;
virtual GLTexture* syncGPUObject(const TexturePointer& texture, bool sync = true) = 0;
virtual GLTexture* syncGPUObject(const TexturePointer& texture, bool sync = true) const = 0;
virtual GLuint getQueryID(const QueryPointer& query) = 0;
virtual GLQuery* syncGPUObject(const Query& query) = 0;

View file

@ -55,14 +55,14 @@ public:
protected:
GLuint getFramebufferID(const FramebufferPointer& framebuffer) override;
gl::GLFramebuffer* syncGPUObject(const Framebuffer& framebuffer) override;
GLuint getFramebufferID(const FramebufferPointer& framebuffer) const override;
gl::GLFramebuffer* syncGPUObject(const Framebuffer& framebuffer) const override;
GLuint getBufferID(const Buffer& buffer) override;
gl::GLBuffer* syncGPUObject(const Buffer& buffer) override;
GLuint getBufferID(const Buffer& buffer) const override;
gl::GLBuffer* syncGPUObject(const Buffer& buffer) const override;
GLuint getTextureID(const TexturePointer& texture, bool needTransfer = true) override;
gl::GLTexture* syncGPUObject(const TexturePointer& texture, bool sync = true) override;
GLuint getTextureID(const TexturePointer& texture, bool needTransfer = true) const override;
gl::GLTexture* syncGPUObject(const TexturePointer& texture, bool sync = true) const override;
GLuint getQueryID(const QueryPointer& query) override;
gl::GLQuery* syncGPUObject(const Query& query) override;

View file

@ -53,10 +53,10 @@ public:
}
};
GLuint GL41Backend::getBufferID(const Buffer& buffer) {
GLuint GL41Backend::getBufferID(const Buffer& buffer) const {
return GL41Buffer::getId<GL41Buffer>(buffer);
}
gl::GLBuffer* GL41Backend::syncGPUObject(const Buffer& buffer) {
gl::GLBuffer* GL41Backend::syncGPUObject(const Buffer& buffer) const {
return GL41Buffer::sync<GL41Buffer>(buffer);
}

View file

@ -119,11 +119,11 @@ public:
: Parent(framebuffer, allocate()) { }
};
gl::GLFramebuffer* GL41Backend::syncGPUObject(const Framebuffer& framebuffer) {
gl::GLFramebuffer* GL41Backend::syncGPUObject(const Framebuffer& framebuffer) const {
return GL41Framebuffer::sync<GL41Framebuffer>(framebuffer);
}
GLuint GL41Backend::getFramebufferID(const FramebufferPointer& framebuffer) {
GLuint GL41Backend::getFramebufferID(const FramebufferPointer& framebuffer) const {
return framebuffer ? GL41Framebuffer::getId<GL41Framebuffer>(*framebuffer) : 0;
}

View file

@ -29,11 +29,11 @@ GLuint GL41Texture::allocate() {
return result;
}
GLuint GL41Backend::getTextureID(const TexturePointer& texture, bool transfer) {
GLuint GL41Backend::getTextureID(const TexturePointer& texture, bool transfer) const {
return GL41Texture::getId<GL41Texture>(texture, transfer);
}
gl::GLTexture* GL41Backend::syncGPUObject(const TexturePointer& texture, bool transfer) {
gl::GLTexture* GL41Backend::syncGPUObject(const TexturePointer& texture, bool transfer) const {
return GL41Texture::sync<GL41Texture>(texture, transfer);
}

View file

@ -33,22 +33,19 @@ void GL41Backend::transferTransformState(const Batch& batch) const {
memcpy(bufferData.data() + (_transform._cameraUboSize * i), &_transform._cameras[i], sizeof(TransformStageState::CameraBufferElement));
}
glBindBuffer(GL_UNIFORM_BUFFER, _transform._cameraBuffer);
glBufferData(GL_UNIFORM_BUFFER, bufferData.size(), bufferData.data(), GL_DYNAMIC_DRAW);
glBufferData(GL_UNIFORM_BUFFER, bufferData.size(), bufferData.data(), GL_STREAM_DRAW);
glBindBuffer(GL_UNIFORM_BUFFER, 0);
}
if (!batch._objects.empty()) {
auto byteSize = batch._objects.size() * sizeof(Batch::TransformObject);
bufferData.resize(byteSize);
memcpy(bufferData.data(), batch._objects.data(), byteSize);
if (batch._objectsBuffer) {
const auto& sysmem = batch._objectsBuffer->_renderSysmem;
#ifdef GPU_SSBO_DRAW_CALL_INFO
glBindBuffer(GL_SHADER_STORAGE_BUFFER, _transform._objectBuffer);
glBufferData(GL_SHADER_STORAGE_BUFFER, bufferData.size(), bufferData.data(), GL_DYNAMIC_DRAW);
glBufferData(GL_SHADER_STORAGE_BUFFER, sysmem.getSize(), sysmem.readData(), GL_STREAM_DRAW);
glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0);
#else
glBindBuffer(GL_TEXTURE_BUFFER, _transform._objectBuffer);
glBufferData(GL_TEXTURE_BUFFER, bufferData.size(), bufferData.data(), GL_DYNAMIC_DRAW);
glBufferData(GL_TEXTURE_BUFFER, sysmem.getSize(), sysmem.readData(), GL_STREAM_DRAW);
glBindBuffer(GL_TEXTURE_BUFFER, 0);
#endif
}
@ -64,7 +61,7 @@ void GL41Backend::transferTransformState(const Batch& batch) const {
}
glBindBuffer(GL_ARRAY_BUFFER, _transform._drawCallInfoBuffer);
glBufferData(GL_ARRAY_BUFFER, bufferData.size(), bufferData.data(), GL_DYNAMIC_DRAW);
glBufferData(GL_ARRAY_BUFFER, bufferData.size(), bufferData.data(), GL_STREAM_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, 0);
}

View file

@ -44,14 +44,14 @@ public:
protected:
GLuint getFramebufferID(const FramebufferPointer& framebuffer) override;
gl::GLFramebuffer* syncGPUObject(const Framebuffer& framebuffer) override;
GLuint getFramebufferID(const FramebufferPointer& framebuffer) const override;
gl::GLFramebuffer* syncGPUObject(const Framebuffer& framebuffer) const override;
GLuint getBufferID(const Buffer& buffer) override;
gl::GLBuffer* syncGPUObject(const Buffer& buffer) override;
GLuint getBufferID(const Buffer& buffer) const override;
gl::GLBuffer* syncGPUObject(const Buffer& buffer) const override;
GLuint getTextureID(const TexturePointer& texture, bool needTransfer = true) override;
gl::GLTexture* syncGPUObject(const TexturePointer& texture, bool sync = true) override;
GLuint getTextureID(const TexturePointer& texture, bool needTransfer = true) const override;
gl::GLTexture* syncGPUObject(const TexturePointer& texture, bool sync = true) const override;
GLuint getQueryID(const QueryPointer& query) override;
gl::GLQuery* syncGPUObject(const Query& query) override;

View file

@ -41,10 +41,10 @@ public:
}
};
GLuint GL45Backend::getBufferID(const Buffer& buffer) {
GLuint GL45Backend::getBufferID(const Buffer& buffer) const {
return GL45Buffer::getId<GL45Buffer>(buffer);
}
gl::GLBuffer* GL45Backend::syncGPUObject(const Buffer& buffer) {
gl::GLBuffer* GL45Backend::syncGPUObject(const Buffer& buffer) const {
return GL45Buffer::sync<GL45Buffer>(buffer);
}

View file

@ -111,11 +111,11 @@ public:
: Parent(framebuffer, allocate()) { }
};
gl::GLFramebuffer* GL45Backend::syncGPUObject(const Framebuffer& framebuffer) {
gl::GLFramebuffer* GL45Backend::syncGPUObject(const Framebuffer& framebuffer) const {
return gl::GLFramebuffer::sync<GL45Framebuffer>(framebuffer);
}
GLuint GL45Backend::getFramebufferID(const FramebufferPointer& framebuffer) {
GLuint GL45Backend::getFramebufferID(const FramebufferPointer& framebuffer) const {
return framebuffer ? gl::GLFramebuffer::getId<GL45Framebuffer>(*framebuffer) : 0;
}

View file

@ -29,11 +29,11 @@ GLuint GL45Texture::allocate(const Texture& texture) {
return result;
}
GLuint GL45Backend::getTextureID(const TexturePointer& texture, bool transfer) {
GLuint GL45Backend::getTextureID(const TexturePointer& texture, bool transfer) const {
return GL45Texture::getId<GL45Texture>(texture, transfer);
}
gl::GLTexture* GL45Backend::syncGPUObject(const TexturePointer& texture, bool transfer) {
gl::GLTexture* GL45Backend::syncGPUObject(const TexturePointer& texture, bool transfer) const {
return GL45Texture::sync<GL45Texture>(texture, transfer);
}

View file

@ -37,11 +37,9 @@ void GL45Backend::transferTransformState(const Batch& batch) const {
glNamedBufferData(_transform._cameraBuffer, bufferData.size(), bufferData.data(), GL_STREAM_DRAW);
}
if (!batch._objects.empty()) {
auto byteSize = batch._objects.size() * sizeof(Batch::TransformObject);
bufferData.resize(byteSize);
memcpy(bufferData.data(), batch._objects.data(), byteSize);
glNamedBufferData(_transform._objectBuffer, bufferData.size(), bufferData.data(), GL_STREAM_DRAW);
if (batch._objectsBuffer) {
const auto& sysmem = batch._objectsBuffer->_renderSysmem;
glNamedBufferData(_transform._objectBuffer, sysmem.getSize(), sysmem.readData(), GL_STREAM_DRAW);
}
if (!batch._namedData.empty()) {

View file

@ -34,7 +34,7 @@ size_t Batch::_commandsMax { BATCH_PREALLOCATE_MIN };
size_t Batch::_commandOffsetsMax { BATCH_PREALLOCATE_MIN };
size_t Batch::_paramsMax { BATCH_PREALLOCATE_MIN };
size_t Batch::_dataMax { BATCH_PREALLOCATE_MIN };
size_t Batch::_objectsMax { BATCH_PREALLOCATE_MIN };
//size_t Batch::_objectsMax { BATCH_PREALLOCATE_MIN };
size_t Batch::_drawCallInfosMax { BATCH_PREALLOCATE_MIN };
Batch::Batch() {
@ -42,7 +42,6 @@ Batch::Batch() {
_commandOffsets.reserve(_commandOffsetsMax);
_params.reserve(_paramsMax);
_data.reserve(_dataMax);
_objects.reserve(_objectsMax);
_drawCallInfos.reserve(_drawCallInfosMax);
}
@ -54,7 +53,7 @@ Batch::Batch(const Batch& batch_) {
_data.swap(batch._data);
_invalidModel = batch._invalidModel;
_currentModel = batch._currentModel;
_objects.swap(batch._objects);
_objectsBuffer.swap(batch._objectsBuffer);
_currentNamedCall = batch._currentNamedCall;
_buffers._items.swap(batch._buffers._items);
@ -78,7 +77,7 @@ Batch::~Batch() {
_commandOffsetsMax = std::max(_commandOffsets.size(), _commandOffsetsMax);
_paramsMax = std::max(_params.size(), _paramsMax);
_dataMax = std::max(_data.size(), _dataMax);
_objectsMax = std::max(_objects.size(), _objectsMax);
//_objectsMax = std::max(_objectsBuffer->getSize(), _objectsMax);
_drawCallInfosMax = std::max(_drawCallInfos.size(), _drawCallInfosMax);
}
@ -87,7 +86,7 @@ void Batch::clear() {
_commandOffsetsMax = std::max(_commandOffsets.size(), _commandOffsetsMax);
_paramsMax = std::max(_params.size(), _paramsMax);
_dataMax = std::max(_data.size(), _dataMax);
_objectsMax = std::max(_objects.size(), _objectsMax);
//_objectsMax = std::max(_objects.size(), _objectsMax);
_drawCallInfosMax = std::max(_drawCallInfos.size(), _drawCallInfosMax);
_commands.clear();
@ -100,7 +99,7 @@ void Batch::clear() {
_transforms.clear();
_pipelines.clear();
_framebuffers.clear();
_objects.clear();
_objectsBuffer.reset();
_drawCallInfos.clear();
}
@ -467,14 +466,18 @@ void Batch::captureDrawCallInfoImpl() {
//_model.getInverseMatrix(_object._modelInverse);
object._modelInverse = glm::inverse(object._model);
_objects.emplace_back(object);
if (!_objectsBuffer) {
_objectsBuffer = std::make_shared<Buffer>();
}
_objectsBuffer->append(object);
// Flag is clean
_invalidModel = false;
}
auto& drawCallInfos = getDrawCallInfoBuffer();
drawCallInfos.emplace_back((uint16)_objects.size() - 1);
drawCallInfos.emplace_back((uint16)(_objectsBuffer->getTypedSize<TransformObject>() - 1));
}
void Batch::captureDrawCallInfo() {
@ -629,3 +632,32 @@ void Batch::_glColor4f(float red, float green, float blue, float alpha) {
_params.emplace_back(green);
_params.emplace_back(red);
}
void Batch::finish(BufferUpdates& updates) {
if (_objectsBuffer && _objectsBuffer->isDirty()) {
updates.push_back({ _objectsBuffer, _objectsBuffer->getUpdate() });
}
for (auto& namedCallData : _namedData) {
for (auto& buffer : namedCallData.second.buffers) {
if (!buffer) {
continue;
}
if (!buffer->isDirty()) {
continue;
}
updates.push_back({ buffer, buffer->getUpdate() });
}
}
for (auto& bufferCacheItem : _buffers._items) {
const BufferPointer& buffer = bufferCacheItem._data;
if (!buffer) {
continue;
}
if (!buffer->isDirty()) {
continue;
}
updates.push_back({ buffer, buffer->getUpdate() });
}
}

View file

@ -75,7 +75,7 @@ public:
Function function;
DrawCallInfoBuffer drawCallInfos;
size_t count() const { return drawCallInfos.size(); }
size_t count() const { return drawCallInfos.size(); }
void process(Batch& batch) {
if (function) {
@ -102,6 +102,8 @@ public:
~Batch();
void clear();
// Call on the main thread to prepare for passing to the render thread
void finish(BufferUpdates& updates);
void preExecute();
@ -449,10 +451,9 @@ public:
Mat4 _modelInverse;
};
using TransformObjects = std::vector<TransformObject>;
bool _invalidModel { true };
Transform _currentModel;
TransformObjects _objects;
BufferPointer _objectsBuffer;
static size_t _objectsMax;
BufferCaches _buffers;

View file

@ -24,37 +24,8 @@ Frame::~Frame() {
}
void Frame::finish() {
std::unordered_set<Buffer*> seenBuffers;
for (Batch& batch : batches) {
for (auto& namedCallData : batch._namedData) {
for (auto& buffer : namedCallData.second.buffers) {
if (!buffer) {
continue;
}
if (!buffer->isDirty()) {
continue;
}
if (seenBuffers.count(buffer.get())) {
continue;
}
seenBuffers.insert(buffer.get());
bufferUpdates.push_back({ buffer, buffer->getUpdate() });
}
}
for (auto& bufferCacheItem : batch._buffers._items) {
const BufferPointer& buffer = bufferCacheItem._data;
if (!buffer) {
continue;
}
if (!buffer->isDirty()) {
continue;
}
if (seenBuffers.count(buffer.get())) {
continue;
}
seenBuffers.insert(buffer.get());
bufferUpdates.push_back({ buffer, buffer->getUpdate() });
}
batch.finish(bufferUpdates);
}
}

View file

@ -21,8 +21,6 @@ namespace gpu {
using Batches = std::vector<Batch>;
using FramebufferRecycler = std::function<void(const FramebufferPointer&)>;
using OverlayRecycler = std::function<void(const TexturePointer&)>;
using BufferUpdate = std::pair<BufferPointer, Buffer::Update>;
using BufferUpdates = std::vector<BufferUpdate>;
virtual ~Frame();
void finish();

View file

@ -280,6 +280,9 @@ public:
// The size in bytes of data stored in the buffer
Size getSize() const;
template <typename T>
Size getTypedSize() const { return getSize() / sizeof(T); };
const Byte* getData() const { return getSysmem().readData(); }
// Resize the buffer
@ -374,6 +377,9 @@ protected:
friend class Frame;
};
using BufferUpdate = std::pair<BufferPointer, Buffer::Update>;
using BufferUpdates = std::vector<BufferUpdate>;
typedef std::shared_ptr<Buffer> BufferPointer;
typedef std::vector< BufferPointer > Buffers;

View file

@ -8,13 +8,7 @@
#include "NsightHelpers.h"
#include <QtCore/QThread>
QThread* RENDER_THREAD = nullptr;
bool isRenderThread() {
return QThread::currentThread() == RENDER_THREAD;
}
#include "../gl/src/gl/GLHelpers.h"
#ifdef _WIN32
#if defined(NSIGHT_FOUND)

View file

@ -9,16 +9,9 @@
#ifndef hifi_gl_NsightHelpers_h
#define hifi_gl_NsightHelpers_h
class QThread;
// FIXME find a better place for this, probably in the GL library
extern QThread* RENDER_THREAD;
extern bool isRenderThread();
#ifdef _WIN32
#include <stdint.h>
#include <QtCore/QThread>
class ProfileRange {
public:
ProfileRange(const char *name);