mirror of
https://github.com/MobileGL-Dev/MobileGL
synced 2026-09-12 22:28:32 +09:00
[Feat]: implement glBindVertexAttribLocation in DirectGLES backend (fixing OptiFine?)
This commit is contained in:
@@ -501,6 +501,9 @@ namespace MobileGL::MG_Backend::DirectGLES {
|
|||||||
auto& spirvCode = shaderSpirvs[index];
|
auto& spirvCode = shaderSpirvs[index];
|
||||||
|
|
||||||
MG_Util::ShaderTranspiler::SpvcSession spvcSession(spirvCode);
|
MG_Util::ShaderTranspiler::SpvcSession spvcSession(spirvCode);
|
||||||
|
if (glShaderType == GL_VERTEX_SHADER) {
|
||||||
|
spvcSession.SetVertexAttribLocation(stateProgramObject->GetAttribLocationMap());
|
||||||
|
}
|
||||||
|
|
||||||
spvc_compiler_options options;
|
spvc_compiler_options options;
|
||||||
spvcSession.CreateOptions(&options);
|
spvcSession.CreateOptions(&options);
|
||||||
|
|||||||
@@ -195,6 +195,10 @@ namespace MobileGL {
|
|||||||
std::swap(m_attribs[location], m_attribs[idx]);
|
std::swap(m_attribs[location], m_attribs[idx]);
|
||||||
std::swap(m_attribTypes[location], m_attribTypes[idx]);
|
std::swap(m_attribTypes[location], m_attribTypes[idx]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (SizeT idx = 0; idx < m_attribs.size(); ++idx) {
|
||||||
|
m_attribLocation[m_attribs[idx]] = idx;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// ---------- UBO ----------
|
// ---------- UBO ----------
|
||||||
@@ -207,7 +211,6 @@ namespace MobileGL {
|
|||||||
m_uniformBlockIndex[ubo.name] = ubo.getBinding();
|
m_uniformBlockIndex[ubo.name] = ubo.getBinding();
|
||||||
m_uniformBlockIndexInTProgram[ubo.getBinding()] = i;
|
m_uniformBlockIndexInTProgram[ubo.getBinding()] = i;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ProgramObject::GenerateBinary() {
|
void ProgramObject::GenerateBinary() {
|
||||||
@@ -244,7 +247,9 @@ namespace MobileGL {
|
|||||||
assert(binaryResult);
|
assert(binaryResult);
|
||||||
m_generatedSpirv = Move(binaryResult.value());
|
m_generatedSpirv = Move(binaryResult.value());
|
||||||
|
|
||||||
for (auto spv : m_generatedSpirv) {
|
for (SizeT i = 0; i < m_generatedSpirv.size(); i++) {
|
||||||
|
auto& spv = m_generatedSpirv[i];
|
||||||
|
auto shaderType = shaderTypes[i];
|
||||||
SpvcSession session(spv);
|
SpvcSession session(spv);
|
||||||
auto result = session.ParseMetaData();
|
auto result = session.ParseMetaData();
|
||||||
if (result < 0) {
|
if (result < 0) {
|
||||||
|
|||||||
@@ -108,6 +108,8 @@ namespace MobileGL {
|
|||||||
|
|
||||||
Uint GetExternalIndex() const { return m_externalIndex; }
|
Uint GetExternalIndex() const { return m_externalIndex; }
|
||||||
|
|
||||||
|
const UnorderedMap<String, Uint>& GetAttribLocationMap() const { return m_attribLocation; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void DoReflection();
|
void DoReflection();
|
||||||
void GenerateBinary();
|
void GenerateBinary();
|
||||||
@@ -124,6 +126,8 @@ namespace MobileGL {
|
|||||||
UnorderedMap<String, Uint> m_explicitAttribLocations;
|
UnorderedMap<String, Uint> m_explicitAttribLocations;
|
||||||
Vector<String> m_attribs;
|
Vector<String> m_attribs;
|
||||||
Vector<GLenum> m_attribTypes;
|
Vector<GLenum> m_attribTypes;
|
||||||
|
// For SpvcSession::SetVertexAttribLocation()
|
||||||
|
UnorderedMap<String, Uint> m_attribLocation;
|
||||||
|
|
||||||
// Uniforms
|
// Uniforms
|
||||||
UnorderedMap<String, Uint> m_uniformLocations;
|
UnorderedMap<String, Uint> m_uniformLocations;
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ TEST_F(ProgramTest, Sanity) {
|
|||||||
|
|
||||||
const char* vsSrc = R"(#version 460
|
const char* vsSrc = R"(#version 460
|
||||||
|
|
||||||
layout (location = 0) in vec4 Position;
|
layout (location = 2) in vec4 Position;
|
||||||
in float fIn4;
|
in float fIn4;
|
||||||
in float fIn2;
|
in float fIn2;
|
||||||
in float fIn5;
|
in float fIn5;
|
||||||
@@ -146,7 +146,7 @@ TEST_F(ProgramTest, CompileAndLink) {
|
|||||||
GetProgramiv(program, GL_ACTIVE_UNIFORM_MAX_LENGTH, &uniformNameMaxLength);
|
GetProgramiv(program, GL_ACTIVE_UNIFORM_MAX_LENGTH, &uniformNameMaxLength);
|
||||||
ASSERT_EQ(uniformNameMaxLength, 12);
|
ASSERT_EQ(uniformNameMaxLength, 12);
|
||||||
|
|
||||||
ASSERT_EQ(GetAttribLocation(program, "Position"), 0);
|
ASSERT_EQ(GetAttribLocation(program, "Position"), 2);
|
||||||
ASSERT_EQ(GetAttribLocation(program, "fIn1"), 1);
|
ASSERT_EQ(GetAttribLocation(program, "fIn1"), 1);
|
||||||
ASSERT_EQ(GetAttribLocation(program, "fIn3"), 3);
|
ASSERT_EQ(GetAttribLocation(program, "fIn3"), 3);
|
||||||
ASSERT_EQ(GetAttribLocation(program, "fIn5"), 5);
|
ASSERT_EQ(GetAttribLocation(program, "fIn5"), 5);
|
||||||
@@ -169,6 +169,36 @@ TEST_F(ProgramTest, CompileAndLink) {
|
|||||||
int intVal;
|
int intVal;
|
||||||
GetUniformiv(program, locInt, &intVal);
|
GetUniformiv(program, locInt, &intVal);
|
||||||
EXPECT_EQ(intVal, 114514);
|
EXPECT_EQ(intVal, 114514);
|
||||||
|
|
||||||
|
auto programObj = MG_State::pGLContext->GetProgramObject(program);
|
||||||
|
auto& shaderSpirvs = programObj->GetGeneratedSpirv();
|
||||||
|
for (int index = 0; index < shaderSpirvs.size(); ++index) {
|
||||||
|
String source;
|
||||||
|
auto& spirvCode = shaderSpirvs[index];
|
||||||
|
|
||||||
|
MG_Util::ShaderTranspiler::SpvcSession spvcSession(spirvCode);
|
||||||
|
|
||||||
|
spvc_compiler_options options;
|
||||||
|
spvcSession.CreateOptions(&options);
|
||||||
|
|
||||||
|
spvc_compiler_options_set_uint(options, SPVC_COMPILER_OPTION_GLSL_VERSION, 320);
|
||||||
|
spvc_compiler_options_set_bool(options, SPVC_COMPILER_OPTION_GLSL_ES, SPVC_TRUE);
|
||||||
|
spvc_compiler_options_set_bool(options, SPVC_COMPILER_OPTION_GLSL_VULKAN_SEMANTICS, SPVC_FALSE);
|
||||||
|
|
||||||
|
spvcSession.SetOptions(options);
|
||||||
|
|
||||||
|
const char* result = nullptr;
|
||||||
|
spvcSession.Compile(&result);
|
||||||
|
|
||||||
|
if (!result) {
|
||||||
|
MG_Util::ShaderTranspiler::ResultInfo r;
|
||||||
|
r.log += "Failed to compile the shader to GLSL: \n";
|
||||||
|
r.log += spvcSession.GetLastErrorString();
|
||||||
|
r.errc = -5;
|
||||||
|
FAIL() << r.log;
|
||||||
|
}
|
||||||
|
printf("shader dump: \n%s\n", result);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_F(ProgramTest, UniformMatrixFunctions) {
|
TEST_F(ProgramTest, UniformMatrixFunctions) {
|
||||||
|
|||||||
@@ -60,6 +60,25 @@ namespace MobileGL {
|
|||||||
return variables;
|
return variables;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
spvc_result SpvcSession::SetVertexAttribLocation(const UnorderedMap<String, Uint>& location) {
|
||||||
|
// TODO: We should assert we're really dealing with vertex shader here
|
||||||
|
|
||||||
|
SPVC_CHK_INIT
|
||||||
|
const spvc_reflected_resource *list = nullptr;
|
||||||
|
size_t count = 0;
|
||||||
|
SPVC_CHK_RESULT(spvc_resources_get_resource_list_for_type(resources, SPVC_RESOURCE_TYPE_STAGE_INPUT, &list, &count));
|
||||||
|
for (size_t i = 0; i < count; ++i) {
|
||||||
|
auto& resource = list[i];
|
||||||
|
auto it = location.find(resource.name);
|
||||||
|
if (it != location.end()) {
|
||||||
|
// realize glBindVertexAttribLocation here
|
||||||
|
// it->second should be the location explicitly requested
|
||||||
|
spvc_compiler_set_decoration(compiler, resource.id, SpvDecorationLocation, it->second);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
SPVC_CHK_RETURN
|
||||||
|
}
|
||||||
|
|
||||||
spvc_result SpvcSession::Compile(const char** result) {
|
spvc_result SpvcSession::Compile(const char** result) {
|
||||||
SPVC_CHK_INIT
|
SPVC_CHK_INIT
|
||||||
SPVC_CHK_RESULT(spvc_compiler_compile(compiler, result));
|
SPVC_CHK_RESULT(spvc_compiler_compile(compiler, result));
|
||||||
|
|||||||
@@ -73,6 +73,7 @@ namespace MobileGL {
|
|||||||
spvc_result CreateOptions(spvc_compiler_options* options);
|
spvc_result CreateOptions(spvc_compiler_options* options);
|
||||||
spvc_result SetOptions(spvc_compiler_options options);
|
spvc_result SetOptions(spvc_compiler_options options);
|
||||||
Vector<InterfaceVariable> GetShaderInterface(spvc_resource_type resource_type) const;
|
Vector<InterfaceVariable> GetShaderInterface(spvc_resource_type resource_type) const;
|
||||||
|
spvc_result SetVertexAttribLocation(const UnorderedMap<String, Uint>& location);
|
||||||
spvc_result Compile(const char** result);
|
spvc_result Compile(const char** result);
|
||||||
const SpvcMetadata& GetMetadata() const;
|
const SpvcMetadata& GetMetadata() const;
|
||||||
const char* GetLastErrorString() const;
|
const char* GetLastErrorString() const;
|
||||||
|
|||||||
Reference in New Issue
Block a user