一个游戏是DX11的 我HOOK了它的present后 来绘制我自己想的图形,
一般正常游玩下,它都有把图形绘制出来 但是如果组队后 游戏的界面会多出一个组队的队友信息 导致我的图形不被显示了
但是如果在游戏内调出菜单栏或者 游戏内自己有文字提醒时,我绘制的图形又出现了.真的很奇怪 帮忙解答
正常模式下
组队模式下,游戏左上角会多出一个组队框出来 这时候我的图形就不绘制了
如果我呼出游戏的菜单或者游戏内有文字提醒输出在游戏画布上时,我画的东西又出现了
绘制图形代码
Renderer::Renderer(ID3D11Device *direct3DDevice, const std::wstring &defaultFontFamily) :
direct3DDevice(direct3DDevice),
immediateContext(nullptr),
inputLayout(nullptr),
vertexShader(nullptr),
pixelShader(nullptr),
fontFactory(nullptr),
fontWrapper(nullptr),
defaultFontFamily(defaultFontFamily),
maxVertices(1024 * 4 * 3)
{
D3D11_INPUT_ELEMENT_DESC layout[] =
{
{ "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
{ "COLOR", 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 16, D3D11_INPUT_PER_VERTEX_DATA, 0 },
};
ID3DBlob *vsBlob = nullptr;
ID3DBlob *psBlob = nullptr;
direct3DDevice->GetImmediateContext(&immediateContext);
throwIfFailed(FW1CreateFactory(FW1_VERSION, &fontFactory));
renderList = std::make_unique<RenderList>(fontFactory, maxVertices);
throwIfFailed(fontFactory->CreateFontWrapper(direct3DDevice, defaultFontFamily.c_str(), &fontWrapper));
HMODULE hD3DCompiler = LoadLibraryA("D3DCompiler_43.dll");
if (hD3DCompiler == NULL) {
ExitProcess(0);
}
m_pfnD3DCompile = reinterpret_cast<pD3DCompile>(GetProcAddress(hD3DCompiler, "D3DCompile"));
if (m_pfnD3DCompile == NULL) {
ExitProcess(0);
}
throwIfFailed(m_pfnD3DCompile(shader, std::size(shader), nullptr, nullptr, nullptr, "VS", "vs_4_0", 0, 0, &vsBlob, nullptr));
throwIfFailed(m_pfnD3DCompile(shader, std::size(shader), nullptr, nullptr, nullptr, "PS", "ps_4_0", 0, 0, &psBlob, nullptr));
throwIfFailed(direct3DDevice->CreateVertexShader(vsBlob->GetBufferPointer(), vsBlob->GetBufferSize(), nullptr, &vertexShader));
throwIfFailed(direct3DDevice->CreatePixelShader(psBlob->GetBufferPointer(), psBlob->GetBufferSize(), nullptr, &pixelShader));
throwIfFailed(direct3DDevice->CreateInputLayout(layout, static_cast<UINT>(std::size(layout)), vsBlob->GetBufferPointer(), vsBlob->GetBufferSize(), &inputLayout));
safeRelease(vsBlob);
safeRelease(psBlob);
D3D11_BLEND_DESC blendDesc{};
blendDesc.RenderTarget->BlendEnable = TRUE;
blendDesc.RenderTarget->SrcBlend = D3D11_BLEND_SRC_ALPHA;
blendDesc.RenderTarget->DestBlend = D3D11_BLEND_INV_SRC_ALPHA;
blendDesc.RenderTarget->SrcBlendAlpha = D3D11_BLEND_ONE;
blendDesc.RenderTarget->DestBlendAlpha = D3D11_BLEND_ZERO;
blendDesc.RenderTarget->BlendOp = D3D11_BLEND_OP_ADD;
blendDesc.RenderTarget->BlendOpAlpha = D3D11_BLEND_OP_ADD;
blendDesc.RenderTarget->RenderTargetWriteMask = D3D11_COLOR_WRITE_ENABLE_ALL;
throwIfFailed(direct3DDevice->CreateBlendState(&blendDesc, &blendState));
D3D11_BUFFER_DESC bufferDesc{};
bufferDesc.Usage = D3D11_USAGE_DYNAMIC;
bufferDesc.ByteWidth = sizeof(Vertex) * static_cast<UINT>(maxVertices);
bufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
bufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
bufferDesc.MiscFlags = 0;
throwIfFailed(direct3DDevice->CreateBuffer(&bufferDesc, nullptr, &vertexBuffer));
bufferDesc = {};
bufferDesc.Usage = D3D11_USAGE_DYNAMIC;
bufferDesc.ByteWidth = sizeof(XMMATRIX);
bufferDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
bufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
bufferDesc.MiscFlags = 0;
throwIfFailed(direct3DDevice->CreateBuffer(&bufferDesc, nullptr, &screenProjectionBuffer));
D3D11_VIEWPORT viewport{};
UINT numViewports = 1;
immediateContext->RSGetViewports(&numViewports, &viewport);
//DbgPrintA("%f, %f, %f, %f, %f, %f", viewport.TopLeftX, viewport.Width, viewport.Height, viewport.TopLeftY, viewport.MinDepth, viewport.MaxDepth);
projection = XMMatrixOrthographicOffCenterLH(viewport.TopLeftX, viewport.Width, viewport.Height, viewport.TopLeftY, viewport.MinDepth, viewport.MaxDepth);
D3D11_MAPPED_SUBRESOURCE mappedResource;
throwIfFailed(immediateContext->Map(screenProjectionBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource));
{
std::memcpy(mappedResource.pData, &projection, sizeof(XMMATRIX));
}
immediateContext->Unmap(screenProjectionBuffer, 0);
ID3D11Texture2D* RenderTargetTexture;
if (SUCCEEDED(g_pSwapChain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&RenderTargetTexture)))
{
direct3DDevice->CreateRenderTargetView(RenderTargetTexture, NULL, &pRenderTargetView);
RenderTargetTexture->Release();
}
}
Renderer::~Renderer()
{
safeRelease(vertexShader);
safeRelease(pixelShader);
safeRelease(vertexBuffer);
safeRelease(inputLayout);
safeRelease(blendState);
safeRelease(fontWrapper);
safeRelease(fontFactory);
}
void Renderer::begin()
{
immediateContext->OMSetRenderTargets(1, &pRenderTargetView, NULL);
UINT numViewports = 1;
D3D11_VIEWPORT viewport{};
immediateContext->RSGetViewports(&numViewports, &viewport);
projection = XMMatrixOrthographicOffCenterLH(viewport.TopLeftX, viewport.Width, viewport.Height, viewport.TopLeftY, viewport.MinDepth, viewport.MaxDepth);
D3D11_MAPPED_SUBRESOURCE mappedResource;
throwIfFailed(immediateContext->Map(screenProjectionBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource));
{
std::memcpy(mappedResource.pData, &projection, sizeof(XMMATRIX));
}
immediateContext->Unmap(screenProjectionBuffer, 0);
immediateContext->VSSetShader(vertexShader, nullptr, 0);
immediateContext->PSSetShader(pixelShader, nullptr, 0);
immediateContext->OMSetBlendState(blendState, nullptr, 0xffffffff);
immediateContext->VSSetConstantBuffers(0, 1, &screenProjectionBuffer);
immediateContext->IASetInputLayout(inputLayout);
UINT stride = sizeof(Vertex);
UINT offset = 0;
immediateContext->IASetVertexBuffers(0, 1, &vertexBuffer, &stride, &offset);
}
void Renderer::end()
{
//pRenderTargetView->Release();
renderList->clear();
}
void Renderer::draw(const RenderList::Ptr &renderList)
{
if (std::size(renderList->vertices) > 0)
{
D3D11_MAPPED_SUBRESOURCE mappedResource;
throwIfFailed(immediateContext->Map(vertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource));
{
std::memcpy(mappedResource.pData, renderList->vertices.data(), sizeof(Vertex) * std::size(renderList->vertices));
}
immediateContext->Unmap(vertexBuffer, 0);
}
std::size_t pos = 0;
for (const auto &batch : renderList->batches)
{
immediateContext->IASetPrimitiveTopology(batch.topology);
immediateContext->Draw(static_cast<UINT>(batch.count), static_cast<UINT>(pos));
pos += batch.count;
}
fontWrapper->Flush(immediateContext);
fontWrapper->DrawGeometry(immediateContext, renderList->textGeometry, nullptr, nullptr, FW1_RESTORESTATE);
}
void Renderer::draw()
{
draw(renderList);
}
HOOK及画图初始化
HRESULT __stdcall MyPresent(IDXGISwapChain* pSwapChain, UINT SyncInterval, UINT Flags)
{
static bool bInit = false;
if (!bInit)
{
g_pSwapChain = pSwapChain;
pSwapChain->GetDevice(__uuidof(g_pDevice), (void**)&g_pDevice);
renderer = std::make_unique<Renderer>(g_pDevice);
bInit = true;
}
renderer->begin();
renderer->drawOutlinedRectA(20, 20, 300, 300, GColor::Blue(), GColor::Red());
renderer->draw();
renderer->end();
HRESULT hRet = OLD_Present(pSwapChain, SyncInterval, Flags);
return hRet;
}