#include "Windows/WindowsWindow.h"
#include "Windows/WindowsInput.h"
#include "Logging/LogMacros.h"
#include "D3D11Device.h"
#include "imgui.h"
WNDCLASS FWindowsWindow::WindowClass = {};
extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
if (ImGui_ImplWin32_WndProcHandler(hwnd, uMsg, wParam, lParam))
{
return true;
}
switch (uMsg)
{
case WM_SIZE:
{
if (FD3D11Device::GetDevice()->GetID3D11Device() != nullptr && wParam != SIZE_MINIMIZED)
{
FD3D11RenderTarget::GetRenderTarget()->CleanupRenderTarget();
FD3D11Device::GetDevice()->GetIDXGISwapChain()->ResizeBuffers(0, (UINT)LOWORD(lParam), (UINT)HIWORD(lParam), DXGI_FORMAT_UNKNOWN, 0);
FD3D11RenderTarget::CreateRenderTarget(FD3D11Device::GetDevice()->GetID3D11Device());
}
return 0;
}
case WM_SYSCOMMAND:
{
if ((wParam & 0xfff0) == SC_KEYMENU)
{
return 0;
}
break;
}
case WM_DESTROY:
{
PostQuitMessage(0);
return 0;
}
case WM_DPICHANGED:
{
if (ImGui::GetIO().ConfigFlags & ImGuiConfigFlags_DpiEnableScaleViewports)
{
const RECT* SuggestedRect = (RECT*)lParam;
SetWindowPos(hwnd, NULL, SuggestedRect->left, SuggestedRect->top, SuggestedRect->right - SuggestedRect->left, SuggestedRect->bottom - SuggestedRect->top, SWP_NOZORDER | SWP_NOACTIVATE);
}
break;
}
}
return DefWindowProc(hwnd, uMsg, wParam, lParam);
}
std::unique_ptr FWindowsWindow::Create()
{
return std::make_unique();
}
void FWindowsWindow::Initialize(HINSTANCE InHInstance, HINSTANCE InHPrevInstance, const bool bShowImmediately)
{
WindowClass.lpfnWndProc = WindowProc;
WindowClass.hInstance = InHInstance;
WindowClass.lpszClassName = "FrostWindow";
WindowClass.hCursor = LoadCursor(InHInstance, IDC_ARROW);
RegisterClass(&WindowClass);
RECT AvailableArea;
SystemParametersInfo(SPI_GETWORKAREA, 0, &AvailableArea, 0);
ScreenWidth = AvailableArea.right - AvailableArea.left;
ScreenHeight = AvailableArea.bottom - AvailableArea.top;
WindowWidth = 1280;
WindowHeight = 720;
Hwnd = CreateWindowEx(
0,
"FrostWindow",
"Frost Game - Scene - Windows, Mac & Linux - Frost Editor 2023.1.0 ",
WS_POPUP | WS_MAXIMIZEBOX,
bIsWindowMaximized ? AvailableArea.left : (ScreenWidth - WindowWidth) / 2,
bIsWindowMaximized ? AvailableArea.top : (ScreenHeight - WindowHeight) / 2,
bIsWindowMaximized ? ScreenWidth : WindowWidth,
bIsWindowMaximized ? ScreenHeight : WindowHeight,
NULL,
NULL,
InHInstance,
NULL);
ShowWindow(Hwnd, bShowImmediately);
UpdateWindow(Hwnd);
ShowWindow(Hwnd, bIsWindowMaximized ? SW_MAXIMIZE : SW_SHOWMAXIMIZED);
SetWindowPos(Hwnd, NULL, 0, 0, WindowWidth, WindowHeight, SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
FD3D11Device::CreateDevice(Hwnd);
}
void FWindowsWindow::Start()
{
Input = std::make_unique(Hwnd);
}
void FWindowsWindow::Update()
{
Input->Update();
FD3D11Device::GetDevice()->GetIDXGISwapChain()->Present(1, 0);
}
void FWindowsWindow::Shutdown()
{
FD3D11Device::GetDevice()->CleanupDevice();
DestroyWindow(Hwnd);
UnregisterClass(WindowClass.lpszClassName, WindowClass.hInstance);
}
void FWindowsWindow::SetWindowMinimized()
{
ShowWindow(Hwnd, SW_MINIMIZE);
}
void FWindowsWindow::SetWindowMaximized(bool bInShouldMaximize)
{
if (bInShouldMaximize)
{
SetWindowLong(Hwnd, GWL_STYLE, WS_POPUP | WS_MAXIMIZEBOX);
bIsWindowMaximized = true;
}
else
{
ShowWindow(Hwnd, SW_RESTORE);
bIsWindowMaximized = false;
}
ShowWindow(Hwnd, true);
}
void FWindowsWindow::SetWindowFullscreen(bool bInShouldFullscreen)
{
if (bInShouldFullscreen)
{
SetWindowLong(Hwnd, GWL_STYLE, WS_POPUP | WS_MAXIMIZE);
bIsWindowFullscreen = true;
}
else
{
SetWindowLong(Hwnd, GWL_STYLE, WS_POPUP | WS_MAXIMIZEBOX);
bIsWindowFullscreen = false;
}
ShowWindow(Hwnd, true);
}
int FWindowsWindow::GetWindowX()
{
return WindowRect.left;
}
int FWindowsWindow::GetWindowY()
{
return WindowRect.top;
}
bool FWindowsWindow::IsWindowMaximized()
{
return bIsWindowMaximized;
}
bool FWindowsWindow::IsWindowFullscreen()
{
return bIsWindowFullscreen;
}
int FWindowsWindow::GetWindowWidth()
{
return WindowWidth;
}
int FWindowsWindow::GetWindowHeight()
{
return WindowHeight;
}
std::unique_ptr& FWindowsWindow::GetInput()
{
return Input;
}
HWND FWindowsWindow::GetHwnd()
{
if (Hwnd)
{
return Hwnd;
}
else
{
FROST_LOG_ERROR("Failed to retrieve 'Hwnd'!");
return nullptr;
}
}