Вы можете обратиться к одному фрагменту 3D-текстуры, играя со значениями координат 3D-текстуры (которые я буду называть (u, v, w)
координатами).
Например, допустим, вы хотите получить срезы вдоль оси Z.Представьте, что ваша трехмерная текстура живет единичным кубом в трехмерном мире.Координаты (u, v, 0)
дадут тексели первого среза.(u, v, 0.5)
даст тексели в середине объема, а (u, v, 1.0)
- тексели последнего среза.
Первый шейдер среза будет выглядеть так:
// slicer.cg
//------------------------------------------------------------------------------
struct AppData
{
float3 position : POSITION;
float3 normal : NORMAL;
float3 texcoord : TEXCOORD0;
};
struct VertexOutput
{
float4 position : POSITION;
float3 texcoord : TEXCOORD0;
};
//------------------------------------------------------------------------------
VertexOutput main_vp( AppData IN
, uniform float4 slice
, uniform float4x4 worldViewProj)
{
VertexOutput OUT;
OUT.position = mul(worldViewProj, float4(IN.position, 1));
OUT.texcoord = float3(IN.texcoord.xy, slice.x);
return OUT;
}
//------------------------------------------------------------------------------
void main_fp( float3 texcoord : TEXCOORD0
, out float3 oColor : COLOR
, uniform sampler3D volume)
{
float val = tex3D(volume, texcoord).a;
oColor = float3(1.0, 0.0, 0.0) ;
}
InВ этом примере индекс среза вдоль оси Z пропускается через равномерную переменную (float4 slice
) в вершинном шейдере (main_vp)
.* Текстурные координаты (u, v)
определены в сетке (в данном случае это будет простой 2D-квад), интерполируются графическим процессором и используются во фрагментном шейдере (main_fp
)
I'mне уверен, чего вы пытаетесь достичь, открыв предыдущий фрагмент, но вы можете сделать это, заново вычислив значение w
в шейдере и повторно сэмплировав 3D-текстуру.
Конечно, вы можетеразрезать ваш куб вдоль другой оси или даже с произвольной плоскостью, но этой последней потребуется немного больше математики, чтобы получить координаты 3 (u, v, w)
.