瀏覽代碼

metal: fix incorrect default values for missing int and color vertex attributes.

Fixes #2169.
Sasha Szpakowski 4 月之前
父節點
當前提交
58a42e2c35
共有 3 個文件被更改,包括 48 次插入6 次删除
  1. 3 0
      src/modules/graphics/metal/Graphics.mm
  2. 7 1
      src/modules/graphics/metal/Shader.h
  3. 38 5
      src/modules/graphics/metal/Shader.mm

+ 3 - 0
src/modules/graphics/metal/Graphics.mm

@@ -259,6 +259,7 @@ struct DefaultVertexAttributes
 {
 	float floats[4];
 	int ints[4];
+	float color[4];
 };
 
 Graphics *Graphics::graphicsInstance = nullptr;
@@ -352,11 +353,13 @@ Graphics::Graphics()
 		std::vector<Buffer::DataDeclaration> dataformat = {
 			{"floats", DATAFORMAT_FLOAT_VEC4, 0},
 			{"ints", DATAFORMAT_INT32_VEC4, 0},
+			{"color", DATAFORMAT_FLOAT_VEC4, 0}
 		};
 
 		DefaultVertexAttributes defaults = {
 			{0.0f, 0.0f, 0.0f, 1.0f},
 			{0, 0, 0, 1},
+			{1.0f, 1.0f, 1.0f, 1.0f}
 		};
 
 		Buffer::Settings attribsettings(BUFFERUSAGEFLAG_VERTEX, BUFFERDATAUSAGE_STATIC);

+ 7 - 1
src/modules/graphics/metal/Shader.h

@@ -126,6 +126,12 @@ public:
 
 private:
 
+	struct AttributeInfo
+	{
+		int index;
+		DataBaseType baseType;
+	};
+
 	struct RenderPipelineHasher
 	{
 		size_t operator() (const RenderPipelineKey &key) const
@@ -151,7 +157,7 @@ private:
 
 	int firstVertexBufferBinding;
 
-	std::map<std::string, int> attributes;
+	std::map<std::string, AttributeInfo> attributes;
 
 	std::vector<TextureBinding> textureBindings;
 	std::vector<BufferBinding> bufferBindings;

+ 38 - 5
src/modules/graphics/metal/Shader.mm

@@ -491,7 +491,22 @@ void Shader::compileFromGLSLang(id<MTLDevice> device, const glslang::TProgram &p
 						}
 					}
 
-					attributes[name] = msl.get_decoration(var, spv::DecorationLocation);
+					int location = (int)msl.get_decoration(var, spv::DecorationLocation);
+					DataBaseType basetype = DATA_BASETYPE_FLOAT;
+
+					switch (msl.get_type_from_variable(var).basetype)
+					{
+					case spirv_cross::SPIRType::Int:
+						basetype = DATA_BASETYPE_INT;
+						break;
+					case spirv_cross::SPIRType::UInt:
+						basetype = DATA_BASETYPE_UINT;
+						break;
+					default:
+						break;
+					}
+
+					attributes[name] = { location, basetype };
 				}
 			}
 
@@ -717,7 +732,7 @@ void Shader::attach()
 int Shader::getVertexAttributeIndex(const std::string &name)
 {
 	const auto it = attributes.find(name);
-	return it != attributes.end() ? it->second : -1;
+	return it != attributes.end() ? it->second.index : -1;
 }
 
 const Shader::UniformInfo *Shader::getUniformInfo(BuiltinUniform builtin) const
@@ -860,7 +875,7 @@ id<MTLRenderPipelineState> Shader::getCachedRenderPipeline(graphics::Graphics *g
 
 	for (const auto &pair : this->attributes)
 	{
-		int i = pair.second;
+		int i = pair.second.index;
 		uint32 bit = 1u << i;
 
 		if (attributes.enableBits & bit)
@@ -882,8 +897,26 @@ id<MTLRenderPipelineState> Shader::getCachedRenderPipeline(graphics::Graphics *g
 		}
 		else
 		{
-			vertdesc.attributes[i].format = MTLVertexFormatFloat4;
-			vertdesc.attributes[i].offset = 0;
+			switch (pair.second.baseType)
+			{
+			case DATA_BASETYPE_INT:
+				vertdesc.attributes[i].format = MTLVertexFormatInt4;
+				vertdesc.attributes[i].offset = sizeof(float) * 4;
+				break;
+			case DATA_BASETYPE_UINT:
+				vertdesc.attributes[i].format = MTLVertexFormatUInt4;
+				vertdesc.attributes[i].offset = sizeof(float) * 4;
+				break;
+			case DATA_BASETYPE_FLOAT:
+				vertdesc.attributes[i].format = MTLVertexFormatFloat4;
+				if (i == ATTRIB_COLOR)
+					vertdesc.attributes[i].offset = sizeof(float) * 4 * 2;
+				else
+					vertdesc.attributes[i].offset = 0;
+			default:
+				break;
+			}
+
 			vertdesc.attributes[i].bufferIndex = DEFAULT_VERTEX_BUFFER_BINDING;
 
 			vertdesc.layouts[DEFAULT_VERTEX_BUFFER_BINDING].stride = sizeof(float) * 4;