Skip to content

Commit 902d2b4

Browse files
committed
Merge pull request godotengine#106400 from RandomShaper/win_compat
Improve platform compatibility of Windows and Direct3D 12
2 parents e625565 + 8203808 commit 902d2b4

File tree

10 files changed

+44
-1
lines changed

10 files changed

+44
-1
lines changed

core/os/os.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -365,9 +365,11 @@ class OS {
365365
// This is invoked by the GDExtensionManager after loading GDExtensions specified by the project.
366366
virtual void load_platform_gdextensions() const {}
367367

368+
#ifdef TOOLS_ENABLED
368369
// Tests OpenGL context and Rendering Device simultaneous creation. This function is expected to crash on some NVIDIA drivers.
369370
virtual bool _test_create_rendering_device_and_gl(const String &p_display_driver) const { return true; }
370371
virtual bool _test_create_rendering_device(const String &p_display_driver) const { return true; }
372+
#endif
371373

372374
OS();
373375
virtual ~OS();

drivers/d3d12/SCsub

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,12 @@ if env["use_pix"]:
4141
env_d3d12_rdd.Append(CPPEXTPATH=[env["pix_path"] + "/Include"])
4242

4343

44+
# Direct composition.
45+
46+
if "dcomp" in env.get("supported", []):
47+
env_d3d12_rdd.Append(CPPDEFINES=["DCOMP_ENABLED"])
48+
49+
4450
# Mesa (SPIR-V to DXIL functionality).
4551

4652
mesa_libs = env["mesa_libs"]

drivers/d3d12/rendering_context_driver_d3d12.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,9 +78,11 @@ RenderingContextDriverD3D12::~RenderingContextDriverD3D12() {
7878
if (lib_dxgi) {
7979
FreeLibrary(lib_dxgi);
8080
}
81+
#ifdef DCOMP_ENABLED
8182
if (lib_dcomp) {
8283
FreeLibrary(lib_dcomp);
8384
}
85+
#endif
8486
}
8587

8688
Error RenderingContextDriverD3D12::_init_device_factory() {
@@ -93,8 +95,10 @@ Error RenderingContextDriverD3D12::_init_device_factory() {
9395
lib_dxgi = LoadLibraryW(L"DXGI.dll");
9496
ERR_FAIL_NULL_V(lib_dxgi, ERR_CANT_CREATE);
9597

98+
#ifdef DCOMP_ENABLED
9699
lib_dcomp = LoadLibraryW(L"Dcomp.dll");
97100
ERR_FAIL_NULL_V(lib_dcomp, ERR_CANT_CREATE);
101+
#endif
98102

99103
// Note: symbol is not available in MinGW import library.
100104
PFN_D3D12_GET_INTERFACE d3d_D3D12GetInterface = (PFN_D3D12_GET_INTERFACE)(void *)GetProcAddress(lib_d3d12, "D3D12GetInterface");

drivers/d3d12/rendering_context_driver_d3d12.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@
4141
#undef AS
4242
#endif
4343

44+
#ifdef DCOMP_ENABLED
4445
#if (WINVER < _WIN32_WINNT_WIN8) && defined(_MSC_VER)
4546
#pragma push_macro("NTDDI_VERSION")
4647
#pragma push_macro("WINVER")
@@ -54,6 +55,7 @@
5455
#else
5556
#include <dcomp.h>
5657
#endif
58+
#endif
5759

5860
#include <d3dx12.h>
5961
#include <dxgi1_6.h>
@@ -104,14 +106,18 @@ class RenderingContextDriverD3D12 : public RenderingContextDriver {
104106
uint32_t height = 0;
105107
DisplayServer::VSyncMode vsync_mode = DisplayServer::VSYNC_ENABLED;
106108
bool needs_resize = false;
109+
#ifdef DCOMP_ENABLED
107110
ComPtr<IDCompositionDevice> composition_device;
108111
ComPtr<IDCompositionTarget> composition_target;
109112
ComPtr<IDCompositionVisual> composition_visual;
113+
#endif
110114
};
111115

112116
HMODULE lib_d3d12 = nullptr;
113117
HMODULE lib_dxgi = nullptr;
118+
#ifdef DCOMP_ENABLED
114119
HMODULE lib_dcomp = nullptr;
120+
#endif
115121

116122
IDXGIAdapter1 *create_adapter(uint32_t p_adapter_index) const;
117123
ID3D12DeviceFactory *device_factory_get() const;

drivers/d3d12/rendering_device_driver_d3d12.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2609,7 +2609,16 @@ Error RenderingDeviceDriverD3D12::swap_chain_resize(CommandQueueID p_cmd_queue,
26092609
swap_chain_desc.Height = surface->height;
26102610

26112611
ComPtr<IDXGISwapChain1> swap_chain_1;
2612+
#ifdef DCOMP_ENABLED
26122613
res = context_driver->dxgi_factory_get()->CreateSwapChainForComposition(command_queue->d3d_queue.Get(), &swap_chain_desc, nullptr, swap_chain_1.GetAddressOf());
2614+
#else
2615+
res = context_driver->dxgi_factory_get()->CreateSwapChainForHwnd(command_queue->d3d_queue.Get(), surface->hwnd, &swap_chain_desc, nullptr, nullptr, swap_chain_1.GetAddressOf());
2616+
if (!SUCCEEDED(res) && swap_chain_desc.AlphaMode != DXGI_ALPHA_MODE_IGNORE) {
2617+
swap_chain_desc.AlphaMode = DXGI_ALPHA_MODE_IGNORE;
2618+
has_comp_alpha[(uint64_t)p_cmd_queue.id] = false;
2619+
res = context_driver->dxgi_factory_get()->CreateSwapChainForHwnd(command_queue->d3d_queue.Get(), surface->hwnd, &swap_chain_desc, nullptr, nullptr, swap_chain_1.GetAddressOf());
2620+
}
2621+
#endif
26132622
ERR_FAIL_COND_V(!SUCCEEDED(res), ERR_CANT_CREATE);
26142623

26152624
swap_chain_1.As(&swap_chain->d3d_swap_chain);
@@ -2619,6 +2628,7 @@ Error RenderingDeviceDriverD3D12::swap_chain_resize(CommandQueueID p_cmd_queue,
26192628
ERR_FAIL_COND_V(!SUCCEEDED(res), ERR_CANT_CREATE);
26202629
}
26212630

2631+
#ifdef DCOMP_ENABLED
26222632
if (surface->composition_device.Get() == nullptr) {
26232633
using PFN_DCompositionCreateDevice = HRESULT(WINAPI *)(IDXGIDevice *, REFIID, void **);
26242634
PFN_DCompositionCreateDevice pfn_DCompositionCreateDevice = (PFN_DCompositionCreateDevice)(void *)GetProcAddress(context_driver->lib_dcomp, "DCompositionCreateDevice");
@@ -2648,6 +2658,7 @@ Error RenderingDeviceDriverD3D12::swap_chain_resize(CommandQueueID p_cmd_queue,
26482658
res = surface->composition_device->Commit();
26492659
ERR_FAIL_COND_V(!SUCCEEDED(res), ERR_CANT_CREATE);
26502660
}
2661+
#endif
26512662

26522663
res = swap_chain->d3d_swap_chain->GetDesc1(&swap_chain_desc);
26532664
ERR_FAIL_COND_V(!SUCCEEDED(res), ERR_CANT_CREATE);

platform/linuxbsd/os_linuxbsd.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1197,6 +1197,7 @@ String OS_LinuxBSD::get_system_ca_certificates() {
11971197
return f->get_as_text();
11981198
}
11991199

1200+
#ifdef TOOLS_ENABLED
12001201
bool OS_LinuxBSD::_test_create_rendering_device(const String &p_display_driver) const {
12011202
// Tests Rendering Device creation.
12021203

@@ -1263,6 +1264,7 @@ bool OS_LinuxBSD::_test_create_rendering_device_and_gl(const String &p_display_d
12631264
#endif
12641265
return _test_create_rendering_device(p_display_driver);
12651266
}
1267+
#endif
12661268

12671269
OS_LinuxBSD::OS_LinuxBSD() {
12681270
main_loop = nullptr;

platform/linuxbsd/os_linuxbsd.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -137,8 +137,10 @@ class OS_LinuxBSD : public OS_Unix {
137137

138138
virtual String get_system_ca_certificates() override;
139139

140+
#ifdef TOOLS_ENABLED
140141
virtual bool _test_create_rendering_device_and_gl(const String &p_display_driver) const override;
141142
virtual bool _test_create_rendering_device(const String &p_display_driver) const override;
143+
#endif
142144

143145
OS_LinuxBSD();
144146
~OS_LinuxBSD();

platform/windows/detect.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -241,7 +241,7 @@ def get_flags():
241241

242242
return {
243243
"arch": arch,
244-
"supported": ["d3d12", "mono", "xaudio2"],
244+
"supported": ["d3d12", "dcomp", "mono", "xaudio2"],
245245
}
246246

247247

platform/windows/os_windows.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -281,6 +281,7 @@ void OS_Windows::initialize() {
281281
QueryPerformanceFrequency((LARGE_INTEGER *)&ticks_per_second);
282282
QueryPerformanceCounter((LARGE_INTEGER *)&ticks_start);
283283

284+
#if WINAPI_FAMILY == WINAPI_FAMILY_DESKTOP_APP
284285
// set minimum resolution for periodic timers, otherwise Sleep(n) may wait at least as
285286
// long as the windows scheduler resolution (~16-30ms) even for calls like Sleep(1)
286287
TIMECAPS time_caps;
@@ -292,6 +293,9 @@ void OS_Windows::initialize() {
292293
delay_resolution = 1000;
293294
timeBeginPeriod(1);
294295
}
296+
#else
297+
delay_resolution = 1000;
298+
#endif
295299

296300
process_map = memnew((HashMap<ProcessID, ProcessInfo>));
297301

@@ -374,7 +378,9 @@ void OS_Windows::finalize_core() {
374378

375379
FileAccessWindows::finalize();
376380

381+
#if WINAPI_FAMILY == WINAPI_FAMILY_DESKTOP_APP
377382
timeEndPeriod(1);
383+
#endif
378384

379385
memdelete(process_map);
380386
NetSocketWinSock::cleanup();
@@ -2564,6 +2570,7 @@ void OS_Windows::add_frame_delay(bool p_can_draw) {
25642570
}
25652571
}
25662572

2573+
#ifdef TOOLS_ENABLED
25672574
bool OS_Windows::_test_create_rendering_device(const String &p_display_driver) const {
25682575
// Tests Rendering Device creation.
25692576

@@ -2656,6 +2663,7 @@ bool OS_Windows::_test_create_rendering_device_and_gl(const String &p_display_dr
26562663
UnregisterClassW(L"Engine probe window", GetModuleHandle(nullptr));
26572664
return ok;
26582665
}
2666+
#endif
26592667

26602668
OS_Windows::OS_Windows(HINSTANCE _hInstance) {
26612669
hInstance = _hInstance;

platform/windows/os_windows.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -257,8 +257,10 @@ class OS_Windows : public OS {
257257

258258
void set_main_window(HWND p_main_window) { main_window = p_main_window; }
259259

260+
#ifdef TOOLS_ENABLED
260261
virtual bool _test_create_rendering_device_and_gl(const String &p_display_driver) const override;
261262
virtual bool _test_create_rendering_device(const String &p_display_driver) const override;
263+
#endif
262264

263265
HINSTANCE get_hinstance() { return hInstance; }
264266
OS_Windows(HINSTANCE _hInstance);

0 commit comments

Comments
 (0)