GL: Use std::array where applicable

This commit is contained in:
Lioncash 2019-08-24 19:06:09 -04:00
parent 07835b58fb
commit e3b44edd51
1 changed files with 166 additions and 118 deletions

View File

@ -93,22 +93,29 @@ class GLDataFactoryImpl final : public GLDataFactory, public GraphicsDataFactory
commitTransaction([this](IGraphicsDataFactory::Context& ctx) {
auto vertex = ctx.newShaderStage((uint8_t*)GammaVS, 0, PipelineStage::Vertex);
auto fragment = ctx.newShaderStage((uint8_t*)GammaFS, 0, PipelineStage::Fragment);
AdditionalPipelineInfo info = {
const AdditionalPipelineInfo info = {
BlendFactor::One, BlendFactor::Zero, Primitive::TriStrips, ZTest::None, false, true, false, CullMode::None};
const VertexElementDescriptor vfmt[] = {{VertexSemantic::Position4}, {VertexSemantic::UV4}};
m_gammaShader = ctx.newShaderPipeline(vertex, fragment, vfmt, info);
const std::array<VertexElementDescriptor, 2> vfmt{{{VertexSemantic::Position4}, {VertexSemantic::UV4}}};
m_gammaShader = ctx.newShaderPipeline(vertex, fragment, vfmt.data(), info);
m_gammaLUT = ctx.newDynamicTexture(256, 256, TextureFormat::I16, TextureClampMode::ClampToEdge);
const struct Vert {
float pos[4];
float uv[4];
} verts[4] = {{{-1.f, -1.f, 0.f, 1.f}, {0.f, 0.f, 0.f, 0.f}},
struct Vert {
std::array<float, 4> pos;
std::array<float, 4> uv;
};
constexpr std::array<Vert, 4> verts{{
{{-1.f, -1.f, 0.f, 1.f}, {0.f, 0.f, 0.f, 0.f}},
{{1.f, -1.f, 0.f, 1.f}, {1.f, 0.f, 0.f, 0.f}},
{{-1.f, 1.f, 0.f, 1.f}, {0.f, 1.f, 0.f, 0.f}},
{{1.f, 1.f, 0.f, 1.f}, {1.f, 1.f, 0.f, 0.f}}};
m_gammaVBO = ctx.newStaticBuffer(BufferUse::Vertex, verts, 32, 4);
ObjToken<ITexture> texs[] = {{}, m_gammaLUT.get()};
m_gammaBinding = ctx.newShaderDataBinding(m_gammaShader, m_gammaVBO.get(), {}, {}, 0, nullptr, nullptr, 2, texs,
nullptr, nullptr);
{{1.f, 1.f, 0.f, 1.f}, {1.f, 1.f, 0.f, 0.f}},
}};
m_gammaVBO = ctx.newStaticBuffer(BufferUse::Vertex, verts.data(), sizeof(Vert), verts.size());
const std::array<ObjToken<ITexture>, 2> texs{{
{},
m_gammaLUT.get(),
}};
m_gammaBinding = ctx.newShaderDataBinding(m_gammaShader, m_gammaVBO.get(), {}, {}, 0, nullptr, nullptr,
texs.size(), texs.data(), nullptr, nullptr);
return true;
} BooTrace);
}
@ -143,7 +150,12 @@ public:
bool areShadersReady() override { return true; }
};
static const GLenum USE_TABLE[] = {GL_INVALID_ENUM, GL_ARRAY_BUFFER, GL_ELEMENT_ARRAY_BUFFER, GL_UNIFORM_BUFFER};
constexpr std::array<GLenum, 4> USE_TABLE{
GL_INVALID_ENUM,
GL_ARRAY_BUFFER,
GL_ELEMENT_ARRAY_BUFFER,
GL_UNIFORM_BUFFER,
};
class GLGraphicsBufferS : public GraphicsDataNode<IGraphicsBufferS> {
friend class GLDataFactory;
@ -174,25 +186,26 @@ class GLGraphicsBufferD : public GraphicsDataNode<IGraphicsBufferD, DataCls> {
friend class GLDataFactory;
friend class GLDataFactoryImpl;
friend struct GLCommandQueue;
GLuint m_bufs[3];
std::array<GLuint, 3> m_bufs{};
GLenum m_target;
std::unique_ptr<uint8_t[]> m_cpuBuf;
size_t m_cpuSz = 0;
int m_validMask = 0;
GLGraphicsBufferD(const ObjToken<DataCls>& parent, BufferUse use, size_t sz)
: GraphicsDataNode<IGraphicsBufferD, DataCls>(parent)
, m_target(USE_TABLE[int(use)])
, m_cpuBuf(new uint8_t[sz])
, m_cpuSz(sz) {
glGenBuffers(3, m_bufs);
for (int i = 0; i < 3; ++i) {
glBindBuffer(m_target, m_bufs[i]);
glGenBuffers(GLsizei(m_bufs.size()), m_bufs.data());
for (const GLuint buf : m_bufs) {
glBindBuffer(m_target, buf);
glBufferData(m_target, m_cpuSz, nullptr, GL_STREAM_DRAW);
}
}
public:
~GLGraphicsBufferD() override { glDeleteBuffers(3, m_bufs); }
~GLGraphicsBufferD() override { glDeleteBuffers(GLsizei(m_bufs.size()), m_bufs.data()); }
void update(int b) {
int slot = 1 << b;
@ -240,16 +253,16 @@ static void SetClampMode(GLenum target, TextureClampMode clampMode) {
glTexParameteri(target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
glTexParameteri(target, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
glTexParameteri(target, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_BORDER);
GLfloat color[] = {1.f, 1.f, 1.f, 1.f};
glTexParameterfv(target, GL_TEXTURE_BORDER_COLOR, color);
constexpr std::array<GLfloat, 4> color{1.f, 1.f, 1.f, 1.f};
glTexParameterfv(target, GL_TEXTURE_BORDER_COLOR, color.data());
break;
}
case TextureClampMode::ClampToBlack: {
glTexParameteri(target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
glTexParameteri(target, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
glTexParameteri(target, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_BORDER);
GLfloat color[] = {0.f, 0.f, 0.f, 1.f};
glTexParameterfv(target, GL_TEXTURE_BORDER_COLOR, color);
constexpr std::array<GLfloat, 4> color{0.f, 0.f, 0.f, 1.f};
glTexParameterfv(target, GL_TEXTURE_BORDER_COLOR, color.data());
break;
}
case TextureClampMode::ClampToEdge: {
@ -441,7 +454,7 @@ public:
class GLTextureD : public GraphicsDataNode<ITextureD> {
friend class GLDataFactory;
friend struct GLCommandQueue;
GLuint m_texs[3];
std::array<GLuint, 3> m_texs{};
std::unique_ptr<uint8_t[]> m_cpuBuf;
size_t m_cpuSz = 0;
GLenum m_intFormat, m_format;
@ -475,10 +488,10 @@ class GLTextureD : public GraphicsDataNode<ITextureD> {
m_cpuSz = width * height * pxPitch;
m_cpuBuf.reset(new uint8_t[m_cpuSz]);
GLenum compType = m_intFormat == GL_R16 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_BYTE;
glGenTextures(3, m_texs);
for (int i = 0; i < 3; ++i) {
glBindTexture(GL_TEXTURE_2D, m_texs[i]);
const GLenum compType = m_intFormat == GL_R16 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_BYTE;
glGenTextures(GLsizei(m_texs.size()), m_texs.data());
for (const GLuint tex : m_texs) {
glBindTexture(GL_TEXTURE_2D, tex);
glTexImage2D(GL_TEXTURE_2D, 0, m_intFormat, width, height, 0, m_format, compType, nullptr);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
@ -487,7 +500,7 @@ class GLTextureD : public GraphicsDataNode<ITextureD> {
}
public:
~GLTextureD() override { glDeleteTextures(3, m_texs); }
~GLTextureD() override { glDeleteTextures(GLsizei(m_texs.size()), m_texs.data()); }
void update(int b) {
int slot = 1 << b;
@ -512,11 +525,13 @@ public:
void unmap() override { m_validMask = 0; }
void setClampMode(TextureClampMode mode) override {
if (m_clampMode == mode)
if (m_clampMode == mode) {
return;
}
m_clampMode = mode;
for (int i = 0; i < 3; ++i) {
glBindTexture(GL_TEXTURE_2D, m_texs[i]);
for (const GLuint tex : m_texs) {
glBindTexture(GL_TEXTURE_2D, tex);
SetClampMode(GL_TEXTURE_2D, mode);
}
}
@ -533,9 +548,9 @@ class GLTextureR : public GraphicsDataNode<ITextureR> {
friend class GLDataFactory;
friend struct GLCommandQueue;
struct GLCommandQueue* m_q;
GLuint m_texs[2] = {};
GLuint m_bindTexs[2][MAX_BIND_TEXS] = {};
GLuint m_bindFBOs[2][MAX_BIND_TEXS] = {};
std::array<GLuint, 2> m_texs{};
std::array<std::array<GLuint, MAX_BIND_TEXS>, 2> m_bindTexs{};
std::array<std::array<GLuint, MAX_BIND_TEXS>, 2> m_bindFBOs{};
GLuint m_fbo = 0;
size_t m_width = 0;
size_t m_height = 0;
@ -548,10 +563,10 @@ class GLTextureR : public GraphicsDataNode<ITextureR> {
public:
~GLTextureR() override {
glDeleteTextures(2, m_texs);
glDeleteTextures(MAX_BIND_TEXS * 2, m_bindTexs[0]);
glDeleteTextures(GLsizei(m_texs.size()), m_texs.data());
glDeleteTextures(MAX_BIND_TEXS * 2, m_bindTexs[0].data());
if (m_samples > 1)
glDeleteFramebuffers(MAX_BIND_TEXS * 2, m_bindFBOs[0]);
glDeleteFramebuffers(MAX_BIND_TEXS * 2, m_bindFBOs[0].data());
glDeleteFramebuffers(1, &m_fbo);
}
@ -593,29 +608,33 @@ public:
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
}
for (int i = 0; i < MAX_BIND_TEXS; ++i) {
if (m_bindTexs[0][i]) {
glBindTexture(GL_TEXTURE_2D, m_bindTexs[0][i]);
glTexImage2D(GL_TEXTURE_2D, 0, m_colorFormat, width, height, 0, GL_RGBA, compType, nullptr);
}
for (const GLuint bindTex : m_bindTexs[0]) {
if (bindTex == 0) {
continue;
}
for (int i = 0; i < MAX_BIND_TEXS; ++i) {
if (m_bindTexs[1][i]) {
glBindTexture(GL_TEXTURE_2D, m_bindTexs[1][i]);
glBindTexture(GL_TEXTURE_2D, bindTex);
glTexImage2D(GL_TEXTURE_2D, 0, m_colorFormat, width, height, 0, GL_RGBA, compType, nullptr);
}
for (const GLuint bindTex : m_bindTexs[1]) {
if (bindTex == 0) {
continue;
}
glBindTexture(GL_TEXTURE_2D, bindTex);
glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT32F, width, height, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_INT,
nullptr);
}
}
}
};
class GLTextureCubeR : public GraphicsDataNode<ITextureCubeR> {
friend class GLDataFactory;
friend struct GLCommandQueue;
struct GLCommandQueue* m_q;
GLuint m_texs[2] = {};
GLuint m_fbos[6] = {};
std::array<GLuint, 2> m_texs{};
std::array<GLuint, 6> m_fbos{};
size_t m_width = 0;
size_t m_mipCount = 0;
GLenum m_colorFormat;
@ -623,8 +642,8 @@ class GLTextureCubeR : public GraphicsDataNode<ITextureCubeR> {
public:
~GLTextureCubeR() override {
glDeleteTextures(2, m_texs);
glDeleteFramebuffers(6, m_fbos);
glDeleteTextures(GLsizei(m_texs.size()), m_texs.data());
glDeleteFramebuffers(GLsizei(m_fbos.size()), m_fbos.data());
}
void setClampMode(TextureClampMode mode) override {}
@ -639,27 +658,29 @@ public:
glBindTexture(GL_TEXTURE_CUBE_MAP, m_texs[0]);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAX_LEVEL, m_mipCount - 1);
for (int f = 0; f < 6; ++f) {
for (size_t f = 0; f < m_fbos.size(); ++f) {
size_t tmpWidth = m_width;
for (size_t m = 0; m < m_mipCount; ++m) {
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + f, m, m_colorFormat, tmpWidth, tmpWidth,
glTexImage2D(GLenum(GL_TEXTURE_CUBE_MAP_POSITIVE_X + f), m, m_colorFormat, tmpWidth, tmpWidth,
0, GL_RGBA, compType, nullptr);
tmpWidth >>= 1;
}
}
glBindTexture(GL_TEXTURE_CUBE_MAP, m_texs[1]);
for (int f = 0; f < 6; ++f)
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + f, 0, GL_DEPTH_COMPONENT32F, m_width, m_width, 0, GL_DEPTH_COMPONENT,
GL_UNSIGNED_INT, nullptr);
for (size_t f = 0; f < m_fbos.size(); ++f) {
glTexImage2D(GLenum(GL_TEXTURE_CUBE_MAP_POSITIVE_X + f), 0, GL_DEPTH_COMPONENT32F, m_width, m_width, 0,
GL_DEPTH_COMPONENT, GL_UNSIGNED_INT, nullptr);
}
}
void resize(size_t width, size_t mips) {
m_width = width;
m_mipCount = mips;
_allocateTextures();
for (int f = 0; f < 6; ++f) {
glBindFramebuffer(GL_FRAMEBUFFER, m_fbos[f]);
for (const GLuint fbo : m_fbos) {
glBindFramebuffer(GL_FRAMEBUFFER, fbo);
glDepthMask(GL_TRUE);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
}
@ -684,17 +705,24 @@ ObjToken<ITextureSA> GLDataFactory::Context::newStaticArrayTexture(size_t width,
new GLTextureSA(m_data, width, height, layers, mips, fmt, clampMode, factory.m_glCtx->m_anisotropy, data, sz)};
}
static const GLenum PRIMITIVE_TABLE[] = {GL_TRIANGLES, GL_TRIANGLE_STRIP, GL_PATCHES};
constexpr std::array<GLenum, 3> PRIMITIVE_TABLE{
GL_TRIANGLES,
GL_TRIANGLE_STRIP,
GL_PATCHES,
};
static const GLenum BLEND_FACTOR_TABLE[] = {GL_ZERO, GL_ONE,
constexpr std::array<GLenum, 12> BLEND_FACTOR_TABLE{
GL_ZERO, GL_ONE,
GL_SRC_COLOR, GL_ONE_MINUS_SRC_COLOR,
GL_DST_COLOR, GL_ONE_MINUS_DST_COLOR,
GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA,
GL_DST_ALPHA, GL_ONE_MINUS_DST_ALPHA,
GL_SRC1_COLOR, GL_ONE_MINUS_SRC1_COLOR};
GL_SRC1_COLOR, GL_ONE_MINUS_SRC1_COLOR,
};
static const GLenum SHADER_STAGE_TABLE[] = {
0, GL_VERTEX_SHADER, GL_FRAGMENT_SHADER, GL_GEOMETRY_SHADER, GL_TESS_CONTROL_SHADER, GL_TESS_EVALUATION_SHADER};
constexpr std::array<GLenum, 6> SHADER_STAGE_TABLE{
0, GL_VERTEX_SHADER, GL_FRAGMENT_SHADER, GL_GEOMETRY_SHADER, GL_TESS_CONTROL_SHADER, GL_TESS_EVALUATION_SHADER,
};
class GLShaderStage : public GraphicsDataNode<IShaderStage> {
friend class GLDataFactory;
@ -702,8 +730,9 @@ class GLShaderStage : public GraphicsDataNode<IShaderStage> {
std::vector<std::pair<std::string, int>> m_texNames;
std::vector<std::pair<std::string, int>> m_blockNames;
static constexpr EShLanguage ShaderTypes[] = {EShLangVertex, EShLangVertex, EShLangFragment,
EShLangGeometry, EShLangTessControl, EShLangTessEvaluation};
static constexpr std::array<EShLanguage, 6> ShaderTypes{
EShLangVertex, EShLangVertex, EShLangFragment, EShLangGeometry, EShLangTessControl, EShLangTessEvaluation,
};
/* Use glslang's reflection API to pull out uniform indices from Vulkan
* version of shader. Aids in glGetUniformBlockIndex and glGetUniformLocation calls */
@ -803,15 +832,15 @@ protected:
bool m_alphaWrite = true;
bool m_subtractBlend = false;
bool m_overwriteAlpha = false;
CullMode m_culling;
CullMode m_culling{};
uint32_t m_patchSize = 0;
mutable GLint m_uniLocs[BOO_GLSL_MAX_UNIFORM_COUNT];
mutable std::array<GLint, BOO_GLSL_MAX_UNIFORM_COUNT> m_uniLocs{};
GLShaderPipeline(const ObjToken<BaseGraphicsData>& parent, ObjToken<IShaderStage> vertex,
ObjToken<IShaderStage> fragment, ObjToken<IShaderStage> geometry, ObjToken<IShaderStage> control,
ObjToken<IShaderStage> evaluation, const VertexFormatInfo& vtxFmt,
const AdditionalPipelineInfo& info)
: GraphicsDataNode<IShaderPipeline>(parent) {
std::fill(std::begin(m_uniLocs), std::end(m_uniLocs), -1);
m_uniLocs.fill(-1);
if (info.srcFac == BlendFactor::Subtract || info.dstFac == BlendFactor::Subtract) {
m_sfactor = GL_SRC_ALPHA;
@ -1112,12 +1141,18 @@ ObjToken<IGraphicsBufferD> GLDataFactoryImpl::newPoolBuffer(BufferUse use, size_
return {new GLGraphicsBufferD<BaseGraphicsPool>(pool, use, stride * count)};
}
static const GLint SEMANTIC_COUNT_TABLE[] = {0, 3, 4, 3, 4, 4, 4, 2, 4, 4, 4};
constexpr std::array<GLint, 11> SEMANTIC_COUNT_TABLE{
0, 3, 4, 3, 4, 4, 4, 2, 4, 4, 4,
};
static const size_t SEMANTIC_SIZE_TABLE[] = {0, 12, 16, 12, 16, 16, 4, 8, 16, 16, 16};
constexpr std::array<size_t, 11> SEMANTIC_SIZE_TABLE{
0, 12, 16, 12, 16, 16, 4, 8, 16, 16, 16,
};
static const GLenum SEMANTIC_TYPE_TABLE[] = {GL_INVALID_ENUM, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT,
GL_UNSIGNED_BYTE, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT};
constexpr std::array<GLenum, 11> SEMANTIC_TYPE_TABLE{
GL_INVALID_ENUM, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT,
GL_UNSIGNED_BYTE, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT,
};
struct GLCommandQueue final : IGraphicsCommandQueue {
Platform platform() const override { return IGraphicsDataFactory::Platform::OpenGL; }
@ -1158,7 +1193,7 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
SWindowRect rect;
float znear, zfar;
} viewport;
float rgba[4];
std::array<float, 4> rgba;
GLbitfield flags;
struct {
size_t start;
@ -1184,7 +1219,7 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
Command(Command&&) = default;
Command& operator=(Command&&) = default;
};
std::vector<Command> m_cmdBufs[3];
std::array<std::vector<Command>, 3> m_cmdBufs;
int m_fillBuf = 0;
int m_completeBuf = 0;
int m_drawBuf = 0;
@ -1212,20 +1247,22 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
std::vector<ObjToken<ITextureCubeR>> m_pendingCubeFboAdds;
static void ConfigureVertexFormat(GLShaderDataBinding* fmt) {
glGenVertexArrays(3, fmt->m_vao.data());
glGenVertexArrays(GLsizei(fmt->m_vao.size()), fmt->m_vao.data());
size_t stride = 0;
size_t instStride = 0;
auto pipeline = fmt->m_pipeline.cast<GLShaderPipeline>();
for (size_t i = 0; i < pipeline->m_elements.size(); ++i) {
const VertexElementDescriptor& desc = pipeline->m_elements[i];
if (True(desc.semantic & VertexSemantic::Instanced))
instStride += SEMANTIC_SIZE_TABLE[int(desc.semantic & VertexSemantic::SemanticMask)];
else
stride += SEMANTIC_SIZE_TABLE[int(desc.semantic & VertexSemantic::SemanticMask)];
const auto* const pipeline = fmt->m_pipeline.cast<GLShaderPipeline>();
for (const auto desc : pipeline->m_elements) {
const size_t size = SEMANTIC_SIZE_TABLE[int(desc.semantic & VertexSemantic::SemanticMask)];
if (True(desc.semantic & VertexSemantic::Instanced)) {
instStride += size;
} else {
stride += size;
}
}
for (int b = 0; b < 3; ++b) {
for (size_t b = 0; b < fmt->m_vao.size(); ++b) {
size_t offset = fmt->m_baseVert * stride;
size_t instOffset = fmt->m_baseInst * instStride;
glBindVertexArray(fmt->m_vao[b]);
@ -1240,28 +1277,31 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
if (vbo != lastVBO) {
lastVBO = vbo;
if (lastVBO->dynamic())
static_cast<GLGraphicsBufferD<BaseGraphicsData>*>(lastVBO)->bindVertex(b);
static_cast<GLGraphicsBufferD<BaseGraphicsData>*>(lastVBO)->bindVertex(int(b));
else
static_cast<GLGraphicsBufferS*>(lastVBO)->bindVertex();
}
if (ebo != lastEBO) {
lastEBO = ebo;
if (lastEBO->dynamic())
static_cast<GLGraphicsBufferD<BaseGraphicsData>*>(lastEBO)->bindIndex(b);
static_cast<GLGraphicsBufferD<BaseGraphicsData>*>(lastEBO)->bindIndex(int(b));
else
static_cast<GLGraphicsBufferS*>(lastEBO)->bindIndex();
}
glEnableVertexAttribArray(i);
int maskedSem = int(desc.semantic & VertexSemantic::SemanticMask);
const int maskedSem = int(desc.semantic & VertexSemantic::SemanticMask);
const auto semanticCount = SEMANTIC_COUNT_TABLE[maskedSem];
const auto semanticType = SEMANTIC_TYPE_TABLE[maskedSem];
const auto semanticSize = SEMANTIC_SIZE_TABLE[maskedSem];
if (True(desc.semantic & VertexSemantic::Instanced)) {
glVertexAttribPointer(i, SEMANTIC_COUNT_TABLE[maskedSem], SEMANTIC_TYPE_TABLE[maskedSem], GL_TRUE, instStride,
(void*)instOffset);
glVertexAttribPointer(i, semanticCount, semanticType, GL_TRUE, instStride, (void*)instOffset);
glVertexAttribDivisor(i, 1);
instOffset += SEMANTIC_SIZE_TABLE[maskedSem];
instOffset += semanticSize;
} else {
glVertexAttribPointer(i, SEMANTIC_COUNT_TABLE[maskedSem], SEMANTIC_TYPE_TABLE[maskedSem], GL_TRUE, stride,
(void*)offset);
offset += SEMANTIC_SIZE_TABLE[maskedSem];
glVertexAttribPointer(i, semanticCount, semanticType, GL_TRUE, stride, (void*)offset);
offset += semanticSize;
}
}
}
@ -1276,14 +1316,14 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
if (tex->m_samples > 1) {
if (tex->m_colorBindCount) {
glGenFramebuffers(tex->m_colorBindCount, tex->m_bindFBOs[0]);
glGenFramebuffers(tex->m_colorBindCount, tex->m_bindFBOs[0].data());
for (size_t i = 0; i < tex->m_colorBindCount; ++i) {
glBindFramebuffer(GL_FRAMEBUFFER, tex->m_bindFBOs[0][i]);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex->m_bindTexs[0][i], 0);
}
}
if (tex->m_depthBindCount) {
glGenFramebuffers(tex->m_depthBindCount, tex->m_bindFBOs[1]);
glGenFramebuffers(tex->m_depthBindCount, tex->m_bindFBOs[1].data());
for (size_t i = 0; i < tex->m_depthBindCount; ++i) {
glBindFramebuffer(GL_FRAMEBUFFER, tex->m_bindFBOs[1][i]);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, tex->m_bindTexs[1][i], 0);
@ -1293,11 +1333,14 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
}
static void ConfigureFBO(GLTextureCubeR* tex) {
glGenFramebuffers(6, tex->m_fbos);
for (int i = 0; i < 6; ++i) {
glGenFramebuffers(GLsizei(tex->m_fbos.size()), tex->m_fbos.data());
for (size_t i = 0; i < tex->m_fbos.size(); ++i) {
glBindFramebuffer(GL_FRAMEBUFFER, tex->m_fbos[i]);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, tex->m_texs[0], 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, tex->m_texs[1], 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GLenum(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i),
tex->m_texs[0], 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GLenum(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i),
tex->m_texs[1], 0);
}
}
@ -1536,7 +1579,7 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
int voffset = 0;
for (BaseGraphicsData& data : *dataFactory->m_dataHead) {
if (GLTextureCubeR* cube = static_cast<GLTextureCubeR*>(data.getHead<ITextureCubeR>())) {
for (int i = 0; i < 6; ++i) {
for (size_t i = 0; i < cube->m_fbos.size(); ++i) {
glBindFramebuffer(GL_READ_FRAMEBUFFER, cube->m_fbos[i]);
glBlitFramebuffer(0, 0, cube->m_width, cube->m_width, offset, voffset,
cube->m_width + offset, cube->m_width + voffset,
@ -1577,8 +1620,9 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
dataFactory->DestroyGammaResources();
std::lock_guard<std::recursive_mutex> fmtLk(self->m_fmtMt);
if (self->m_pendingFmtDels.size()) {
for (const auto& v : self->m_pendingFmtDels)
glDeleteVertexArrays(3, v.data());
for (const auto& v : self->m_pendingFmtDels) {
glDeleteVertexArrays(GLsizei(v.size()), v.data());
}
self->m_pendingFmtDels.clear();
}
}
@ -1595,10 +1639,12 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
if (m_running) {
m_running = false;
m_cv.notify_one();
if (m_thr.joinable())
if (m_thr.joinable()) {
m_thr.join();
for (int i = 0; i < 3; ++i)
m_cmdBufs[i].clear();
}
for (auto& cmdBuf : m_cmdBufs) {
cmdBuf.clear();
}
}
}
@ -1760,10 +1806,10 @@ struct GLCommandQueue final : IGraphicsCommandQueue {
SCOPED_GRAPHICS_DEBUG_GROUP(this, "GLCommandQueue::execute", {1.f, 0.f, 0.f, 1.f});
std::unique_lock<std::mutex> lk(m_mt);
m_completeBuf = m_fillBuf;
for (int i = 0; i < 3; ++i) {
if (i == m_completeBuf || i == m_drawBuf)
for (size_t i = 0; i < m_cmdBufs.size(); ++i) {
if (int(i) == m_completeBuf || int(i) == m_drawBuf)
continue;
m_fillBuf = i;
m_fillBuf = int(i);
break;
}
@ -1839,16 +1885,18 @@ GLTextureR::GLTextureR(const ObjToken<BaseGraphicsData>& parent, GLCommandQueue*
, m_colorFormat(colorFormat)
, m_colorBindCount(colorBindingCount)
, m_depthBindCount(depthBindingCount) {
glGenTextures(2, m_texs);
glGenTextures(GLsizei(m_texs.size()), m_texs.data());
if (colorBindingCount) {
if (colorBindingCount > MAX_BIND_TEXS)
if (colorBindingCount > MAX_BIND_TEXS) {
Log.report(logvisor::Fatal, fmt("too many color bindings for render texture"));
glGenTextures(colorBindingCount, m_bindTexs[0]);
}
glGenTextures(colorBindingCount, m_bindTexs[0].data());
}
if (depthBindingCount) {
if (depthBindingCount > MAX_BIND_TEXS)
if (depthBindingCount > MAX_BIND_TEXS) {
Log.report(logvisor::Fatal, fmt("too many depth bindings for render texture"));
glGenTextures(depthBindingCount, m_bindTexs[1]);
}
glGenTextures(depthBindingCount, m_bindTexs[1].data());
}
GLenum compType = colorFormat == GL_RGBA16 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_BYTE;
@ -1906,7 +1954,7 @@ GLTextureCubeR::GLTextureCubeR(const ObjToken<BaseGraphicsData>& parent, GLComma
, m_width(width)
, m_mipCount(mips)
, m_colorFormat(colorFormat) {
glGenTextures(2, m_texs);
glGenTextures(GLsizei(m_texs.size()), m_texs.data());
_allocateTextures();