getting world position in vertex shader - another bug with shaders?

For a simple lighting shader I have the following input and output structs:

// vertex shader input
struct VertexShaderInput
{
	float4 Position : POSITION0;
	float4 Normal : NORMAL0;
	float2 TextureCoordinate : TEXCOORD0;
};

// vertex shader output
struct VertexShaderOutput
{
	float4 Position : SV_POSITION;
	float3 Normal : TEXCOORD0;
	float2 TextureCoordinate : TEXCOORD1;
	float3 WorldPos : TEXCOORD2;
};

If I do the following in my vertex shader:

// main vertex shader for flat lighting
VertexShaderOutput FlatLightingMainVS(in VertexShaderInput input)
{
	VertexShaderOutput output;
	output.Position = mul(input.Position, WorldViewProjection);
	output.WorldPos = mul(input.Position, World);
	output.Normal = input.Normal;
	output.TextureCoordinate = input.TextureCoordinate;
	return output;
}

I get the following error while calling Draw():

An unhandled exception of type 'System.ArgumentException' occurred in MonoGame.Framework.dll

Additional information: Offset and length were out of bounds for the array or count is greater than the number of elements from index to the end of the source collection.

The problem seems to be from output.WorldPos = mul(input.Position, World);, and if I do the following instead:

// main vertex shader for flat lighting
VertexShaderOutput FlatLightingMainVS(in VertexShaderInput input)
{
	VertexShaderOutput output;
	output.Position = mul(input.Position, WorldViewProjection);
	output.WorldPos = input.Position; // <-- DIFF HERE
	output.Normal = input.Normal;
	output.TextureCoordinate = input.TextureCoordinate;
	return output;
}

and then in pixel shader multiply with world matrix:

float3 position = mul(input.WorldPos, World);

There is no error (although position seems to be wrong, but I will handle it later).

Can anyone explain the error in the first way please, eg calculating in vertex shader? Is this a bug with MonoGame?

Thanks,

Changing WorldPos and Normal to float4 solves it, for some reason :confused:

If you only use a float3 from the matrix optimization, the part of the matrix that’s used to calculate the fourth value is optimized out. There is an open issue for this: https://github.com/MonoGame/MonoGame/issues/911
Using float4’s is a good workaround.

MG should check if the size matches and if not only send the necessary part of the matrix to the GPU. It would also be nice if 2MGFX had an optimization level option.

2 Likes

Thanks for the info…

I love MonoGame and have mad respect for its devs, but s far my experience with custom effects was pretty bad. Feels broken and unstable.

Hope it gets better after I memorize all the known issues and pitfalls.

1 Like

Check out the effect writing tips section in the docs for some common pitfalls/issues.

1 Like