Reputation: 23
This is my Hull Shader, I get "warning X3554: unknown attribute <attr_name_here>, or attribute invalid for this statement" on every attribute above the main function, as well as "error X3658: 'main': InputPatch inputs can only be used in the domain shaders and a hull shader's patch constant function" on the InputPatch parameter in the main function:
struct HullShaderInput
{
float4 wPos : WPOSITION;
float4 position : SV_POSITION;
float3 colour : COLOUR;
float3 normal : NORMAL;
float2 uv : UV;
};
struct HullShaderConstDataOutput
{
float EdgeTessFactor[3] : SV_TessFactor;
float InsideTessFactor : SV_InsideTessFactor;
};
struct HullShaderOutput
{
float4 wPos : WPOSITION;
float4 position : SV_POSITION;
float3 colour : COLOUR;
float3 normal : NORMAL;
float2 uv : UV;
};
cbuffer cBuff : register(b0)
{
float4x4 world;
float4x4 view;
float4x4 projection;
float4 camPos;
}
//cbuffer iBuff : register(b1)
//{
// float4 objPos;
//}
#define NUM_CONTROL_POINTS 3
float calcTessFactor(float3 vertP1, float3 vertP2)
{
float edgeLen = distance(vertP1, vertP2);
float edgeCamDist = distance((vertP1+vertP2)/2, camPos.xyz);
// Not based on objects size on the screen
// To give more accurate approximation, multiply with the screen height in pixels and an FOV factor (1 at 90 deg, increasing at lower FOV),
//and divide by the allowed edge length in pixels.
return clamp((edgeLen)/(edgeCamDist), 1.0f, 63.0f); // Using max=63 because of fractional_odd partitioning
}
HullShaderConstDataOutput CalcHSPatchConstants
( InputPatch<HullShaderInput, NUM_CONTROL_POINTS> ip,
uint i : SV_PrimitiveID )
{
HullShaderConstDataOutput output;
// This function should calculate the factors based on distance to camera, so the constant value is just temporary... I think
//output.EdgeTessFactor[0] = output.EdgeTessFactor[1] = output.EdgeTessFactor[2] = output.InsideTessFactor = 32;
// Anyways, this should have a decent approximation for realistic tessellation factors based on distance to camera
// That is, if every "ip" represents a triangle, and "i" represents a point on said triangle
output.EdgeTessFactor[i] = calcTessFactor(ip[i].wPos.xyz, ip[(i+1)%3].wPos.xyz);
output.InsideTessFactor = (output.EdgeTessFactor[0]+output.EdgeTessFactor[1]+output.EdgeTessFactor[2])/3;
return output;
}
[domain("tri")]
[partitioning("fractional_odd")]
[outputtopology("triangle_cw")]
[outputcontrolpoints(3)]
[patchconstantfunc("HullShaderConstDataOutput")]
HullShaderOutput main
( InputPatch<HullShaderInput, NUM_CONTROL_POINTS> ip,
uint i : SV_OutputControlPointID )
{
HullShaderOutput output;
output.wPos = ip[i].wPos;
output.position = ip[i].position;
output.normal = ip[i].normal;
output.uv = ip[i].uv;
return output;
}
This is my Domain Shader, I get "warning X3554" on [domain("tri")] and "error X3658" on on the main function's OutputPatch parameter:
struct DomainShaderConstDataInput
{
float EdgeTessFactor[3] : SV_TessFactor;
float InsideTessFactor : SV_InsideTessFactor;
};
struct DomainShaderInput
{
float4 wPos : WPOSITION;
float4 position : SV_POSITION;
float3 colour : COLOUR;
float3 normal : NORMAL;
float2 uv : UV;
};
struct DomainShaderOutput
{
float4 wPos : WPOSITION;
float4 position : SV_POSITION;
float3 colour : COLOUR;
float3 normal : NORMAL;
float2 uv : UV;
};
cbuffer cBuff : register(b0)
{
float4x4 world;
float4x4 view;
float4x4 projection;
float4 camPos;
};
#define NUM_CONTROL_POINTS 3
[domain("tri")]
DomainShaderOutput main
( DomainShaderConstDataInput input, float3 barycentric : SV_DomainLocation,
const OutputPatch<DomainShaderInput, NUM_CONTROL_POINTS> patch )
{
DomainShaderOutput output;
output.wPos = patch[0].wPos*barycentric.x + patch[1].wPos*barycentric.y + patch[2].wPos*barycentric.z;
output.normal = normalize(patch[0].normal*barycentric.x + patch[1].normal*barycentric.y + patch[2].normal*barycentric.z);
output.uv = patch[0].uv*barycentric.x + patch[1].uv*barycentric.y + patch[2].uv*barycentric.z;
output.position = mul(mul(output.wPos, view), projection);
return output;
}
What am I doing wrong here?
Edit:
So, it turns out that my Hull and Domain shaders were using Shader Model 4, when 5 is required. Still, I can't compile them yet, because for some reason the HullShaderConstDataOutput attribute's entrypoint can't be found in the main function.
Upvotes: 0
Views: 164
Reputation: 23
So, it turns out that my Hull and Domain shaders were using Shader Model 4, when 5 is required. It is now fixed. I also had the issue of referring to the constData struct and not the constData function, so that also sucks. Anyways, I can now render tessellated surfaces based on distance to the camera and the edge length for a fixed window size and FOV==90.
Upvotes: 1