模型:
生成一个弧形的顶
//===========================================================================
//
// x = r * cos(phi) * sin(theta)
// y = r * sin(phi) * sin(theta)
// z = r * cos(theta)
//
// 这里phi的范围是0 < phi <= 2Pi,theta范围是0 < theta < Pi
// 半球的theta范围是[0, Pi/2]
// 因为使用单位向量r=1,所以上述公式简化为:
//
// x = cos(phi) * sin(theta)
// y = sin(phi) * sin(theta)
// z = cos(theta)
//
//------------------------------------------------------------------------------
//
// 1) 我们必须注意顶点是以逆时针顺序绘制的,因为我们是从天空球内部向外看的。
//
// 2) uv坐标必须正确计算。
//
//
// 最终我们获得以下公式:
//
// x = cos(phi) * sin(theta)
// y = cos(theta)
// z = sin(phi) * sin(theta)
//
//===========================================================================
int cylinders = 100; // 水平面数
int slices = 100; // 垂直面数
mVertexCount = (slices + 1) * (cylinders + 1);
mIndexCount = (3 * slices * (cylinders + 1)) * 2;
float verticalRadians = PI;
vertices = new VertexBuffer[mVertexCount];
indices = new unsigned long[mIndexCount];
float stackAngle = verticalRadians / (float)slices;
float sliceAngle = (float)(PI * 2.0) / (float)cylinders;
int wVertexIndex = 0;
int vertcount = 0;
int Indexcount = 0;
for (int stack = 0; stack < (slices + 1); stack++)
{
float r = sin((float)stack * stackAngle);
float y = cos((float)stack * stackAngle);
for (int slice = 0; slice < (cylinders + 1); slice++)
{
float z = r * sin((float)slice * sliceAngle); //* -1;
float x = r * cos((float)slice * sliceAngle);
vertices[vertcount].position = Vector3(x, y, z);
//vertices[vertcount].texture = Vector2(1.0f - (float)slice / (float)cylinders, (float)stack / (float)slices);
vertcount++;
if (!(stack == (slices - 1)))
{
indices[Indexcount] = wVertexIndex + (cylinders + 1);
Indexcount++;
indices[Indexcount] = wVertexIndex + 1;
Indexcount++;
indices[Indexcount] = wVertexIndex;
Indexcount++;
indices[Indexcount] = wVertexIndex + (cylinders);
Indexcount++;
indices[Indexcount] = wVertexIndex + (cylinders + 1);
Indexcount++;
indices[Indexcount] = wVertexIndex;
Indexcount++;
wVertexIndex++;
}
}
}
hlsl:这里需要注意的是:output.tex = input.position 纹理坐标是模型的相对坐标,而建模的时候球心要为相对坐标的(0,0,0)位置。
TextureCube mCubeTexture;
SamplerState mSamplerState;
/
// GLOBALS //
/
cbuffer MatrixBuffer
{
matrix world;
matrix transform;
};
//
// TYPEDEFS //
//
struct VertexInputType
{
float4 position : POSITION;
};
struct PixelInputType
{
float4 position : SV_POSITION;
float3 tex :TEXCOORD;
};
// Vertex Shader
PixelInputType PortVertexShader(VertexInputType input)
{
PixelInputType output;
input.position.w = 1.0f;
output.position = normalize(mul(input.position, transform));
output.tex = input.position; //用local坐标做为cubemap查询向量.
return output;
}
// Pixel Shader
float4 PortPixelShader(PixelInputType input) : SV_TARGET
{
float4 color = mCubeTexture.Sample(mSamplerState, input.tex);
return color;
}