Vertex color and custom vertex format


#1

I’m trying to create a quad by code with position and color per vertex.

HMesh getMesh()
{
	SPtr<VertexDataDesc> vertexDesc = bs_shared_ptr_new<VertexDataDesc>();
	vertexDesc->addVertElem(VET_FLOAT3, VES_POSITION);
	vertexDesc->addVertElem(VET_FLOAT4, VES_COLOR);

	UINT32 numVertices = 4;
	UINT32 numIndices = 6;

	SPtr<MeshData> meshData = MeshData::create(numVertices, numIndices, vertexDesc);

	Vector3 topLeft = Vector3(-1, 1, 0);
	Vector3 topRight = Vector3(1, 1, 0);
	Vector3 bottomLeft = Vector3(-1, -1, 0);
	Vector3 bottomRight = Vector3(1, -1, 0);

	Vector3 positions[4];
	positions[0] = topLeft;
	positions[1] = topRight;
	positions[2] = bottomLeft;
	positions[3] = bottomRight;

	Color colors[4];
	colors[0] = Color::Red;
	colors[1] = Color::Blue;
	colors[2] = Color::White;
	colors[3] = Color::Green;

	UINT32* indices = meshData->getIndices32();
	indices[0] = 0;
	indices[1] = 1;
	indices[2] = 2;

	indices[3] = 1;
	indices[4] = 3;
	indices[5] = 2;

	meshData->setVertexData(VES_POSITION, (UINT8*)positions, sizeof(positions));
	meshData->setVertexData(VES_COLOR, (UINT8*)colors, sizeof(colors));

	return Mesh::create((meshData));
}

void setup()
{
	HSceneObject cameraSO = SceneObject::create("SceneCamera");
	HCamera sceneCamera = cameraSO->addComponent<CCamera>();
	sceneCamera->setMain(true);
	cameraSO->setPosition(Vector3(1, 1.5f, 2.5f));
	cameraSO->lookAt(Vector3(0, 0, 0));

	HMesh mesh = getMesh();

	HSceneObject object = SceneObject::create("Object");
	object->setPosition(Vector3(0, 0, 0));
	HRenderable renderable = object->addComponent<CRenderable>();

	//HShader shader = gBuiltinResources().getBuiltinShader(BuiltinShader::Standard);
	HShader shader = gImporter().import<Shader>(CI_DATA_PATH + "Shaders/SolidColor.bsl");
	HMaterial material = Material::create(shader);

	renderable->setMesh(mesh);
	renderable->setMaterial(material);
}

And a simple shader that uses only that position and color vertex data.

shader SolidColor
{
	code
	{
		struct VStoFS
		{
			float4 position : SV_Position;
			float4 color : COLOR;
		};
		
		cbuffer PerObject
		{
			float4x4 gMatWorldViewProj;
		}
		
		struct VertexInput
		{
			float3 position : POSITION;
			float4 color : COLOR;
		};
		
		VStoFS vsmain(VertexInput input)
		{
			VStoFS output;
		
			output.position = mul(gMatWorldViewProj, input.position);		
			output.color = input.color;

			return output;
		}

		float4 fsmain(in VStoFS input) : SV_Target0
		{
			return input.color;
		}	
	};
};

But nothing appers on screen. How do I code a simple shader to use only vertex position and color?


#2

I think I had a similar issue. The core of the issue was that to use a material on a CRenderable, it needs to import the common shader parts:

#include "$ENGINE$/BasePass.bslinc"
#include "$ENGINE$/GBufferOutput.bslinc"
#include "$ENGINE$/PerCameraData.bslinc"

And not define the things itself. Then the customised vsmain and fsmain can be defined to ignore things.
Here’s one of my custom shaders: https://github.com/Revolutionary-Games/Thrive/blob/c6348ebeda8cd43f04c29b398b3e81ed7e285f09/shaders/background.bsl
(It doesn’t override the vertex shader main).
Here’s a transparent custom material that implements both a custom vsmain and fsmain: https://github.com/Revolutionary-Games/Thrive/blob/c6348ebeda8cd43f04c29b398b3e81ed7e285f09/shaders/membrane.bsl