📄 mvolumerender.cpp
字号:
// make linear otf array
makeOtf();
HRESULT hr;
// Fill pre-integrated texture
// make
preIntegratedArray[0][0][0] = m_linearOtfArray[0];
preIntegratedArray[0][0][1] = m_linearOtfArray[0];
// float tmpAlpha = m_linearOtfArray[0]/255.0f;
// summedTable[0][0] = m_linearOtfArray[0] * tmpAlpha; // for RGB
summedTable[0][0] = (float)m_linearOtfArray[0]; // for RGB
summedTable[0][1] = (float)m_linearOtfArray[0]; // for alpha
for(int d=1; d<OTFTEXTUREWIDTH; d++) {
preIntegratedArray[d][d][0] = m_linearOtfArray[d];
preIntegratedArray[d][d][1] = m_linearOtfArray[d];
// tmpAlpha = m_linearOtfArray[d]/255.0f;
// summedTable[d][0] = summedTable[d-1][0] + m_linearOtfArray[d]*tmpAlpha; // for RGB
summedTable[d][0] = summedTable[d-1][0] + m_linearOtfArray[d]; // for RGB
summedTable[d][1] = summedTable[d-1][1] + m_linearOtfArray[d]; // for alpha
}
//
for(int sBack = 0; sBack < OTFTEXTUREWIDTH ; sBack++) {
int div = 0;
for(int sFront = sBack+1; sFront < OTFTEXTUREWIDTH; sFront++) {
div++;
preIntegratedArray[sBack][sFront][0] = DWORD((summedTable[sFront][0] - summedTable[sBack][0]) / (float)div);
preIntegratedArray[sBack][sFront][1] = DWORD((summedTable[sFront][1] - summedTable[sBack][1]) / (float)div);
}
}
// Upper-left copy
for(int sFront = 0; sFront < OTFTEXTUREWIDTH ; sFront++) {
for(int sBack = sFront+1; sBack < OTFTEXTUREWIDTH; sBack++) {
preIntegratedArray[sBack][sFront][0] = preIntegratedArray[sFront][sBack][0];
preIntegratedArray[sBack][sFront][1] = preIntegratedArray[sFront][sBack][1];
}
}
D3DLOCKED_RECT LockedRect;
hr = m_pPreIntegratedTexture->LockRect( 0, &LockedRect, 0, D3DLOCK_DISCARD);
if( FAILED(hr) )
return hr;
// yellow color
DWORD a, r, g, b;
#define OTFRED 255
#define OTFGREEN 255
#define OTFBLUE 255//159
for( UINT v=0; v<OTFTEXTUREWIDTH; v++ ) {
for( UINT u=0; u<OTFTEXTUREWIDTH; u++ ) {
r = preIntegratedArray[v][u][0];
g = preIntegratedArray[v][u][0];
b = preIntegratedArray[v][u][0];
a = preIntegratedArray[v][u][1];
// float tempDiv = (a / 255.0f);
//-----------------------------------------------------------------
/*
//for Opacity Weighted interpolation (color 俊 alpha 蚌秦辑 持绢淋.)???
// 咯扁辑 窍绰霸 唱篮瘤, 利盒窍扁傈俊 蚌秦辑 利盒窍绰霸 唱篮瘤?...
r = DWORD(OTFRED * tempDiv);
g = DWORD(OTFGREEN * tempDiv);
b = DWORD(OTFBLUE * tempDiv);
*/
((DWORD*)LockedRect.pBits)[u] = 0x00000000 + (a<<24) + (r<<16) + (g<<8) + (b);
}
LockedRect.pBits = (BYTE*)LockedRect.pBits + LockedRect.Pitch;
}
m_pPreIntegratedTexture->UnlockRect( 0 );
return TRUE;
}
//////////////////////// make(update) Min Max Volume texture //////////////////
//----- called in InitDeviceObjects(), OnHScroll() --------------------------------
HRESULT CAppForm::makeMMVolumeTexture()
{
HRESULT hr;
D3DLOCKED_BOX LockedBox;
hr = m_pVolumeTexMM->LockBox(0, &LockedBox, 0, 0);
if( FAILED(hr) )
return FALSE;
for(int w=0; w<divZ; w++ )
{
BYTE* pSliceStart = (BYTE*)LockedBox.pBits;
for(int v=0; v<divY; v++ )
{
for(int u=0; u<divX; u++ )
{
BYTE nonEmpty = 255;
int scalarMin = int(minDenDiv8[u][v][w] / float(0xffff) * (OTFTEXTUREWIDTH-1));
int scalarMax = int(maxDenDiv8[u][v][w] / float(0xffff) * (OTFTEXTUREWIDTH-1));
if( scalarMin >= OTFTEXTUREWIDTH ) scalarMin = OTFTEXTUREWIDTH - 1;
if( scalarMax >= OTFTEXTUREWIDTH ) scalarMax = OTFTEXTUREWIDTH - 1;
if( preIntegratedArray[scalarMin][scalarMax][1] == 0 ) { // preInt alpha 啊 0 搁..
nonEmpty = 0;
}
((BYTE*)LockedBox.pBits)[u] = nonEmpty;
}
LockedBox.pBits = (BYTE*)LockedBox.pBits + LockedBox.RowPitch;
}
LockedBox.pBits = pSliceStart + LockedBox.SlicePitch;
}//end of for
m_pVolumeTexMM->UnlockBox(0);
return TRUE;
}
////////////////// make HLSL Effect shader() ///////////////////////////////////////
//----- called in InitDeviceObjects() --------------------------------------
HRESULT CAppForm::MCreateShader()
{
HRESULT hr;
D3DCAPS9 caps;
m_pd3dDevice->GetDeviceCaps(&caps); // initialize m_pd3dDevice before using
if( caps.VertexShaderVersion < D3DVS_VERSION(2,0) )
return E_FAIL;
// Create the shader declaration for pass0.
D3DVERTEXELEMENT9 declPass0Proxy[] =
{
{ 0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0 },
{ 0, 12, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0 },
D3DDECL_END()
};
if( FAILED( hr = m_pd3dDevice->CreateVertexDeclaration( declPass0Proxy, &m_pObjOrderProxyVertexDecl ) ) )
return hr;
// Create the shader declaration for pass1.
D3DVERTEXELEMENT9 declPass1Proxy[] =
{
{ 0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0 },
{ 0, 12, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0 },
{ 0, 24, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1 },
D3DDECL_END()
};
if( FAILED( hr = m_pd3dDevice->CreateVertexDeclaration( declPass1Proxy, &m_pImagOrderProxyVertexDecl ) ) )
return hr;
//------------ make effect shader ----------------------------
// D3DXSHADER_PACKMATRIX_COLUMNMAJOR (DEFAULT) 荤侩.
hr = D3DXCreateEffectFromFile(m_pd3dDevice, "./shaders/mv_render.fx", NULL, NULL, NULL/*D3DXSHADER_PACKMATRIX_COLUMNMAJOR*/, NULL, &m_pEffect, NULL );
// .fx file failed to compile
if( FAILED( hr ) ) {
AfxMessageBox("ps_pass0.... -_-. Quitting...");
return E_FAIL;
}
return S_OK;
}
//-----------------------------------------------------------------------------
// Name: CAppForm::RestoreDeviceObjects()
// Desc: Paired with InvalidateDeviceObjects()
// The device exists, but may have just been Reset(). Resources in
// D3DPOOL_DEFAULT and any other device state that persists during
// rendering should be set here. Render states, matrices, textures,
// etc., that don't change during rendering can be set once here to
// avoid redundant state setting during Render() or FrameMove().
//-----------------------------------------------------------------------------
HRESULT CAppForm::RestoreDeviceObjects()
{
// TODO: setup render states
//--------- Set up the sampler 0 (3D volume texture sampler)
m_pd3dDevice->SetSamplerState( 0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 0, D3DSAMP_BORDERCOLOR, 0x00000000);
m_pd3dDevice->SetSamplerState( 0, D3DSAMP_ADDRESSU, D3DTADDRESS_BORDER);
m_pd3dDevice->SetSamplerState( 0, D3DSAMP_ADDRESSV, D3DTADDRESS_BORDER);
m_pd3dDevice->SetSamplerState( 0, D3DSAMP_ADDRESSW, D3DTADDRESS_BORDER);
//---------- Set up the sampler 1 (3D gradient texture sampler)
m_pd3dDevice->SetSamplerState( 1, D3DSAMP_MINFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 1, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 1, D3DSAMP_BORDERCOLOR, 0x00000000);
m_pd3dDevice->SetSamplerState( 1, D3DSAMP_ADDRESSU, D3DTADDRESS_BORDER );
m_pd3dDevice->SetSamplerState( 1, D3DSAMP_ADDRESSV, D3DTADDRESS_BORDER );
m_pd3dDevice->SetSamplerState( 1, D3DSAMP_ADDRESSW, D3DTADDRESS_BORDER);
//---------- Set up the sampler 2 (for 2D texture sampler) - PreInt Texture
m_pd3dDevice->SetSamplerState( 2, D3DSAMP_MINFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 2, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR );
// m_pd3dDevice->SetSamplerState( 2, D3DSAMP_MINFILTER, D3DTEXF_POINT );
// m_pd3dDevice->SetSamplerState( 2, D3DSAMP_MAGFILTER, D3DTEXF_POINT );
//--- D3DTADDRESS_CLAMP 肺.... ------------
m_pd3dDevice->SetSamplerState( 2, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP );
m_pd3dDevice->SetSamplerState( 2, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP );
// m_pd3dDevice->SetSamplerState( 2, D3DSAMP_BORDERCOLOR, 0x00000000);
// m_pd3dDevice->SetSamplerState( 2, D3DSAMP_ADDRESSU, D3DTADDRESS_BORDER );
// m_pd3dDevice->SetSamplerState( 2, D3DSAMP_ADDRESSV, D3DTADDRESS_BORDER );
//---------- Set up the sampler 3 (for 2D texture sampler) - InterTexture
// shader 俊辑 texture offset ( + 1.0/ (512*2) ) 歹秦拎辑 point sampling 栏肺 秦拎具..
//m_pd3dDevice->SetSamplerState( 3, D3DSAMP_MINFILTER, D3DTEXF_POINT );
//m_pd3dDevice->SetSamplerState( 3, D3DSAMP_MAGFILTER, D3DTEXF_POINT );
m_pd3dDevice->SetSamplerState( 3, D3DSAMP_MINFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 3, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 3, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP );
m_pd3dDevice->SetSamplerState( 3, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP );
//----------- Set up the sampler 4 (for 3D min-max texture)
m_pd3dDevice->SetSamplerState( 4, D3DSAMP_MINFILTER, D3DTEXF_POINT );
m_pd3dDevice->SetSamplerState( 4, D3DSAMP_MAGFILTER, D3DTEXF_POINT );
// m_pd3dDevice->SetSamplerState( 4, D3DSAMP_MINFILTER, D3DTEXF_LINEAR );
// m_pd3dDevice->SetSamplerState( 4, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 4, D3DSAMP_BORDERCOLOR, 0x00000000);
m_pd3dDevice->SetSamplerState( 4, D3DSAMP_ADDRESSU, D3DTADDRESS_BORDER);
m_pd3dDevice->SetSamplerState( 4, D3DSAMP_ADDRESSV, D3DTADDRESS_BORDER);
m_pd3dDevice->SetSamplerState( 4, D3DSAMP_ADDRESSW, D3DTADDRESS_BORDER);
//---------- Set up the sampler 5 - MPR Texture
m_pd3dDevice->SetSamplerState( 5, D3DSAMP_MINFILTER, D3DTEXF_POINT );
m_pd3dDevice->SetSamplerState( 5, D3DSAMP_MAGFILTER, D3DTEXF_POINT );
m_pd3dDevice->SetSamplerState( 5, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP );
m_pd3dDevice->SetSamplerState( 5, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP );
//---------- Set up the sampler 6 - MPR Mapper
m_pd3dDevice->SetSamplerState( 6, D3DSAMP_MINFILTER, D3DTEXF_POINT );
m_pd3dDevice->SetSamplerState( 6, D3DSAMP_MAGFILTER, D3DTEXF_POINT );
m_pd3dDevice->SetSamplerState( 6, D3DSAMP_BORDERCOLOR, 0x00000000);
m_pd3dDevice->SetSamplerState( 6, D3DSAMP_ADDRESSU, D3DTADDRESS_BORDER );
m_pd3dDevice->SetSamplerState( 6, D3DSAMP_ADDRESSV, D3DTADDRESS_BORDER );
//---------- Set up the sampler 7 - Virtual Volume
m_pd3dDevice->SetSamplerState( 7, D3DSAMP_MINFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 7, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR );
m_pd3dDevice->SetSamplerState( 7, D3DSAMP_BORDERCOLOR, 0x00000000);
m_pd3dDevice->SetSamplerState( 7, D3DSAMP_ADDRESSU, D3DTADDRESS_BORDER );
m_pd3dDevice->SetSamplerState( 7, D3DSAMP_ADDRESSV, D3DTADDRESS_BORDER );
// Set miscellaneous render states
m_pd3dDevice->SetRenderState( D3DRS_DITHERENABLE, FALSE );
m_pd3dDevice->SetRenderState( D3DRS_SPECULARENABLE, FALSE );
m_pd3dDevice->SetRenderState( D3DRS_CLIPPING, TRUE);
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE);
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, FALSE);
// RGBA blend
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, TRUE);
// Front to Back compositing
m_pd3dDevice->SetRenderState( D3DRS_SRCBLEND, D3DBLEND_INVDESTALPHA);
m_pd3dDevice->SetRenderState( D3DRS_DESTBLEND, D3DBLEND_ONE);
/*
//test
m_pd3dDevice->SetRenderState( D3DRS_SEPARATEALPHABLENDENABLE, TRUE);
m_pd3dDevice->SetRenderState( D3DRS_SRCBLENDALPHA, D3DBLEND_INVDESTALPHA);
m_pd3dDevice->SetRenderState( D3DRS_DESTBLENDALPHA, D3DBLEND_ONE);
*/
// Back to Front compositing
// m_pd3dDevice->SetRenderState( D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
// m_pd3dDevice->SetRenderState( D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
// Opacity Weighted interpolation 捞骨肺 D3DBLEND_SRCALPHA 措脚 D3DBLEND_ONE !!
// m_pd3dDevice->SetRenderState( D3DRS_SRCBLEND, D3DBLEND_ONE);
// m_pd3dDevice->SetRenderState( D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA );
// enable clip planes
m_pd3dDevice->SetRenderState( D3DRS_CLIPPLANEENABLE,
D3DCLIPPLANE0 | D3DCLIPPLANE1 | D3DCLIPPLANE2 | D3DCLIPPLANE3 | D3DCLIPPLANE4 | D3DCLIPPLANE5);
// Set the world matrix
// D3DXMATRIX matIdentity;
// D3DXMatrixIdentity( &matIdentity );
// m_pd3dDevice->SetTransform( D3DTS_WORLD, &matIdentity );
// Set up our view matrix. A view matrix can be defined given an eye point,
// a point to lookat, and a direction for which way is up. Here, we set the
// eye five units back along the z-axis and up three units, look at the
// origin, and define "up" to be in the y-direction.
D3DXVECTOR3 vFromPt = D3DXVECTOR3( 0.0f, 0.0f, -15.0f );
D3DXVECTOR3 vLookatPt = D3DXVECTOR3( 0.0f, 0.0f, 0.0f );
D3DXVECTOR3 vUpVec = D3DXVECTOR3( 0.0f, 1.0f, 0.0f );
D3DXMatrixLookAtLH( &matView, &vFromPt, &vLookatPt, &vUpVec );
// set Orthogonal Projection.
MSetOrthoProjection();
////////////////// plane for MESH. /////////////////////////////
// Restore the font
m_pFont->RestoreDeviceObjects();
return S_OK;
}
//-----------------------------------------------------------------------------
// Name: CAppForm::MSetOrthoProjection()
// Desc: Set Orthogonal Projection.
// Called in RestoreDeviceObjects(), OnMouseMove(UINT nFlags, CPoint point)
//-----------------------------------------------------------------------------
void CAppForm::MSetOrthoProjection()
{
/*
D3DVIEWPORT9 MainViewport;
//m_pd3dDevice->GetViewport(&MainViewport);
// Builds a left-handed orthogonal projection matrix
MainViewport.Height = m_d3dpp.BackBufferHeight;
MainViewport.Width = m_d3dpp.BackBufferWidth;
if(MainViewport.Height == 0) MainViewport.Height = 1;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -