Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

'ImGui_ImplWin32_WndProcHandler': identifier not found #8255

Open
barzor opened this issue Dec 22, 2024 · 4 comments
Open

'ImGui_ImplWin32_WndProcHandler': identifier not found #8255

barzor opened this issue Dec 22, 2024 · 4 comments

Comments

@barzor
Copy link

barzor commented Dec 22, 2024

Version/Branch of Dear ImGui:

Version 1.XX, Branch: XXX (master/docking/etc.)

Back-ends:

imgui_impl_dx11.cpp + imgui_impl_win32.cpp

Compiler, OS:

Windows 10

Full config/build information:

No response

Details:

My Issue/Question:

XXX (please provide as much context as possible)

Screenshots/Video:

image

Minimal, Complete and Verifiable Example code:

I am new to this. please review my screenshot. why am i getting the error while everything seem to be well placed?

@PathogenDavid
Copy link
Contributor

You need to manually copy the function prototype into your source file as per the instructions in imgui_impl_win32.h:

// Win32 message handler your application need to call.
// - Intentionally commented out in a '#if 0' block to avoid dragging dependencies on <windows.h> from this helper.
// - You should COPY the line below into your .cpp code to forward declare the function and then you can call it.
// - Call from your application's message handler. Keep calling your message handler unless this function returns TRUE.
#if 0
extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);
#endif

@barzor
Copy link
Author

barzor commented Dec 23, 2024

You need to manually copy the function prototype into your source file as per the instructions in imgui_impl_win32.h:

// Win32 message handler your application need to call.
// - Intentionally commented out in a '#if 0' block to avoid dragging dependencies on <windows.h> from this helper.
// - You should COPY the line below into your .cpp code to forward declare the function and then you can call it.
// - Call from your application's message handler. Keep calling your message handler unless this function returns TRUE.
#if 0
extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);
#endif

image

I am sorry for the mess and thank you for your time. I think I did everything you and GPT suggested me to do.
I installed Directx SDK as well

// Main Function
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {
    WNDCLASSEX wc = { sizeof(WNDCLASSEX), CS_CLASSDC, WndProc, 0L, 0L, GetModuleHandle(NULL), NULL, NULL, NULL, NULL, _T("Desktop Organizer"), NULL };
    RegisterClassEx(&wc);
    g_hWnd = CreateWindow(wc.lpszClassName, _T("Desktop Organizer"), WS_OVERLAPPEDWINDOW, 100, 100, 800, 600, NULL, NULL, wc.hInstance, NULL);

@barzor
Copy link
Author

barzor commented Dec 23, 2024

#include "imgui.h"
#include "imgui_impl_win32.h"
#include "imgui_impl_dx11.h"
#include <d3d11.h>
#include <tchar.h>
#include <shlobj.h>
#include <comdef.h>
#include <atlbase.h>
#include <string>
#include <vector>
#include <stdexcept>

// Add this line for the ImGui Win32 handler
extern "C" IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);

// Global Variables for DirectX
HWND g_hWnd = NULL;
ID3D11Device* g_pd3dDevice = NULL;
ID3D11DeviceContext* g_pd3dDeviceContext = NULL;
IDXGISwapChain* g_pSwapChain = NULL;
ID3D11RenderTargetView* g_mainRenderTargetView = NULL;

// Logs for Display
std::vector<std::wstring> g_LogMessages;

// Helper Function to Add Log Messages
void AddLog(const std::wstring& message) {
    g_LogMessages.push_back(message);
}

// Get the Path for a Known Folder Using its ID
std::wstring GetKnownFolderPath(REFKNOWNFOLDERID folderId) {
    PWSTR path = nullptr;
    if (SUCCEEDED(SHGetKnownFolderPath(folderId, 0, NULL, &path))) {
        std::wstring folderPath(path);
        CoTaskMemFree(path);
        return folderPath;
    }
    throw std::runtime_error("Failed to retrieve known folder path.");
}

