我使用 ID3DXFont::DrawText 在窗口上绘制文本。但是当窗口调整大小时,文本也会拉伸/收缩。我试图计算窗口大小改变的百分比,并应用于字体大小,但它看起来真的很奇怪。我想知道是否有固定字体大小,即使窗口大小改变了。这是我绘制文本的方式:
g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0,0,255), 1.0f, 0 );
if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )
{
D3DXFONT_DESC df;
ZeroMemory(&df,sizeof(D3DXFONT_DESC));
df.Height = 25;
df.Width = 0;
df.Weight = 100;
df.MipLevels = D3DX_DEFAULT;
df.Italic = false;
df.CharSet = DEFAULT_CHARSET;
df.Quality = 0;
df.PitchAndFamily = 0;
strcpy(df.FaceName,"Candara");
D3DXCreateFontIndirect(g_pd3dDevice,&df,&g_font);
RECT g_FontPosition = {0, 0, 300, 300};
g_font->DrawText(NULL,"Hello World",-1,&g_FontPosition,
DT_CENTER|DT_VCENTER,D3DCOLOR_XRGB(255,255,255));
// End the scene
g_pd3dDevice->EndScene();
}
g_pd3dDevice->Present( NULL, NULL, NULL, NULL );
我尝试使用 SetViewport 方法,但是没有用。以下代码显示了我如何操作 direct3d。我已经在这个问题上停留了很长一段时间,完全不知道如何解决它。
STDMETHODIMP VideoRender::InitializeD3D(VOID)
{
HRESULT hr = E_FAIL;
D3DDISPLAYMODE d3ddm;
D3DCAPS9 d3dcaps;
DWORD dwCreateFlags = D3DCREATE_FPU_PRESERVE;
D3DPRESENT_PARAMETERS d3dpp;
m_lpD3D = Direct3DCreate9(D3D_SDK_VERSION);
hr = IDirect3D9_GetAdapterDisplayMode(m_lpD3D, D3DADAPTER_DEFAULT, &d3ddm);
if (m_lpD3D == NULL)
goto error_occured;
hr = IDirect3D9_GetAdapterDisplayMode(m_lpD3D, D3DADAPTER_DEFAULT, &d3ddm);
if (FAILED(hr))
goto error_occured;
hr = IDirect3D9_GetDeviceCaps(m_lpD3D, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, &d3dcaps);
if (FAILED(hr))
goto error_occured;
if ((d3dcaps.DevCaps & D3DDEVCAPS_HWTRANSFORMANDLIGHT) == D3DDEVCAPS_HWTRANSFORMANDLIGHT)
dwCreateFlags |= D3DCREATE_HARDWARE_VERTEXPROCESSING;
else
dwCreateFlags |= D3DCREATE_SOFTWARE_VERTEXPROCESSING;
if ( (d3dcaps.StretchRectFilterCaps & D3DPTFILTERCAPS_MINFLINEAR) == D3DPTFILTERCAPS_MINFLINEAR
&& (d3dcaps.StretchRectFilterCaps & D3DPTFILTERCAPS_MAGFLINEAR) == D3DPTFILTERCAPS_MAGFLINEAR ) {
m_d3dfiltertype = D3DTEXF_LINEAR;
} else
m_d3dfiltertype = D3DTEXF_NONE;
m_d3dformat = d3ddm.Format;
ZeroMemory(&d3dpp, sizeof(D3DPRESENT_PARAMETERS));
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferCount = 1;
d3dpp.BackBufferFormat = m_d3dformat;
d3dpp.BackBufferWidth = m_dwWindowWidth;
d3dpp.BackBufferHeight = m_dwWindowHeight;
d3dpp.MultiSampleQuality = D3DMULTISAMPLE_NONE;
d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_DEFAULT;
hr = IDirect3D9_CreateDevice(m_lpD3D, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, m_hAppWindow, dwCreateFlags, &d3dpp, &m_lpDevice);
if (FAILED(hr))
goto error_occured;
return S_OK;
error_occured:
return hr;
}
STDMETHODIMP VideoRender::InitializeSwapChain(DWORD dwWidth, DWORD dwHeight)
{
HRESULT hr = E_FAIL;
D3DPRESENT_PARAMETERS d3dpp;
D3DTEXTUREFILTERTYPE d3dfiltertype;
D3DFORMAT d3dformat;
D3DFORMAT d3dfourcc;
D3DLOCKED_RECT LockedRect = {0};
LPBYTE lpByte = NULL;
LPDWORD lpdwColor = NULL;
DWORD dwFontSize = 16;
if (m_lpDevice == NULL)
InitializeD3D();
if (m_lpDevice) {
if (dwWidth && dwHeight) {
m_dwVideoWidth = dwWidth;
m_dwVideoHeight = dwHeight;
d3dfourcc = (D3DFORMAT) MAKEFOURCC('Y', 'V', '1', '2');
d3dformat = D3DFMT_X8R8G8B8;
ZeroMemory(&d3dpp, sizeof(D3DPRESENT_PARAMETERS));
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferWidth = m_dwVideoWidth;
d3dpp.BackBufferHeight = m_dwVideoHeight;
d3dpp.BackBufferFormat = d3dformat;
d3dpp.hDeviceWindow = m_hAppWindow;
hr = IDirect3DDevice9_CreateAdditionalSwapChain(m_lpDevice, &d3dpp, &m_lpSwapChain);
if (FAILED(hr))
goto error_occured;
hr = IDirect3DDevice9_CreateOffscreenPlainSurface(m_lpDevice, m_dwVideoWidth, m_dwVideoHeight, d3dfourcc, D3DPOOL_DEFAULT, &m_lpSurface, NULL);
if (FAILED(hr))
goto error_occured;
hr = IDirect3D9_CheckDeviceFormat(m_lpD3D, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, m_d3dformat, D3DUSAGE_QUERY_FILTER, D3DRTYPE_TEXTURE, d3dformat);
if (FAILED(hr))
d3dfiltertype = D3DTEXF_NONE;
else
d3dfiltertype = m_d3dfiltertype;
m_d3dfiltertype = d3dfiltertype;
m_d3dformat = d3dformat;
m_d3dfourcc = d3dfourcc;
hr = IDirect3DDevice9_CreateTexture(m_lpDevice, 2048, 2048, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &m_lpTexture, NULL);
IDirect3DTexture9_LockRect(m_lpTexture, 0, &LockedRect, NULL, D3DLOCK_DISCARD);
lpByte = (LPBYTE) LockedRect.pBits;
lpdwColor = (LPDWORD) lpByte;
memset(lpByte, 0xff, 2048 * 2048 * 4);
IDirect3DTexture9_UnlockRect(m_lpTexture, 0);
hr = D3DXCreateSprite(m_lpDevice, &m_lpSprite);
if (FAILED(hr)) {
}
hr = D3DXCreateFont(m_lpDevice, dwFontSize, 0, FW_BOLD, 0, FALSE, DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_DONTCARE, L"Consolas", &m_lpInfoFont);
if (FAILED(hr)) {
}
m_bInitedSwapChain = TRUE;
}
}
return S_OK;
error_occured:
return hr;
}
STDMETHODIMP VideoRender::Update(LPBYTE lpBuffer)
{
HRESULT hr = S_OK;
LPDIRECT3DSURFACE9 lpBackBuffer = NULL;
DWORD dwWidth = 0;
DWORD dwHeight = 0;
D3DPRESENT_PARAMETERS d3dpp;
if (lpPluginBuffer) {
EnterCriticalSection(&m_csSwapChain);
if (m_lpSwapChain) {
IDirect3DSwapChain9_GetPresentParameters(m_lpSwapChain, &d3dpp);
hr = IDirect3DSwapChain9_GetBackBuffer(m_lpSwapChain, 0, D3DBACKBUFFER_TYPE_MONO, &lpBackBuffer);
hr = IDirect3DDevice9_SetRenderTarget(m_lpDevice, 0, lpBackBuffer);
hr = IDirect3DSurface9_Release(lpBackBuffer);
hr = IDirect3DDevice9_Clear(m_lpDevice, 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 0, 0), 1.0f, 0);
hr = IDirect3DDevice9_BeginScene(m_lpDevice);
if (SUCCEEDED(hr)) {
D3DLOCKED_RECT LockedRect;
LPBYTE source = 0, dest = 0;
ZeroMemory(&LockedRect, sizeof(D3DLOCKED_RECT));
hr = IDirect3DSurface9_LockRect(m_lpSurface, &LockedRect, NULL, 0);
dest = (LPBYTE) LockedRect.pBits;
source = lpPluginBuffer->lpBuffer;
if (SUCCEEDED(hr) && dest) {
/* copy image buffer to LockedRect */
}
IDirect3DSurface9_UnlockRect(m_lpSurface);
hr = IDirect3DDevice9_StretchRect(m_lpDevice, m_lpSurface, lprtSrc, lpBackBuffer, lprtDest, D3DTEXF_LINEAR);
m_lpSprite->Begin(D3DXSPRITE_ALPHABLEND);
pos.x = 0;
pos.y = 0;
pos.z = 0;
SetRect(&rt, 0, 0, 100, 100);
m_lpInfoFont->DrawTextW(m_lpSprite, L"test", -1, &rt, DT_VCENTER, D3DCOLOR_RGBA(0, 255, 255, 0xff));
m_lpSprite->End();
}
hr = IDirect3DDevice9_EndScene(m_lpDevice);
hr = IDirect3DSwapChain9_Present(m_lpSwapChain, NULL, NULL, NULL, NULL, 0);
}
LeaveCriticalSection(&m_csSwapChain);
}
return S_OK;
}
非常感谢,这真的很有帮助。
但是,如果我创建一个与窗口大小(更大或更小)具有不同分辨率后备缓冲区的交换链。并将一些图像渲染到窗口,它会自动重新调整图像大小以适应窗口大小。由于大小不同,视口似乎已更改。绘制的文本也会被拉伸/收缩。有什么办法可以防止这种情况发生吗?
我希望覆盖文本不受其他任何影响。