|
|
|
@@ -945,6 +945,8 @@ void CHSH_Device::DrawTexture(float pt[4][2],DWORD dwColor,float tx1,float ty1,f
|
|
|
|
|
|
|
|
|
|
extern int g_nDualHead;
|
|
|
|
|
extern int g_nNonDualHead;
|
|
|
|
|
extern int g_nMFD1; // mode 4: left 640x480 MFD monitor
|
|
|
|
|
extern int g_nMFD2; // mode 4: right 640x480 MFD monitor
|
|
|
|
|
// MSL 5.03 Mechview
|
|
|
|
|
extern int g_nMechViewType; // jcem : 0 - no mechview, 1 - on radar screen, 2 - on main screen
|
|
|
|
|
|
|
|
|
@@ -1066,6 +1068,23 @@ bool CMR_Device::LoadMRTargetTexture(const char *mechtexturename)
|
|
|
|
|
|
|
|
|
|
CMR_Device mr_device;
|
|
|
|
|
|
|
|
|
|
// Mode 4: the right-hand 640x480 MFD device. Shares VRAM with mfd_device
|
|
|
|
|
// (same GPU), so mfd_device's pDDSTarget texture can be passed to this
|
|
|
|
|
// device's pD3DDevice->SetTexture without a copy.
|
|
|
|
|
CMFDRight_Device mfd_device_right;
|
|
|
|
|
|
|
|
|
|
bool CMFDRight_Device::InitFirst()
|
|
|
|
|
{
|
|
|
|
|
// Take over g_nMFD2 monitor at 640x480 fullscreen.
|
|
|
|
|
return CHSH_Device::InitFirst(g_nMFD2, 640, 480);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool CMFDRight_Device::InitSecond()
|
|
|
|
|
{
|
|
|
|
|
// Create flip chain, D3D device and a render-target slot (1024x512).
|
|
|
|
|
return CHSH_Device::InitSecond(1024, 512);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/////////////////////////////////// CRadar_Device ///////////////////////////////////
|
|
|
|
|
const char g_szRadarShutdown[] = "SHUT\nDOWN";
|
|
|
|
|
const char g_szRadarStartup[] = "START\nUP";
|
|
|
|
@@ -1349,7 +1368,7 @@ static DWORD channel_color[6]={
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
CMFD_Device::CMFD_Device()
|
|
|
|
|
: ch((DWORD)-1)
|
|
|
|
|
: ch((DWORD)-1), m_pRightDevice(NULL)
|
|
|
|
|
{
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@@ -1359,6 +1378,15 @@ CMFD_Device::~CMFD_Device()
|
|
|
|
|
|
|
|
|
|
bool CMFD_Device::InitFirst()
|
|
|
|
|
{
|
|
|
|
|
// Mode 4: use g_nMFD1 (640x480) for left panel; also start up the right
|
|
|
|
|
// device here so both displays are ready before InitSecond runs.
|
|
|
|
|
if (g_nTypeOfMFDs == 4) {
|
|
|
|
|
m_pRightDevice = &mfd_device_right;
|
|
|
|
|
CHSH_Device::InitFirst(g_nMFD1, 640, 480); // left device
|
|
|
|
|
mfd_device_right.InitFirst(); // right device display mode
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
m_pRightDevice = NULL;
|
|
|
|
|
return CHSH_Device::InitFirst(g_nDualHead,1280,480);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@@ -1409,6 +1437,11 @@ bool CMFD_Device::InitSecond()
|
|
|
|
|
pD3DDevice->SetMaterial( &mtrl );
|
|
|
|
|
pD3DDevice->SetRenderState( D3DRENDERSTATE_AMBIENT, 0xffffffff );
|
|
|
|
|
|
|
|
|
|
// Mode 4: create flip chain + D3D device for the right 640x480 monitor.
|
|
|
|
|
if (g_nTypeOfMFDs == 4 && m_pRightDevice) {
|
|
|
|
|
mfd_device_right.InitSecond();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@@ -1450,6 +1483,11 @@ bool CMFD_Device::BeginChannel(DWORD channel)
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
break;
|
|
|
|
|
case 4:
|
|
|
|
|
// Same 7-step timing as mode 1: channels 0-4 map to sh_step 2-6.
|
|
|
|
|
if (sh_step != (int)(channel + 2))
|
|
|
|
|
return false;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
ch=channel;
|
|
|
|
|
|
|
|
|
@@ -1475,8 +1513,42 @@ bool CMFD_Device::EndChannel()
|
|
|
|
|
gCaptureScreen = 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
SetRenderTargetBackbuffer();
|
|
|
|
|
pD3DDevice->BeginScene();
|
|
|
|
|
// Mode 4: route this channel's blit to the correct physical monitor.
|
|
|
|
|
// Handled here, before the modes 1-3 SetRenderTargetBackbuffer/BeginScene
|
|
|
|
|
// block, so each path has exactly one matched Begin/EndScene pair.
|
|
|
|
|
// Channels 0-2 go to the LEFT device (this, g_nMFD1).
|
|
|
|
|
// Channels 3-4 go to the RIGHT device (m_pRightDevice, g_nMFD2).
|
|
|
|
|
// pDDSTarget was created by this device's pDD; both devices are on the
|
|
|
|
|
// same GPU so VRAM textures are mutually accessible.
|
|
|
|
|
if (g_nTypeOfMFDs == 4 && m_pRightDevice) {
|
|
|
|
|
CHSH_Device* target = (ch >= 3) ? m_pRightDevice : static_cast<CHSH_Device*>(this);
|
|
|
|
|
target->SetRenderTargetBackbuffer();
|
|
|
|
|
target->pD3DDevice->BeginScene();
|
|
|
|
|
|
|
|
|
|
target->pD3DDevice->SetRenderState(D3DRENDERSTATE_ALPHABLENDENABLE,TRUE);
|
|
|
|
|
target->pD3DDevice->SetRenderState(D3DRENDERSTATE_SRCBLEND,D3DBLEND_ONE);
|
|
|
|
|
target->pD3DDevice->SetRenderState(D3DRENDERSTATE_DESTBLEND,D3DBLEND_ONE);
|
|
|
|
|
|
|
|
|
|
target->pD3DDevice->SetTexture(0, pDDSTarget);
|
|
|
|
|
|
|
|
|
|
DWORD color4 = channel_color[ch];
|
|
|
|
|
float w4 = (float)target->size_back.cx; // 640
|
|
|
|
|
float h4 = (float)target->size_back.cy; // 480
|
|
|
|
|
float w2_4 = (float)size_target.cx; // 1024
|
|
|
|
|
float h2_4 = (float)size_target.cy; // 512
|
|
|
|
|
D3DTLVERTEX V4[4];
|
|
|
|
|
V4[0]=D3DTLVERTEX(D3DVECTOR( -0.5f,h4-0.5f,0.9f),1.0f,color4,0, 0/w2_4,h4/h2_4);
|
|
|
|
|
V4[1]=D3DTLVERTEX(D3DVECTOR( -0.5f, -0.5f,0.9f),1.0f,color4,0, 0/w2_4, 0/h2_4);
|
|
|
|
|
V4[2]=D3DTLVERTEX(D3DVECTOR(w4-0.5f,h4-0.5f,0.9f),1.0f,color4,0,w4/w2_4,h4/h2_4);
|
|
|
|
|
V4[3]=D3DTLVERTEX(D3DVECTOR(w4-0.5f, -0.5f,0.9f),1.0f,color4,0,w4/w2_4, 0/h2_4);
|
|
|
|
|
target->pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP,D3DFVF_TLVERTEX,V4,4,NULL);
|
|
|
|
|
|
|
|
|
|
target->pD3DDevice->EndScene();
|
|
|
|
|
ch = (DWORD)-1;
|
|
|
|
|
} else {
|
|
|
|
|
// Modes 1-3: blit to half of the single 1280-wide (or 640-wide) backbuffer.
|
|
|
|
|
SetRenderTargetBackbuffer();
|
|
|
|
|
pD3DDevice->BeginScene();
|
|
|
|
|
|
|
|
|
|
pD3DDevice->SetRenderState(D3DRENDERSTATE_ALPHABLENDENABLE,TRUE);
|
|
|
|
|
pD3DDevice->SetRenderState(D3DRENDERSTATE_SRCBLEND,D3DBLEND_ONE);
|
|
|
|
@@ -1504,8 +1576,9 @@ bool CMFD_Device::EndChannel()
|
|
|
|
|
|
|
|
|
|
pD3DDevice->DrawPrimitive( D3DPT_TRIANGLESTRIP, D3DFVF_TLVERTEX , Vertices, 4, NULL );
|
|
|
|
|
|
|
|
|
|
pD3DDevice->EndScene();
|
|
|
|
|
ch = (DWORD)-1;
|
|
|
|
|
pD3DDevice->EndScene();
|
|
|
|
|
ch = (DWORD)-1;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
@@ -1533,6 +1606,25 @@ bool CMFD_Device::BeginScene()
|
|
|
|
|
pD3DDevice->Clear(1,&s_rc2,D3DCLEAR_TARGET ,0,1.0f,0);
|
|
|
|
|
//pD3DDevice->Clear(0,NULL,D3DCLEAR_TARGET ,0,1.0f,0);
|
|
|
|
|
}break;
|
|
|
|
|
case 4:
|
|
|
|
|
// Clear and draw background grid on the LEFT device.
|
|
|
|
|
SetRenderTargetBackbuffer();
|
|
|
|
|
pD3DDevice->Clear(0,NULL,D3DCLEAR_TARGET,0,1.0f,0);
|
|
|
|
|
pD3DDevice->BeginScene();
|
|
|
|
|
if(sh_game_started) DrawMFDBackGrid();
|
|
|
|
|
pD3DDevice->EndScene();
|
|
|
|
|
// Clear and draw background grid on the RIGHT device.
|
|
|
|
|
if (m_pRightDevice) {
|
|
|
|
|
m_pRightDevice->SetRenderTargetBackbuffer();
|
|
|
|
|
m_pRightDevice->pD3DDevice->Clear(0,NULL,D3DCLEAR_TARGET,0,1.0f,0);
|
|
|
|
|
m_pRightDevice->pD3DDevice->BeginScene();
|
|
|
|
|
if(sh_game_started) {
|
|
|
|
|
m_pRightDevice->pD3DDevice->SetTexture(0,0);
|
|
|
|
|
m_pRightDevice->DrawQuadList(8,rcs640_solo,0xFFFFFFFF);
|
|
|
|
|
}
|
|
|
|
|
m_pRightDevice->pD3DDevice->EndScene();
|
|
|
|
|
}
|
|
|
|
|
return true; // skip the common BeginScene/DrawGrid/EndScene below
|
|
|
|
|
}
|
|
|
|
|
pD3DDevice->BeginScene();
|
|
|
|
|
if(sh_game_started) {
|
|
|
|
@@ -1559,6 +1651,11 @@ bool CMFD_Device::Release()
|
|
|
|
|
SAFE_RELEASE(pDDSDamageTexture);
|
|
|
|
|
// MSL 5.03 Target Damage Display
|
|
|
|
|
SAFE_RELEASE(pDDSTargetTexture);
|
|
|
|
|
// Mode 4: release the right device before releasing this (left) device.
|
|
|
|
|
if (g_nTypeOfMFDs == 4 && m_pRightDevice) {
|
|
|
|
|
m_pRightDevice->Release();
|
|
|
|
|
m_pRightDevice = NULL;
|
|
|
|
|
}
|
|
|
|
|
CHSH_Device::Release();
|
|
|
|
|
}
|
|
|
|
|
return true;
|
|
|
|
@@ -1700,6 +1797,19 @@ static RECT rcs640[8]={
|
|
|
|
|
{1120-1,440,1120+1,480},
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
// Mode 4: same grid pattern as rcs640 but offset to x=0 for a standalone
|
|
|
|
|
// 640x480 surface (left half of rcs1280).
|
|
|
|
|
static RECT rcs640_solo[8]={
|
|
|
|
|
{0,40,640,42},
|
|
|
|
|
{ 160-1,0, 160+1,40},
|
|
|
|
|
{ 320-1,0, 320+1,40},
|
|
|
|
|
{ 480-1,0, 480+1,40},
|
|
|
|
|
{0,480-42,640,480-40},
|
|
|
|
|
{ 160-1,440, 160+1,480},
|
|
|
|
|
{ 320-1,440, 320+1,480},
|
|
|
|
|
{ 480-1,440, 480+1,480},
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
bool CMFD_Device::DrawMFDBackGrid()
|
|
|
|
|
{
|
|
|
|
|
pD3DDevice->SetTexture(0,0);
|
|
|
|
@@ -1714,6 +1824,11 @@ bool CMFD_Device::DrawMFDBackGrid()
|
|
|
|
|
case 2:
|
|
|
|
|
DrawQuadList(8,rcs640,0xFFFFFFFF);
|
|
|
|
|
break;
|
|
|
|
|
case 4:
|
|
|
|
|
// Left device uses the left-half grid (0..640).
|
|
|
|
|
// Right device grid is drawn separately in BeginScene.
|
|
|
|
|
DrawQuadList(8,rcs640_solo,0xFFFFFFFF);
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return true;
|
|
|
|
@@ -2489,6 +2604,9 @@ bool IsMultimonitorAvaliable()
|
|
|
|
|
if ((*g_pfnCTCL_GetType)()==_ECTCL_CameraShip)
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
// Mode 4 uses its own device slots ? g_nDualHead is not required.
|
|
|
|
|
if (g_nTypeOfMFDs == 4)
|
|
|
|
|
return (g_nMFD1 != -1 && g_nMFD2 != -1);
|
|
|
|
|
if (g_nDualHead != -1) {
|
|
|
|
|
// 0 - no MFDs, 1 - orginal(5+1=dual & single), 2 - B&W(3 + 1=1 dual), 3 - color(3 + 1=2 dual)
|
|
|
|
|
switch(g_nTypeOfMFDs)
|
|
|
|
|