mirror of
https://github.com/HifiExperiments/overte.git
synced 2025-04-14 08:16:03 +02:00
Merge pull request #3992 from samcake/temp0
Add the BufferView class in gpu::Resource
This commit is contained in:
commit
fb15b0f2a7
10 changed files with 431 additions and 34 deletions
|
@ -107,6 +107,19 @@ void Batch::setInputFormat(const Stream::FormatPointer& format) {
|
|||
_params.push_back(_streamFormats.cache(format));
|
||||
}
|
||||
|
||||
void Batch::setInputBuffer(Slot channel, const BufferPointer& buffer, Offset offset, Offset stride) {
|
||||
ADD_COMMAND(setInputBuffer);
|
||||
|
||||
_params.push_back(stride);
|
||||
_params.push_back(offset);
|
||||
_params.push_back(_buffers.cache(buffer));
|
||||
_params.push_back(channel);
|
||||
}
|
||||
|
||||
void Batch::setInputBuffer(Slot channel, const BufferView& view) {
|
||||
setInputBuffer(channel, view._buffer, view._offset, Offset(view._stride));
|
||||
}
|
||||
|
||||
void Batch::setInputStream(Slot startChannel, const BufferStream& stream) {
|
||||
if (stream.getNumBuffers()) {
|
||||
const Buffers& buffers = stream.getBuffers();
|
||||
|
@ -118,15 +131,6 @@ void Batch::setInputStream(Slot startChannel, const BufferStream& stream) {
|
|||
}
|
||||
}
|
||||
|
||||
void Batch::setInputBuffer(Slot channel, const BufferPointer& buffer, Offset offset, Offset stride) {
|
||||
ADD_COMMAND(setInputBuffer);
|
||||
|
||||
_params.push_back(stride);
|
||||
_params.push_back(offset);
|
||||
_params.push_back(_buffers.cache(buffer));
|
||||
_params.push_back(channel);
|
||||
}
|
||||
|
||||
void Batch::setIndexBuffer(Type type, const BufferPointer& buffer, Offset offset) {
|
||||
ADD_COMMAND(setIndexBuffer);
|
||||
|
||||
|
@ -153,3 +157,17 @@ void Batch::setProjectionTransform(const Transform& proj) {
|
|||
_params.push_back(_transforms.cache(proj));
|
||||
}
|
||||
|
||||
void Batch::setUniformBuffer(uint32 slot, const BufferPointer& buffer, Offset offset, Offset size) {
|
||||
ADD_COMMAND(setUniformBuffer);
|
||||
|
||||
_params.push_back(size);
|
||||
_params.push_back(offset);
|
||||
_params.push_back(_buffers.cache(buffer));
|
||||
_params.push_back(slot);
|
||||
}
|
||||
|
||||
void Batch::setUniformBuffer(uint32 slot, const BufferView& view) {
|
||||
setUniformBuffer(slot, view._buffer, view._offset, view._size);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -72,8 +72,9 @@ public:
|
|||
// IndexBuffer
|
||||
void setInputFormat(const Stream::FormatPointer& format);
|
||||
|
||||
void setInputStream(Slot startChannel, const BufferStream& stream); // not a command, just unroll into a loop of setInputBuffer
|
||||
void setInputBuffer(Slot channel, const BufferPointer& buffer, Offset offset, Offset stride);
|
||||
void setInputBuffer(Slot channel, const BufferView& buffer); // not a command, just a shortcut from a BufferView
|
||||
void setInputStream(Slot startChannel, const BufferStream& stream); // not a command, just unroll into a loop of setInputBuffer
|
||||
|
||||
void setIndexBuffer(Type type, const BufferPointer& buffer, Offset offset);
|
||||
|
||||
|
@ -87,6 +88,9 @@ public:
|
|||
void setViewTransform(const Transform& view);
|
||||
void setProjectionTransform(const Transform& proj);
|
||||
|
||||
// Shader Stage
|
||||
void setUniformBuffer(uint32 slot, const BufferPointer& buffer, Offset offset, Offset size);
|
||||
void setUniformBuffer(uint32 slot, const BufferView& view); // not a command, just a shortcut from a BufferView
|
||||
|
||||
// TODO: As long as we have gl calls explicitely issued from interface
|
||||
// code, we need to be able to record and batch these calls. THe long
|
||||
|
@ -117,6 +121,7 @@ public:
|
|||
void _glUseProgram(GLuint program);
|
||||
void _glUniform1f(GLint location, GLfloat v0);
|
||||
void _glUniform2f(GLint location, GLfloat v0, GLfloat v1);
|
||||
void _glUniform4fv(GLint location, GLsizei count, const GLfloat* value);
|
||||
void _glUniformMatrix4fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value);
|
||||
|
||||
void _glMatrixMode(GLenum mode);
|
||||
|
@ -161,6 +166,8 @@ public:
|
|||
COMMAND_setViewTransform,
|
||||
COMMAND_setProjectionTransform,
|
||||
|
||||
COMMAND_setUniformBuffer,
|
||||
|
||||
// TODO: As long as we have gl calls explicitely issued from interface
|
||||
// code, we need to be able to record and batch these calls. THe long
|
||||
// term strategy is to get rid of any GL calls in favor of the HIFI GPU API
|
||||
|
@ -187,6 +194,7 @@ public:
|
|||
COMMAND_glUseProgram,
|
||||
COMMAND_glUniform1f,
|
||||
COMMAND_glUniform2f,
|
||||
COMMAND_glUniform4fv,
|
||||
COMMAND_glUniformMatrix4fv,
|
||||
|
||||
COMMAND_glMatrixMode,
|
||||
|
|
|
@ -12,7 +12,6 @@
|
|||
#define hifi_gpu_Context_h
|
||||
|
||||
#include <assert.h>
|
||||
#include "GPUConfig.h"
|
||||
|
||||
#include "Resource.h"
|
||||
|
||||
|
|
|
@ -12,8 +12,6 @@
|
|||
#define hifi_gpu_Format_h
|
||||
|
||||
#include <assert.h>
|
||||
#include "GPUConfig.h"
|
||||
|
||||
|
||||
namespace gpu {
|
||||
|
||||
|
@ -94,7 +92,8 @@ static const int DIMENSION_COUNT[NUM_DIMENSIONS] = {
|
|||
// Semantic of an Element
|
||||
// Provide information on how to use the element
|
||||
enum Semantic {
|
||||
RGB = 0,
|
||||
RAW = 0, // used as RAW memory
|
||||
RGB,
|
||||
RGBA,
|
||||
XYZ,
|
||||
XYZW,
|
||||
|
@ -104,6 +103,8 @@ enum Semantic {
|
|||
DIR_XYZ,
|
||||
UV,
|
||||
R8,
|
||||
INDEX, //used by index buffer of a mesh
|
||||
PART, // used by part buffer of a mesh
|
||||
|
||||
NUM_SEMANTICS,
|
||||
};
|
||||
|
@ -119,7 +120,7 @@ public:
|
|||
_type(type)
|
||||
{}
|
||||
Element() :
|
||||
_semantic(R8),
|
||||
_semantic(RAW),
|
||||
_dimension(SCALAR),
|
||||
_type(INT8)
|
||||
{}
|
||||
|
|
|
@ -31,6 +31,8 @@ GLBackend::CommandCall GLBackend::_commandCalls[Batch::NUM_COMMANDS] =
|
|||
(&::gpu::GLBackend::do_setViewTransform),
|
||||
(&::gpu::GLBackend::do_setProjectionTransform),
|
||||
|
||||
(&::gpu::GLBackend::do_setUniformBuffer),
|
||||
|
||||
(&::gpu::GLBackend::do_glEnable),
|
||||
(&::gpu::GLBackend::do_glDisable),
|
||||
|
||||
|
@ -54,6 +56,7 @@ GLBackend::CommandCall GLBackend::_commandCalls[Batch::NUM_COMMANDS] =
|
|||
(&::gpu::GLBackend::do_glUseProgram),
|
||||
(&::gpu::GLBackend::do_glUniform1f),
|
||||
(&::gpu::GLBackend::do_glUniform2f),
|
||||
(&::gpu::GLBackend::do_glUniform4fv),
|
||||
(&::gpu::GLBackend::do_glUniformMatrix4fv),
|
||||
|
||||
(&::gpu::GLBackend::do_glMatrixMode),
|
||||
|
@ -483,6 +486,25 @@ void GLBackend::updateTransform() {
|
|||
}
|
||||
}
|
||||
|
||||
void GLBackend::do_setUniformBuffer(Batch& batch, uint32 paramOffset) {
|
||||
GLuint slot = batch._params[paramOffset + 3]._uint;
|
||||
BufferPointer uniformBuffer = batch._buffers.get(batch._params[paramOffset + 2]._uint);
|
||||
GLintptr rangeStart = batch._params[paramOffset + 1]._uint;
|
||||
GLsizeiptr rangeSize = batch._params[paramOffset + 0]._uint;
|
||||
#if defined(Q_OS_MAC)
|
||||
GLfloat* data = (GLfloat*) (uniformBuffer->getData() + rangeStart);
|
||||
glUniform4fv(slot, rangeSize / sizeof(GLfloat[4]), data);
|
||||
#else
|
||||
GLuint bo = getBufferID(*uniformBuffer);
|
||||
glBindBufferRange(GL_UNIFORM_BUFFER, slot, bo, rangeStart, rangeSize);
|
||||
|
||||
// glUniformBufferEXT(_shader._program, slot, bo);
|
||||
|
||||
//glBindBufferBase(GL_UNIFORM_BUFFER, slot, bo);
|
||||
#endif
|
||||
CHECK_GL_ERROR();
|
||||
}
|
||||
|
||||
// TODO: As long as we have gl calls explicitely issued from interface
|
||||
// code, we need to be able to record and batch these calls. THe long
|
||||
// term strategy is to get rid of any GL calls in favor of the HIFI GPU API
|
||||
|
@ -672,7 +694,10 @@ void Batch::_glUseProgram(GLuint program) {
|
|||
DO_IT_NOW(_glUseProgram, 1);
|
||||
}
|
||||
void GLBackend::do_glUseProgram(Batch& batch, uint32 paramOffset) {
|
||||
glUseProgram(batch._params[paramOffset]._uint);
|
||||
|
||||
_shader._program = batch._params[paramOffset]._uint;
|
||||
glUseProgram(_shader._program);
|
||||
|
||||
CHECK_GL_ERROR();
|
||||
}
|
||||
|
||||
|
@ -708,6 +733,25 @@ void GLBackend::do_glUniform2f(Batch& batch, uint32 paramOffset) {
|
|||
CHECK_GL_ERROR();
|
||||
}
|
||||
|
||||
void Batch::_glUniform4fv(GLint location, GLsizei count, const GLfloat* value) {
|
||||
ADD_COMMAND_GL(glUniform4fv);
|
||||
|
||||
const int VEC4_SIZE = 4 * sizeof(float);
|
||||
_params.push_back(cacheData(count * VEC4_SIZE, value));
|
||||
_params.push_back(count);
|
||||
_params.push_back(location);
|
||||
|
||||
DO_IT_NOW(_glUniform4fv, 3);
|
||||
}
|
||||
void GLBackend::do_glUniform4fv(Batch& batch, uint32 paramOffset) {
|
||||
glUniform4fv(
|
||||
batch._params[paramOffset + 2]._int,
|
||||
batch._params[paramOffset + 1]._uint,
|
||||
(const GLfloat*)batch.editData(batch._params[paramOffset + 0]._uint));
|
||||
|
||||
CHECK_GL_ERROR();
|
||||
}
|
||||
|
||||
void Batch::_glUniformMatrix4fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value) {
|
||||
ADD_COMMAND_GL(glUniformMatrix4fv);
|
||||
|
||||
|
|
|
@ -122,6 +122,19 @@ protected:
|
|||
_lastMode(GL_TEXTURE) {}
|
||||
} _transform;
|
||||
|
||||
// Shader Stage
|
||||
void do_setUniformBuffer(Batch& batch, uint32 paramOffset);
|
||||
|
||||
void updateShader();
|
||||
struct ShaderStageState {
|
||||
|
||||
GLuint _program;
|
||||
|
||||
ShaderStageState() :
|
||||
_program(0) {}
|
||||
} _shader;
|
||||
|
||||
|
||||
// TODO: As long as we have gl calls explicitely issued from interface
|
||||
// code, we need to be able to record and batch these calls. THe long
|
||||
// term strategy is to get rid of any GL calls in favor of the HIFI GPU API
|
||||
|
@ -148,6 +161,7 @@ protected:
|
|||
void do_glUseProgram(Batch& batch, uint32 paramOffset);
|
||||
void do_glUniform1f(Batch& batch, uint32 paramOffset);
|
||||
void do_glUniform2f(Batch& batch, uint32 paramOffset);
|
||||
void do_glUniform4fv(Batch& batch, uint32 paramOffset);
|
||||
void do_glUniformMatrix4fv(Batch& batch, uint32 paramOffset);
|
||||
|
||||
void do_glMatrixMode(Batch& batch, uint32 paramOffset);
|
||||
|
|
|
@ -67,6 +67,26 @@ Resource::Sysmem::Sysmem(Size size, const Byte* bytes) :
|
|||
}
|
||||
}
|
||||
|
||||
Resource::Sysmem::Sysmem(const Sysmem& sysmem) :
|
||||
_stamp(0),
|
||||
_size(0),
|
||||
_data(NULL)
|
||||
{
|
||||
if (sysmem.getSize() > 0) {
|
||||
_size = allocateMemory(&_data, sysmem.getSize());
|
||||
if (_size >= sysmem.getSize()) {
|
||||
if (sysmem.readData()) {
|
||||
memcpy(_data, sysmem.readData(), sysmem.getSize());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Resource::Sysmem& Resource::Sysmem::operator=(const Sysmem& sysmem) {
|
||||
setData(sysmem.getSize(), sysmem.readData());
|
||||
return (*this);
|
||||
}
|
||||
|
||||
Resource::Sysmem::~Sysmem() {
|
||||
deallocateMemory( _data, _size );
|
||||
_data = NULL;
|
||||
|
@ -152,9 +172,25 @@ Resource::Size Resource::Sysmem::append(Size size, const Byte* bytes) {
|
|||
|
||||
Buffer::Buffer() :
|
||||
Resource(),
|
||||
_sysmem(NULL),
|
||||
_sysmem(new Sysmem()),
|
||||
_gpuObject(NULL) {
|
||||
_sysmem = new Sysmem();
|
||||
}
|
||||
|
||||
Buffer::Buffer(Size size, const Byte* bytes) :
|
||||
Resource(),
|
||||
_sysmem(new Sysmem(size, bytes)),
|
||||
_gpuObject(NULL) {
|
||||
}
|
||||
|
||||
Buffer::Buffer(const Buffer& buf) :
|
||||
Resource(),
|
||||
_sysmem(new Sysmem(buf.getSysmem())),
|
||||
_gpuObject(NULL) {
|
||||
}
|
||||
|
||||
Buffer& Buffer::operator=(const Buffer& buf) {
|
||||
(*_sysmem) = buf.getSysmem();
|
||||
return (*this);
|
||||
}
|
||||
|
||||
Buffer::~Buffer() {
|
||||
|
|
|
@ -12,13 +12,15 @@
|
|||
#define hifi_gpu_Resource_h
|
||||
|
||||
#include <assert.h>
|
||||
#include "GPUConfig.h"
|
||||
|
||||
#include "Format.h"
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include <QSharedPointer>
|
||||
#ifdef _DEBUG
|
||||
#include <QDebug>
|
||||
#endif
|
||||
|
||||
namespace gpu {
|
||||
|
||||
|
@ -29,7 +31,7 @@ typedef int Stamp;
|
|||
class Resource {
|
||||
public:
|
||||
typedef unsigned char Byte;
|
||||
typedef unsigned int Size;
|
||||
typedef unsigned int Size;
|
||||
|
||||
static const Size NOT_ALLOCATED = -1;
|
||||
|
||||
|
@ -47,6 +49,8 @@ protected:
|
|||
|
||||
Sysmem();
|
||||
Sysmem(Size size, const Byte* bytes);
|
||||
Sysmem(const Sysmem& sysmem); // deep copy of the sysmem buffer
|
||||
Sysmem& operator=(const Sysmem& sysmem); // deep copy of the sysmem buffer
|
||||
~Sysmem();
|
||||
|
||||
Size getSize() const { return _size; }
|
||||
|
@ -90,9 +94,6 @@ protected:
|
|||
static void deallocateMemory(Byte* memDeallocated, Size size);
|
||||
|
||||
private:
|
||||
Sysmem(const Sysmem& sysmem) {}
|
||||
Sysmem &operator=(const Sysmem& other) {return *this;}
|
||||
|
||||
Stamp _stamp;
|
||||
Size _size;
|
||||
Byte* _data;
|
||||
|
@ -104,12 +105,15 @@ class Buffer : public Resource {
|
|||
public:
|
||||
|
||||
Buffer();
|
||||
Buffer(const Buffer& buf);
|
||||
Buffer(Size size, const Byte* bytes);
|
||||
Buffer(const Buffer& buf); // deep copy of the sysmem buffer
|
||||
Buffer& operator=(const Buffer& buf); // deep copy of the sysmem buffer
|
||||
~Buffer();
|
||||
|
||||
// The size in bytes of data stored in the buffer
|
||||
Size getSize() const { return getSysmem().getSize(); }
|
||||
const Byte* getData() const { return getSysmem().readData(); }
|
||||
Byte* editData() { return editSysmem().editData(); }
|
||||
|
||||
// Resize the buffer
|
||||
// Keep previous data [0 to min(pSize, mSize)]
|
||||
|
@ -130,7 +134,7 @@ public:
|
|||
|
||||
// Access the sysmem object.
|
||||
const Sysmem& getSysmem() const { assert(_sysmem); return (*_sysmem); }
|
||||
|
||||
Sysmem& editSysmem() { assert(_sysmem); return (*_sysmem); }
|
||||
|
||||
protected:
|
||||
|
||||
|
@ -138,8 +142,6 @@ protected:
|
|||
|
||||
mutable GPUObject* _gpuObject;
|
||||
|
||||
Sysmem& editSysmem() { assert(_sysmem); return (*_sysmem); }
|
||||
|
||||
// This shouldn't be used by anything else than the Backend class with the proper casting.
|
||||
void setGPUObject(GPUObject* gpuObject) const { _gpuObject = gpuObject; }
|
||||
GPUObject* getGPUObject() const { return _gpuObject; }
|
||||
|
@ -149,6 +151,281 @@ protected:
|
|||
|
||||
typedef QSharedPointer<Buffer> BufferPointer;
|
||||
typedef std::vector< BufferPointer > Buffers;
|
||||
|
||||
|
||||
class BufferView {
|
||||
public:
|
||||
typedef Resource::Size Size;
|
||||
typedef int Index;
|
||||
|
||||
BufferPointer _buffer;
|
||||
Size _offset;
|
||||
Size _size;
|
||||
Element _element;
|
||||
uint16 _stride;
|
||||
|
||||
BufferView() :
|
||||
_buffer(NULL),
|
||||
_offset(0),
|
||||
_size(0),
|
||||
_element(gpu::SCALAR, gpu::UINT8, gpu::RAW),
|
||||
_stride(1)
|
||||
{};
|
||||
|
||||
BufferView(const Element& element) :
|
||||
_buffer(NULL),
|
||||
_offset(0),
|
||||
_size(0),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
|
||||
// create the BufferView and own the Buffer
|
||||
BufferView(Buffer* newBuffer, const Element& element = Element(gpu::SCALAR, gpu::UINT8, gpu::RAW)) :
|
||||
_buffer(newBuffer),
|
||||
_offset(0),
|
||||
_size(newBuffer->getSize()),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
BufferView(const BufferPointer& buffer, const Element& element = Element(gpu::SCALAR, gpu::UINT8, gpu::RAW)) :
|
||||
_buffer(buffer),
|
||||
_offset(0),
|
||||
_size(buffer->getSize()),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
BufferView(const BufferPointer& buffer, Size offset, Size size, const Element& element = Element(gpu::SCALAR, gpu::UINT8, gpu::RAW)) :
|
||||
_buffer(buffer),
|
||||
_offset(offset),
|
||||
_size(size),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
~BufferView() {}
|
||||
BufferView(const BufferView& view) = default;
|
||||
BufferView& operator=(const BufferView& view) = default;
|
||||
|
||||
Size getNumElements() const { return _size / _element.getSize(); }
|
||||
|
||||
//Template iterator with random access on the buffer sysmem
|
||||
template<typename T>
|
||||
class Iterator : public std::iterator<std::random_access_iterator_tag,
|
||||
T,
|
||||
Index,
|
||||
T*,
|
||||
T&>
|
||||
{
|
||||
public:
|
||||
|
||||
Iterator(T* ptr = NULL) { _ptr = ptr; }
|
||||
Iterator(const Iterator<T>& iterator) = default;
|
||||
~Iterator() {}
|
||||
|
||||
Iterator<T>& operator=(const Iterator<T>& iterator) = default;
|
||||
Iterator<T>& operator=(T* ptr) {
|
||||
_ptr = ptr;
|
||||
return (*this);
|
||||
}
|
||||
|
||||
operator bool() const
|
||||
{
|
||||
if(_ptr)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
bool operator==(const Iterator<T>& iterator) const { return (_ptr == iterator.getConstPtr()); }
|
||||
bool operator!=(const Iterator<T>& iterator) const { return (_ptr != iterator.getConstPtr()); }
|
||||
|
||||
Iterator<T>& operator+=(const Index& movement) {
|
||||
_ptr += movement;
|
||||
return (*this);
|
||||
}
|
||||
Iterator<T>& operator-=(const Index& movement) {
|
||||
_ptr -= movement;
|
||||
return (*this);
|
||||
}
|
||||
Iterator<T>& operator++() {
|
||||
++_ptr;
|
||||
return (*this);
|
||||
}
|
||||
Iterator<T>& operator--() {
|
||||
--_ptr;
|
||||
return (*this);
|
||||
}
|
||||
Iterator<T> operator++(Index) {
|
||||
auto temp(*this);
|
||||
++_ptr;
|
||||
return temp;
|
||||
}
|
||||
Iterator<T> operator--(Index) {
|
||||
auto temp(*this);
|
||||
--_ptr;
|
||||
return temp;
|
||||
}
|
||||
Iterator<T> operator+(const Index& movement) {
|
||||
auto oldPtr = _ptr;
|
||||
_ptr += movement;
|
||||
auto temp(*this);
|
||||
_ptr = oldPtr;
|
||||
return temp;
|
||||
}
|
||||
Iterator<T> operator-(const Index& movement) {
|
||||
auto oldPtr = _ptr;
|
||||
_ptr -= movement;
|
||||
auto temp(*this);
|
||||
_ptr = oldPtr;
|
||||
return temp;
|
||||
}
|
||||
|
||||
Index operator-(const Iterator<T>& iterator) { return (iterator.getPtr() - this->getPtr())/sizeof(T); }
|
||||
|
||||
T& operator*(){return *_ptr;}
|
||||
const T& operator*()const{return *_ptr;}
|
||||
T* operator->(){return _ptr;}
|
||||
|
||||
T* getPtr()const{return _ptr;}
|
||||
const T* getConstPtr()const{return _ptr;}
|
||||
|
||||
protected:
|
||||
|
||||
T* _ptr;
|
||||
};
|
||||
|
||||
template <typename T> Iterator<T> begin() { return Iterator<T>(&edit<T>(0)); }
|
||||
template <typename T> Iterator<T> end() { return Iterator<T>(&edit<T>(getNum<T>())); }
|
||||
template <typename T> Iterator<const T> cbegin() const { return Iterator<const T>(&get<T>(0)); }
|
||||
template <typename T> Iterator<const T> cend() const { return Iterator<const T>(&get<T>(getNum<T>())); }
|
||||
|
||||
// the number of elements of the specified type fitting in the view size
|
||||
template <typename T> Index getNum() const {
|
||||
return Index(_size / sizeof(T));
|
||||
}
|
||||
|
||||
template <typename T> const T& get() const {
|
||||
#if _DEBUG
|
||||
if (_buffer.isNull()) {
|
||||
qDebug() << "Accessing null gpu::buffer!";
|
||||
}
|
||||
if (sizeof(T) > (_buffer->getSize() - _offset)) {
|
||||
qDebug() << "Accessing buffer in non allocated memory, element size = " << sizeof(T) << " available space in buffer at offset is = " << (_buffer->getSize() - _offset);
|
||||
}
|
||||
if (sizeof(T) > _size) {
|
||||
qDebug() << "Accessing buffer outside the BufferView range, element size = " << sizeof(T) << " when bufferView size = " << _size;
|
||||
}
|
||||
#endif
|
||||
const T* t = (reinterpret_cast<const T*> (_buffer->getData() + _offset));
|
||||
return *(t);
|
||||
}
|
||||
|
||||
template <typename T> T& edit() {
|
||||
#if _DEBUG
|
||||
if (_buffer.isNull()) {
|
||||
qDebug() << "Accessing null gpu::buffer!";
|
||||
}
|
||||
if (sizeof(T) > (_buffer->getSize() - _offset)) {
|
||||
qDebug() << "Accessing buffer in non allocated memory, element size = " << sizeof(T) << " available space in buffer at offset is = " << (_buffer->getSize() - _offset);
|
||||
}
|
||||
if (sizeof(T) > _size) {
|
||||
qDebug() << "Accessing buffer outside the BufferView range, element size = " << sizeof(T) << " when bufferView size = " << _size;
|
||||
}
|
||||
#endif
|
||||
T* t = (reinterpret_cast<T*> (_buffer->editData() + _offset));
|
||||
return *(t);
|
||||
}
|
||||
|
||||
template <typename T> const T& get(const Index index) const {
|
||||
Resource::Size elementOffset = index * sizeof(T) + _offset;
|
||||
#if _DEBUG
|
||||
if (_buffer.isNull()) {
|
||||
qDebug() << "Accessing null gpu::buffer!";
|
||||
}
|
||||
if (sizeof(T) > (_buffer->getSize() - elementOffset)) {
|
||||
qDebug() << "Accessing buffer in non allocated memory, index = " << index << ", element size = " << sizeof(T) << " available space in buffer at offset is = " << (_buffer->getSize() - elementOffset);
|
||||
}
|
||||
if (index > getNum<T>()) {
|
||||
qDebug() << "Accessing buffer outside the BufferView range, index = " << index << " number elements = " << getNum<T>();
|
||||
}
|
||||
#endif
|
||||
return *(reinterpret_cast<const T*> (_buffer->getData() + elementOffset));
|
||||
}
|
||||
|
||||
template <typename T> T& edit(const Index index) const {
|
||||
Resource::Size elementOffset = index * sizeof(T) + _offset;
|
||||
#if _DEBUG
|
||||
if (_buffer.isNull()) {
|
||||
qDebug() << "Accessing null gpu::buffer!";
|
||||
}
|
||||
if (sizeof(T) > (_buffer->getSize() - elementOffset)) {
|
||||
qDebug() << "Accessing buffer in non allocated memory, index = " << index << ", element size = " << sizeof(T) << " available space in buffer at offset is = " << (_buffer->getSize() - elementOffset);
|
||||
}
|
||||
if (index > getNum<T>()) {
|
||||
qDebug() << "Accessing buffer outside the BufferView range, index = " << index << " number elements = " << getNum<T>();
|
||||
}
|
||||
#endif
|
||||
return *(reinterpret_cast<T*> (_buffer->editData() + elementOffset));
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// TODO: For now TextureView works with Buffer as a place holder for the Texture.
|
||||
// The overall logic should be about the same except that the Texture will be a real GL Texture under the hood
|
||||
class TextureView {
|
||||
public:
|
||||
typedef Resource::Size Size;
|
||||
typedef int Index;
|
||||
|
||||
BufferPointer _buffer;
|
||||
Size _offset;
|
||||
Size _size;
|
||||
Element _element;
|
||||
uint16 _stride;
|
||||
|
||||
TextureView() :
|
||||
_buffer(NULL),
|
||||
_offset(0),
|
||||
_size(0),
|
||||
_element(gpu::VEC3, gpu::UINT8, gpu::RGB),
|
||||
_stride(1)
|
||||
{};
|
||||
|
||||
TextureView(const Element& element) :
|
||||
_buffer(NULL),
|
||||
_offset(0),
|
||||
_size(0),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
|
||||
// create the BufferView and own the Buffer
|
||||
TextureView(Buffer* newBuffer, const Element& element) :
|
||||
_buffer(newBuffer),
|
||||
_offset(0),
|
||||
_size(newBuffer->getSize()),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
TextureView(const BufferPointer& buffer, const Element& element) :
|
||||
_buffer(buffer),
|
||||
_offset(0),
|
||||
_size(buffer->getSize()),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
TextureView(const BufferPointer& buffer, Size offset, Size size, const Element& element) :
|
||||
_buffer(buffer),
|
||||
_offset(offset),
|
||||
_size(size),
|
||||
_element(element),
|
||||
_stride(uint16(element.getSize()))
|
||||
{};
|
||||
~TextureView() {}
|
||||
TextureView(const TextureView& view) = default;
|
||||
TextureView& operator=(const TextureView& view) = default;
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -18,7 +18,7 @@ void Stream::Format::evaluateCache() {
|
|||
_elementTotalSize = 0;
|
||||
for(AttributeMap::iterator it = _attributes.begin(); it != _attributes.end(); it++) {
|
||||
Attribute& attrib = (*it).second;
|
||||
Channel& channel = _channels[attrib._channel];
|
||||
ChannelInfo& channel = _channels[attrib._channel];
|
||||
channel._slots.push_back(attrib._slot);
|
||||
channel._stride = std::max(channel._stride, attrib.getSize() + attrib._offset);
|
||||
channel._netSize += attrib.getSize();
|
||||
|
@ -41,7 +41,7 @@ BufferStream::BufferStream() :
|
|||
BufferStream::~BufferStream() {
|
||||
}
|
||||
|
||||
void BufferStream::addBuffer(BufferPointer& buffer, Offset offset, Offset stride) {
|
||||
void BufferStream::addBuffer(const BufferPointer& buffer, Offset offset, Offset stride) {
|
||||
_buffers.push_back(buffer);
|
||||
_offsets.push_back(offset);
|
||||
_strides.push_back(stride);
|
||||
|
|
|
@ -12,7 +12,6 @@
|
|||
#define hifi_gpu_Stream_h
|
||||
|
||||
#include <assert.h>
|
||||
#include "GPUConfig.h"
|
||||
|
||||
#include "Resource.h"
|
||||
#include "Format.h"
|
||||
|
@ -83,16 +82,16 @@ public:
|
|||
public:
|
||||
typedef std::map< Slot, Attribute > AttributeMap;
|
||||
|
||||
class Channel {
|
||||
class ChannelInfo {
|
||||
public:
|
||||
std::vector< Slot > _slots;
|
||||
std::vector< Offset > _offsets;
|
||||
Offset _stride;
|
||||
uint32 _netSize;
|
||||
|
||||
Channel() : _stride(0), _netSize(0) {}
|
||||
ChannelInfo() : _stride(0), _netSize(0) {}
|
||||
};
|
||||
typedef std::map< Slot, Channel > ChannelMap;
|
||||
typedef std::map< Slot, ChannelInfo > ChannelMap;
|
||||
|
||||
Format() :
|
||||
_attributes(),
|
||||
|
@ -104,6 +103,7 @@ public:
|
|||
|
||||
uint8 getNumChannels() const { return _channels.size(); }
|
||||
const ChannelMap& getChannels() const { return _channels; }
|
||||
const Offset getChannelStride(Slot channel) const { return _channels.at(channel)._stride; }
|
||||
|
||||
uint32 getElementTotalSize() const { return _elementTotalSize; }
|
||||
|
||||
|
@ -131,7 +131,7 @@ public:
|
|||
BufferStream();
|
||||
~BufferStream();
|
||||
|
||||
void addBuffer(BufferPointer& buffer, Offset offset, Offset stride);
|
||||
void addBuffer(const BufferPointer& buffer, Offset offset, Offset stride);
|
||||
|
||||
const Buffers& getBuffers() const { return _buffers; }
|
||||
const Offsets& getOffsets() const { return _offsets; }
|
||||
|
|
Loading…
Reference in a new issue