#if !defined(DN_OS_W32_H) #define DN_OS_W32_H #if defined(_CLANGD) #define DN_H_WITH_OS 1 #include "../dn.h" #include "dn_os_windows.h" #endif typedef enum DN_OSW32DllLoadFunctionsResult { DN_OSW32DllLoadFunctionsResult_Ok, DN_OSW32DllLoadFunctionsResult_LoadLibraryFailed, DN_OSW32DllLoadFunctionsResult_FunctionMissing, } DN_OSW32DllLoadFunctionsResult; typedef struct DN_OSW32DllFunction DN_OSW32DllLoadFunction; struct DN_OSW32DllFunction { DN_Str8 name; void *func_ptr; }; typedef struct DN_OSW32DllCore DN_OSW32DllCore; struct DN_OSW32DllCore { void* handle; DN_OSW32DllFunction* functions; DN_USize functions_count; }; typedef struct DN_OSW32Error DN_OSW32Error; struct DN_OSW32Error { unsigned long code; DN_Str8 msg; }; typedef struct DN_OSW32FolderIteratorW DN_OSW32FolderIteratorW; struct DN_OSW32FolderIteratorW { void *handle; DN_Str16 file_name; wchar_t file_name_buf[512]; }; typedef struct DN_OSW32Window DN_OSW32Window; struct DN_OSW32Window { HWND hwnd; // NOTE: For windows with custom title bars, this should be the rect in framebuffer units that // when the mouse is down will move the window, or if the mouse is double-clicked then toggle the // maximisation of the window. This rect should not include any custom drawn menu buttons so that // those buttons can be handled by your application. DN_Rect custom_title_bar_rect_that_is_draggable; bool custom_title_bar; DN_OSW32Window *next; }; typedef enum DN_OSW32SyncPrimitiveType { DN_OSW32SyncPrimitiveType_Semaphore, DN_OSW32SyncPrimitiveType_Mutex, DN_OSW32SyncPrimitiveType_ConditionVariable, DN_OSW32SyncPrimitiveType_Barrier, } DN_OSW32SyncPrimitiveType; typedef struct DN_OSW32SyncPrimitive DN_OSW32SyncPrimitive; struct DN_OSW32SyncPrimitive { union { void *sem; CRITICAL_SECTION mutex; CONDITION_VARIABLE cv; SYNCHRONIZATION_BARRIER barrier; }; DN_OSW32SyncPrimitive *next; }; typedef HRESULT DN_OSW32SetThreadDescriptionFunc (HANDLE hThread, PWSTR const lpThreadDescription); typedef BOOL DN_OSW32SetProcessDpiAwarenessContextFunc(void* value); typedef UINT DN_OSW32GetDpiForWindowFunc (HWND hwnd); typedef HRESULT DN_OSW32GetDpiForMonitorFunc (HMONITOR hmonitor, MONITOR_DPI_TYPE dpiType, UINT *dpiX, UINT *dpiY); typedef int DN_OSW32GetSystemMetricsForDpiFunc (int nIndex, UINT dpi); #define DN_OSW32DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2 ((void*)-4) typedef struct DN_OSW32Core DN_OSW32Core; struct DN_OSW32Core { // NOTE: These functions are dynamically loaded because they might not be present on the user's // machine. For example the GetDpiForWindow is Windows 10+ only. DN_OSW32SetThreadDescriptionFunc *set_thread_description; DN_OSW32GetDpiForWindowFunc *get_dpi_for_window; DN_OSW32GetDpiForMonitorFunc *get_dpi_for_monitor; DN_OSW32GetSystemMetricsForDpiFunc *get_system_metrics_for_dpi; LARGE_INTEGER qpc_frequency; void* bcrypt_rng_handle; bool bcrypt_init_success; bool sym_initialised; CRITICAL_SECTION sync_primitive_free_list_mutex; DN_OSW32SyncPrimitive* sync_primitive_free_list; DN_OSW32Window* windows; WNDPROC fallback_wnd_proc; }; //////////////////////////////////////////////////////////////////////////////////////////////////// // NOTE: DN Win32 book-keeping DN_API void DN_OS_W32Init (DN_OSW32Core *w32); DN_API DN_OSW32Core* DN_OS_W32GetCore (); DN_API DN_OSW32Window* DN_OS_W32WindowFromHwndMaybeAlloc(DN_OSW32Core *w32, HWND hwnd, DN_Arena *arena); //////////////////////////////////////////////////////////////////////////////////////////////////// // NOTE: Process management DN_API void DN_OS_W32ThreadSetName (DN_Str8 name); DN_API LRESULT __stdcall DN_OS_W32WindowProcCustomTitlebar(HWND hwnd, UINT msg, WPARAM w_param, LPARAM l_param); DN_API void DN_OS_W32MakeProcessDPIAware (); //////////////////////////////////////////////////////////////////////////////////////////////////// // NOTE: DLL DN_API void DN_OS_W32DllUnload (DN_OSW32DllCore *dll); DN_API DN_OSW32DllLoadFunctionsResult DN_OS_W32DllLoadFunctions (DN_OSW32DllCore *dll, DN_Str8 dll_path); //////////////////////////////////////////////////////////////////////////////////////////////////// // NOTE: Errors DN_API DN_Str16 DN_OS_W32ErrorCodeToMsg16Alloc (DN_U32 error_code); DN_API DN_OSW32Error DN_OS_W32ErrorCodeToMsg (DN_Arena *arena, DN_U32 error_code); DN_API DN_OSW32Error DN_OS_W32ErrorCodeToMsgAlloc (DN_U32 error_code); DN_API DN_OSW32Error DN_OS_W32LastError (DN_Arena *arena); DN_API DN_OSW32Error DN_OS_W32LastErrorAlloc (); //////////////////////////////////////////////////////////////////////////////////////////////////// // NOTE: Windows Str8 <-> Str16 DN_API DN_Str16 DN_OS_W32Str8ToStr16 (DN_Arena *arena, DN_Str8 src); DN_API int DN_OS_W32Str8ToStr16Buffer (DN_Str16 src, char *dest, int dest_size); DN_API DN_Str8 DN_OS_W32Str16ToStr8 (DN_Arena *arena, DN_Str16 src); DN_API int DN_OS_W32Str16ToStr8Buffer (DN_Str16 src, char *dest, int dest_size); DN_API DN_Str8 DN_OS_W32Str16ToStr8FromHeap (DN_Str16 src); //////////////////////////////////////////////////////////////////////////////////////////////////// // NOTE: Path navigation DN_API DN_Str16 DN_OS_W32ExePathW (DN_Arena *arena); DN_API DN_Str16 DN_OS_W32ExeDirW (DN_Arena *arena); DN_API DN_Str8 DN_OS_W32WorkingDir (DN_Arena *arena, DN_Str8 suffix); DN_API DN_Str16 DN_OS_W32WorkingDirW (DN_Arena *arena, DN_Str16 suffix); DN_API bool DN_OS_W32DirWIterate (DN_Str16 path, DN_OSW32FolderIteratorW *it); #endif // !defined(DN_OS_W32_H)