// Create a Shortcut to a Folder on the Desktop
void CreateShortcutToDesktop(const std::wstring& folderName, const std::wstring& targetPath) {
    std::wstring desktopPath = GetKnownFolderPath(FOLDERID_Desktop);
    std::wstring shortcutPath = desktopPath + L"\\" + folderName + L".lnk";

    if (PathFileExists(shortcutPath.c_str())) {
        AddLog(L"Shortcut already exists: " + folderName);
        return;
    }

    CComPtr<IShellLink> pShellLink;
    HRESULT hr = CoCreateInstance(CLSID_ShellLink, NULL, CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&pShellLink));
    if (FAILED(hr)) {
        AddLog(L"Failed to create ShellLink COM object.");
        return;
    }

    pShellLink->SetPath(targetPath.c_str());
    pShellLink->SetDescription((folderName + L" Shortcut").c_str());

    CComPtr<IPersistFile> pPersistFile;
    hr = pShellLink.QueryInterface(&pPersistFile);
    if (FAILED(hr)) {
        AddLog(L"Failed to query IPersistFile interface.");
        return;
    }

    hr = pPersistFile->Save(shortcutPath.c_str(), TRUE);
    if (SUCCEEDED(hr)) {
        AddLog(L"Created shortcut: " + folderName);
    }
    else {
        AddLog(L"Failed to save shortcut: " + folderName);
    }
}

// Direct3D Helper Functions
bool CreateDeviceD3D(HWND hWnd) {
    DXGI_SWAP_CHAIN_DESC sd{};
    sd.BufferCount = 2;
    sd.BufferDesc.Width = 0;
    sd.BufferDesc.Height = 0;
    sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
    sd.BufferDesc.RefreshRate.Numerator = 60;
    sd.BufferDesc.RefreshRate.Denominator = 1;
    sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
    sd.OutputWindow = hWnd;
    sd.SampleDesc.Count = 1;
    sd.SampleDesc.Quality = 0;
    sd.Windowed = TRUE;
    sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD;

    HRESULT hr = D3D11CreateDeviceAndSwapChain(NULL, D3D_DRIVER_TYPE_HARDWARE, NULL, 0, NULL, 0,
        D3D11_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice, NULL, &g_pd3dDeviceContext);
    if (FAILED(hr)) {
        MessageBox(hWnd, L"Failed to create device and swap chain.", L"Error", MB_ICONERROR);
        return false;
    }

    ID3D11Texture2D* pBackBuffer = NULL;
    hr = g_pSwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer));
    if (FAILED(hr) || pBackBuffer == nullptr) {
        MessageBox(hWnd, L"Failed to retrieve back buffer.", L"Error", MB_ICONERROR);
        return false;
    }

    hr = g_pd3dDevice->CreateRenderTargetView(pBackBuffer, NULL, &g_mainRenderTargetView);
    pBackBuffer->Release();
    if (FAILED(hr)) {
        MessageBox(hWnd, L"Failed to create render target view.", L"Error", MB_ICONERROR);
        return false;
    }

    return true;
}

void CleanupDeviceD3D() {
    if (g_mainRenderTargetView) { g_mainRenderTargetView->Release(); g_mainRenderTargetView = NULL; }
    if (g_pSwapChain) { g_pSwapChain->Release(); g_pSwapChain = NULL; }
    if (g_pd3dDeviceContext) { g_pd3dDeviceContext->Release(); g_pd3dDeviceContext = NULL; }
    if (g_pd3dDevice) { g_pd3dDevice->Release(); g_pd3dDevice = NULL; }
}

// Render ImGui Layout
void RenderImGui() {
    ImGui_ImplDX11_NewFrame();
    ImGui_ImplWin32_NewFrame();
    ImGui::NewFrame();

    // Sidebar
    ImGui::Begin("Sidebar", NULL, ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoCollapse);
    ImGui::SetWindowPos(ImVec2(0, 0));
    ImGui::SetWindowSize(ImVec2(200, 600));

    if (ImGui::Button("Create Shortcuts", ImVec2(180, 40))) {
        AddLog(L"Creating shortcuts...");
        try {
            CreateShortcutToDesktop(L"Downloads", GetKnownFolderPath(FOLDERID_Downloads));
            CreateShortcutToDesktop(L"Documents", GetKnownFolderPath(FOLDERID_Documents));
            CreateShortcutToDesktop(L"Pictures", GetKnownFolderPath(FOLDERID_Pictures));
            CreateShortcutToDesktop(L"Videos", GetKnownFolderPath(FOLDERID_Videos));
            AddLog(L"Shortcuts created successfully.");
        }
        catch (const std::exception& e) {
            AddLog(L"Error: " + std::wstring(e.what(), e.what() + strlen(e.what())));
        }
    }

    if (ImGui::Button("Clear Logs", ImVec2(180, 40))) {
        g_LogMessages.clear();  // Clear the logs
    }

    if (ImGui::Button("Exit", ImVec2(180, 40))) {
        PostQuitMessage(0);
    }
    ImGui::End();

    // Log Window
    ImGui::SetNextWindowPos(ImVec2(210, 10), ImGuiCond_FirstUseEver);
    ImGui::SetNextWindowSize(ImVec2(570, 580), ImGuiCond_FirstUseEver);
    ImGui::Begin("Logs");
    for (const auto& log : g_LogMessages) {
        ImGui::Text("%ls", log.c_str());
    }
    ImGui::End();

    ImGui::Render();
    const float clear_color_with_alpha[4] = { 0.45f, 0.55f, 0.60f, 1.00f };
    g_pd3dDeviceContext->OMSetRenderTargets(1, &g_mainRenderTargetView, NULL);
    g_pd3dDeviceContext->ClearRenderTargetView(g_mainRenderTargetView, clear_color_with_alpha);
    ImGui_ImplDX11_RenderDrawData(ImGui::GetDrawData());
}

// Main Function
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {
    WNDCLASSEX wc = { sizeof(WNDCLASSEX), CS_CLASSDC, WndProc, 0L, 0L, GetModuleHandle(NULL), NULL, NULL, NULL, NULL, _T("Desktop Organizer"), NULL };
    RegisterClassEx(&wc);
    g_hWnd = CreateWindow(wc.lpszClassName, _T("Desktop Organizer"), WS_OVERLAPPEDWINDOW, 100, 100, 800, 600, NULL, NULL, wc.hInstance, NULL);

    if (!CreateDeviceD3D(g_hWnd)) {
        CleanupDeviceD3D();
        UnregisterClass(wc.lpszClassName, wc.hInstance);
        return 1;
    }

    ShowWindow(g_hWnd, SW_SHOWDEFAULT);
    UpdateWindow(g_hWnd);

    IMGUI_CHECKVERSION();
    ImGui::CreateContext();
    ImGuiIO& io = ImGui::GetIO(); (void)io;
    ImGui::StyleColorsDark();
    ImGui_ImplWin32_Init(g_hWnd);
    ImGui_ImplDX11_Init(g_pd3dDevice, g_pd3dDeviceContext);

    MSG msg;
    ZeroMemory(&msg, sizeof(msg));
    while (msg.message != WM_QUIT) {
        if (PeekMessage(&msg, NULL, 0U, 0U, PM_REMOVE)) {
            TranslateMessage(&msg);
            DispatchMessage(&msg);
            continue;
        }
        RenderImGui();
        g_pSwapChain->Present(1, 0);
    }

    ImGui_ImplDX11_Shutdown();
    ImGui_ImplWin32_Shutdown();
    ImGui::DestroyContext();
    CleanupDeviceD3D();
    UnregisterClass(wc.lpszClassName, wc.hInstance);

    return 0;
}

// Windows Message Handler
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) {
    if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam))
        return true;

    switch (msg) {
    case WM_SIZE:
        if (g_pd3dDevice != NULL && wParam != SIZE_MINIMIZED) {
            CleanupDeviceD3D();
            CreateDeviceD3D(hWnd);
        }
        return 0;
    case WM_DESTROY:
        PostQuitMessage(0);
        return 0;
    }
    return DefWindowProc(hWnd, msg, wParam, lParam);
}

@PathogenDavid
Copy link
Contributor

You did not actually copy it, you marked it as extern "C" which is incorrect.

Also you really shouldn't rely on ChatGPT when you're starting out and can't judge the quality of its responses. It doesn't actually understand anything it's saying and will just create confusion.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants