diff --git a/Makefile.common b/Makefile.common index d8f78db89b..b183da5e5f 100644 --- a/Makefile.common +++ b/Makefile.common @@ -1269,7 +1269,7 @@ endif ifeq ($(HAVE_D3D12), 1) OBJ += gfx/drivers/d3d12.o gfx/common/d3d12_common.o \ - gfx/drivers_font/d3d12_font.o + gfx/drivers_font/d3d12_font.o menu/drivers_display/menu_display_d3d12.o DEFINES += -DHAVE_D3D12 endif diff --git a/Makefile.msvc b/Makefile.msvc index 7760279670..77d02fc9fa 100644 --- a/Makefile.msvc +++ b/Makefile.msvc @@ -55,6 +55,7 @@ HAVE_LANGEXTRA := 1 HAVE_CHEEVOS := 1 HAVE_KEYMAPPER := 1 HAVE_SHADERPIPELINE := 1 +HAVE_IMAGEVIEWER := 1 include Makefile.common INCLUDE_DIRS := $(patsubst -isystem%,-I%,$(INCLUDE_DIRS)) diff --git a/gfx/common/d3d12_common.h b/gfx/common/d3d12_common.h index eb320e3ba3..936d50ff77 100644 --- a/gfx/common/d3d12_common.h +++ b/gfx/common/d3d12_common.h @@ -1311,7 +1311,27 @@ typedef struct bool dirty; } d3d12_texture_t; -#define TEXTURE_DESC_SLOTS_COUNT 128 +#ifndef ALIGN +#ifdef _MSC_VER +#define ALIGN(x) __declspec(align(x)) +#else +#define ALIGN(x) __attribute__((aligned(x))) +#endif +#endif + +typedef struct ALIGN(16) +{ + math_matrix_4x4 mvp; + struct + { + float width; + float height; + } OutputSize; + float time; +} d3d12_uniform_t; + +static_assert( + (!(sizeof(d3d12_uniform_t) & 0xF)), "sizeof(d3d12_uniform_t) must be a multiple of 16"); typedef struct { @@ -1386,6 +1406,7 @@ typedef struct } sprites; D3D12PipelineState pipes[GFX_MAX_SHADERS]; + d3d12_uniform_t ubo_values; D3D12Resource ubo; D3D12_CONSTANT_BUFFER_VIEW_DESC ubo_view; DXGI_FORMAT format; @@ -1395,6 +1416,8 @@ typedef struct bool resize_chain; bool keep_aspect; bool resize_viewport; + D3D12Resource menu_pipeline_vbo; + D3D12_VERTEX_BUFFER_VIEW menu_pipeline_vbo_view; #ifdef DEBUG D3D12Debug debugController; diff --git a/gfx/drivers/d3d12.c b/gfx/drivers/d3d12.c index 87f866747c..3798c29890 100644 --- a/gfx/drivers/d3d12.c +++ b/gfx/drivers/d3d12.c @@ -26,11 +26,13 @@ #include "../common/d3d12_common.h" #include "../common/d3dcompiler_common.h" -//#include "../../menu/menu_driver.h" +#include "../../menu/menu_driver.h" #include "../../driver.h" #include "../../verbosity.h" #include "../../configuration.h" +#include "wiiu/wiiu_dbg.h" + static void d3d12_set_filtering(void* data, unsigned index, bool smooth) { int i; @@ -71,10 +73,10 @@ static void d3d12_update_viewport(void* data, bool force_full) video_driver_update_viewport(&d3d12->vp, force_full, d3d12->keep_aspect); - d3d12->frame.viewport.TopLeftX = (float)d3d12->vp.x; - d3d12->frame.viewport.TopLeftY = (float)d3d12->vp.y; - d3d12->frame.viewport.Width = (float)d3d12->vp.width; - d3d12->frame.viewport.Height = (float)d3d12->vp.height; + d3d12->frame.viewport.TopLeftX = d3d12->vp.x; + d3d12->frame.viewport.TopLeftY = d3d12->vp.y; + d3d12->frame.viewport.Width = d3d12->vp.width; + d3d12->frame.viewport.Height = d3d12->vp.height; d3d12->frame.viewport.MaxDepth = 0.0f; d3d12->frame.viewport.MaxDepth = 1.0f; @@ -160,6 +162,7 @@ static bool d3d12_gfx_init_pipelines(d3d12_video_t* d3d12) if (!d3d_compile(shader, sizeof(shader), NULL, "GSMain", "gs_5_0", &gs_code)) goto error; + // desc.BlendState.RenderTarget[0].BlendEnable = false; desc.PrimitiveTopologyType = D3D12_PRIMITIVE_TOPOLOGY_TYPE_POINT; desc.InputLayout.pInputElementDescs = inputElementDesc; desc.InputLayout.NumElements = countof(inputElementDesc); @@ -301,9 +304,9 @@ static bool d3d12_gfx_init_pipelines(d3d12_video_t* d3d12) vs_code = NULL; ps_code = NULL; - if (!d3d_compile(ribbon_simple, sizeof(ribbon), NULL, "VSMain", "vs_5_0", &vs_code)) + if (!d3d_compile(ribbon_simple, sizeof(ribbon_simple), NULL, "VSMain", "vs_5_0", &vs_code)) goto error; - if (!d3d_compile(ribbon_simple, sizeof(ribbon), NULL, "PSMain", "ps_5_0", &ps_code)) + if (!d3d_compile(ribbon_simple, sizeof(ribbon_simple), NULL, "PSMain", "ps_5_0", &ps_code)) goto error; if (!d3d12_init_pipeline( @@ -383,6 +386,8 @@ static void* d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** input_data) { WNDCLASSEX wndclass = { 0 }; + MONITORINFOEX current_mon; + HMONITOR hm_to_use; settings_t* settings = config_get_ptr(); d3d12_video_t* d3d12 = (d3d12_video_t*)calloc(1, sizeof(*d3d12)); @@ -394,7 +399,17 @@ d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** i wndclass.lpfnWndProc = WndProcD3D; win32_window_init(&wndclass, true, NULL); - if (!win32_set_video_mode(d3d12, video->width, video->height, video->fullscreen)) + win32_monitor_info(¤t_mon, &hm_to_use, &d3d12->cur_mon_id); + + d3d12->vp.full_width = video->width; + d3d12->vp.full_height = video->height; + + if (!d3d12->vp.full_width) + d3d12->vp.full_width = current_mon.rcMonitor.right - current_mon.rcMonitor.left; + if (!d3d12->vp.full_height) + d3d12->vp.full_height = current_mon.rcMonitor.bottom - current_mon.rcMonitor.top; + + if (!win32_set_video_mode(d3d12, d3d12->vp.full_width, d3d12->vp.full_height, video->fullscreen)) { RARCH_ERR("[D3D12]: win32_set_video_mode failed.\n"); goto error; @@ -414,7 +429,7 @@ d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** i if (!d3d12_init_queue(d3d12)) goto error; - if (!d3d12_init_swapchain(d3d12, video->width, video->height, main_window.hwnd)) + if (!d3d12_init_swapchain(d3d12, d3d12->vp.full_width, d3d12->vp.full_height, main_window.hwnd)) goto error; d3d12_init_samplers(d3d12); @@ -429,21 +444,20 @@ d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** i d3d12->sprites.vbo_view.BufferLocation = d3d12_create_buffer( d3d12->device, d3d12->sprites.vbo_view.SizeInBytes, &d3d12->sprites.vbo); - d3d12->keep_aspect = video->force_aspect; - d3d12->chain.vsync = video->vsync; - d3d12->format = video->rgb32 ? DXGI_FORMAT_B8G8R8X8_UNORM : DXGI_FORMAT_B5G6R5_UNORM; - d3d12->frame.texture.desc.Format = d3d12->format; - - d3d12->ubo_view.SizeInBytes = sizeof(math_matrix_4x4); + d3d12->ubo_view.SizeInBytes = sizeof(d3d12_uniform_t); d3d12->ubo_view.BufferLocation = d3d12_create_buffer(d3d12->device, d3d12->ubo_view.SizeInBytes, &d3d12->ubo); - d3d12->frame.ubo_view.SizeInBytes = sizeof(math_matrix_4x4); + d3d12->frame.ubo_view.SizeInBytes = sizeof(d3d12_uniform_t); d3d12->frame.ubo_view.BufferLocation = d3d12_create_buffer(d3d12->device, d3d12->frame.ubo_view.SizeInBytes, &d3d12->frame.ubo); matrix_4x4_ortho(d3d12->mvp_no_rot, 0.0f, 1.0f, 0.0f, 1.0f, -1.0f, 1.0f); + d3d12->ubo_values.mvp = d3d12->mvp_no_rot; + d3d12->ubo_values.OutputSize.width = d3d12->chain.viewport.Width; + d3d12->ubo_values.OutputSize.height = d3d12->chain.viewport.Height; + { math_matrix_4x4* mvp; D3D12_RANGE read_range = { 0, 0 }; @@ -453,9 +467,14 @@ d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** i } d3d12_gfx_set_rotation(d3d12, 0); - d3d12->vp.full_width = video->width; - d3d12->vp.full_height = video->height; - d3d12->resize_viewport = true; + video_driver_set_size(&d3d12->vp.full_width, &d3d12->vp.full_height); + d3d12->chain.viewport.Width = d3d12->vp.full_width; + d3d12->chain.viewport.Height = d3d12->vp.full_height; + d3d12->resize_viewport = true; + d3d12->keep_aspect = video->force_aspect; + d3d12->chain.vsync = video->vsync; + d3d12->format = video->rgb32 ? DXGI_FORMAT_B8G8R8X8_UNORM : DXGI_FORMAT_B5G6R5_UNORM; + d3d12->frame.texture.desc.Format = d3d12->format; font_driver_init_osd(d3d12, false, video->is_threaded, FONT_DRIVER_RENDER_D3D12_API); @@ -496,8 +515,18 @@ static bool d3d12_gfx_frame( } d3d12->chain.frame_index = DXGIGetCurrentBackBufferIndex(d3d12->chain.handle); - d3d12->resize_chain = false; - d3d12->resize_viewport = true; + + d3d12->chain.viewport.Width = video_info->width; + d3d12->chain.viewport.Height = video_info->height; + d3d12->chain.scissorRect.right = video_info->width; + d3d12->chain.scissorRect.bottom = video_info->height; + d3d12->resize_chain = false; + d3d12->resize_viewport = true; + + d3d12->ubo_values.OutputSize.width = d3d12->chain.viewport.Width; + d3d12->ubo_values.OutputSize.height = d3d12->chain.viewport.Height; + + video_driver_set_size(&video_info->width, &video_info->height); } PERF_START(); @@ -578,7 +607,7 @@ static bool d3d12_gfx_frame( D3D12IASetVertexBuffers(d3d12->queue.cmd, 0, 1, &d3d12->sprites.vbo_view); d3d12->sprites.enabled = true; -#if 0 +#if 1 if (d3d12->menu.enabled) menu_driver_frame(video_info); #endif @@ -589,7 +618,6 @@ static bool d3d12_gfx_frame( } d3d12->sprites.enabled = false; - d3d12_resource_transition( d3d12->queue.cmd, d3d12->chain.renderTargets[d3d12->chain.frame_index], D3D12_RESOURCE_STATE_RENDER_TARGET, D3D12_RESOURCE_STATE_PRESENT); @@ -759,11 +787,64 @@ static void d3d12_gfx_set_osd_msg( } } +static uintptr_t d3d12_gfx_load_texture( + void* video_data, void* data, bool threaded, enum texture_filter_type filter_type) +{ + d3d12_texture_t* texture = NULL; + d3d12_video_t* d3d12 = (d3d12_video_t*)video_data; + struct texture_image* image = (struct texture_image*)data; + + if (!d3d12) + return 0; + + texture = (d3d12_texture_t*)calloc(1, sizeof(*texture)); + + if (!texture) + return 0; + + /* todo : mipmapping */ + switch (filter_type) + { + case TEXTURE_FILTER_MIPMAP_LINEAR: + /* fallthrough */ + case TEXTURE_FILTER_LINEAR: + texture->sampler = d3d12->samplers[RARCH_FILTER_LINEAR][RARCH_WRAP_DEFAULT]; + break; + case TEXTURE_FILTER_MIPMAP_NEAREST: + /* fallthrough */ + case TEXTURE_FILTER_NEAREST: + texture->sampler = d3d12->samplers[RARCH_FILTER_NEAREST][RARCH_WRAP_DEFAULT]; + break; + } + + texture->desc.Width = image->width; + texture->desc.Height = image->height; + texture->desc.Format = DXGI_FORMAT_B8G8R8A8_UNORM; + texture->srv_heap = &d3d12->desc.srv_heap; + + d3d12_init_texture(d3d12->device, texture); + + d3d12_update_texture( + image->width, image->height, 0, DXGI_FORMAT_B8G8R8A8_UNORM, image->pixels, texture); + + return (uintptr_t)texture; +} +static void d3d12_gfx_unload_texture(void* data, uintptr_t handle) +{ + d3d12_texture_t* texture = (d3d12_texture_t*)handle; + + if (!texture) + return; + + d3d12_release_texture(texture); + free(texture); +} + static const video_poke_interface_t d3d12_poke_interface = { NULL, /* set_coords */ NULL, /* set_mvp */ - NULL, /* load_texture */ - NULL, /* unload_texture */ + d3d12_gfx_load_texture, + d3d12_gfx_unload_texture, NULL, /* set_video_mode */ d3d12_set_filtering, NULL, /* get_video_output_size */ diff --git a/griffin/griffin.c b/griffin/griffin.c index 30d21c4f35..602764cf15 100644 --- a/griffin/griffin.c +++ b/griffin/griffin.c @@ -1172,6 +1172,10 @@ MENU #include "../menu/drivers_display/menu_display_d3d11.c" #endif +#if defined(HAVE_D3D12) +#include "../menu/drivers_display/menu_display_d3d12.c" +#endif + #ifdef HAVE_OPENGL #include "../menu/drivers_display/menu_display_gl.c" #endif diff --git a/menu/drivers_display/menu_display_d3d12.c b/menu/drivers_display/menu_display_d3d12.c new file mode 100644 index 0000000000..122ad20c4a --- /dev/null +++ b/menu/drivers_display/menu_display_d3d12.c @@ -0,0 +1,244 @@ +/* RetroArch - A frontend for libretro. + * Copyright (C) 2014-2018 - Ali Bouhlel + * + * RetroArch is free software: you can redistribute it and/or modify it under the terms + * of the GNU General Public License as published by the Free Software Found- + * ation, either version 3 of the License, or (at your option) any later version. + * + * RetroArch is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; + * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + * PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with RetroArch. + * If not, see . + */ + +#define CINTERFACE + +#include + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "../menu_driver.h" + +#include "../../retroarch.h" +#include "../../gfx/font_driver.h" +#include "../../gfx/video_driver.h" +#include "../../gfx/common/d3d12_common.h" + +static const float* menu_display_d3d12_get_default_vertices(void) { return NULL; } + +static const float* menu_display_d3d12_get_default_tex_coords(void) { return NULL; } + +static void* menu_display_d3d12_get_default_mvp(void) { return NULL; } + +static void menu_display_d3d12_blend_begin(void) +{ + d3d12_video_t* d3d12 = (d3d12_video_t*)video_driver_get_ptr(false); + + /*todo: d3d12->sprites.pipe_blend */ + D3D12SetPipelineState(d3d12->queue.cmd, d3d12->sprites.pipe); +} + +static void menu_display_d3d12_blend_end(void) +{ + d3d12_video_t* d3d12 = (d3d12_video_t*)video_driver_get_ptr(false); + + /*todo: d3d12->sprites.pipe_noblend */ + D3D12SetPipelineState(d3d12->queue.cmd, d3d12->sprites.pipe); +} + +static void menu_display_d3d12_viewport(void* data) {} + +static void menu_display_d3d12_draw(void* data) +{ + d3d12_video_t* d3d12 = (d3d12_video_t*)video_driver_get_ptr(false); + menu_display_ctx_draw_t* draw = (menu_display_ctx_draw_t*)data; + + if (!d3d12 || !draw || !draw->texture) + return; + + switch (draw->pipeline.id) + { + case VIDEO_SHADER_MENU: + case VIDEO_SHADER_MENU_2: + case VIDEO_SHADER_MENU_3: + case VIDEO_SHADER_MENU_4: + case VIDEO_SHADER_MENU_5: + case VIDEO_SHADER_MENU_6: + D3D12SetPipelineState(d3d12->queue.cmd, d3d12->pipes[draw->pipeline.id]); + D3D12DrawInstanced(d3d12->queue.cmd, draw->coords->vertices, 1, 0, 0); + D3D12SetPipelineState(d3d12->queue.cmd, d3d12->sprites.pipe); + D3D12IASetPrimitiveTopology(d3d12->queue.cmd, D3D_PRIMITIVE_TOPOLOGY_POINTLIST); + D3D12IASetVertexBuffers(d3d12->queue.cmd, 0, 1, &d3d12->sprites.vbo_view); + return; + } + + if (!d3d12->sprites.enabled) + return; + + if (d3d12->sprites.offset + 1 > d3d12->sprites.capacity) + d3d12->sprites.offset = 0; + + { + d3d12_sprite_t* v; + D3D12_RANGE range = { 0, 0 }; + D3D12Map(d3d12->sprites.vbo, 0, &range, (void**)&v); + v += d3d12->sprites.offset; + + v->pos.x = draw->x / (float)d3d12->chain.viewport.Width; + v->pos.y = (d3d12->chain.viewport.Height - draw->y - draw->height) / + (float)d3d12->chain.viewport.Height; + v->pos.w = draw->width / (float)d3d12->chain.viewport.Width; + v->pos.h = draw->height / (float)d3d12->chain.viewport.Height; + + v->coords.u = 0.0f; + v->coords.v = 0.0f; + v->coords.w = 1.0f; + v->coords.h = 1.0f; + + if (draw->scale_factor) + v->params.scaling = draw->scale_factor; + else + v->params.scaling = 1.0f; + + v->params.rotation = draw->rotation; + + v->colors[3] = DXGI_COLOR_RGBA( + 0xFF * draw->coords->color[0], 0xFF * draw->coords->color[1], + 0xFF * draw->coords->color[2], 0xFF * draw->coords->color[3]); + v->colors[2] = DXGI_COLOR_RGBA( + 0xFF * draw->coords->color[4], 0xFF * draw->coords->color[5], + 0xFF * draw->coords->color[6], 0xFF * draw->coords->color[7]); + v->colors[1] = DXGI_COLOR_RGBA( + 0xFF * draw->coords->color[8], 0xFF * draw->coords->color[9], + 0xFF * draw->coords->color[10], 0xFF * draw->coords->color[12]); + v->colors[0] = DXGI_COLOR_RGBA( + 0xFF * draw->coords->color[12], 0xFF * draw->coords->color[13], + 0xFF * draw->coords->color[14], 0xFF * draw->coords->color[15]); + + range.Begin = d3d12->sprites.offset * sizeof(*v); + range.End = (d3d12->sprites.offset + 1) * sizeof(*v); + D3D12Unmap(d3d12->sprites.vbo, 0, &range); + } + + { + d3d12_texture_t* texture = (d3d12_texture_t*)draw->texture; + if (texture->dirty) + d3d12_upload_texture(d3d12->queue.cmd, texture); + d3d12_set_texture_and_sampler(d3d12->queue.cmd, texture); + } + + D3D12DrawInstanced(d3d12->queue.cmd, 1, 1, d3d12->sprites.offset, 0); + d3d12->sprites.offset++; + return; +} + +static void menu_display_d3d12_draw_pipeline(void* data) +{ + menu_display_ctx_draw_t* draw = (menu_display_ctx_draw_t*)data; + d3d12_video_t* d3d12 = (d3d12_video_t*)video_driver_get_ptr(false); + + if (!d3d12 || !draw) + return; + + switch (draw->pipeline.id) + { + case VIDEO_SHADER_MENU: + case VIDEO_SHADER_MENU_2: + { + video_coord_array_t* ca = menu_display_get_coords_array(); + + if (!d3d12->menu_pipeline_vbo) + { + void* vertex_data_begin; + D3D12_RANGE read_range = { 0, 0 }; + + d3d12->menu_pipeline_vbo_view.StrideInBytes = 2 * sizeof(float); + d3d12->menu_pipeline_vbo_view.SizeInBytes = + ca->coords.vertices * d3d12->menu_pipeline_vbo_view.StrideInBytes; + d3d12->menu_pipeline_vbo_view.BufferLocation = d3d12_create_buffer( + d3d12->device, d3d12->menu_pipeline_vbo_view.SizeInBytes, + &d3d12->menu_pipeline_vbo); + + D3D12Map(d3d12->menu_pipeline_vbo, 0, &read_range, &vertex_data_begin); + memcpy(vertex_data_begin, ca->coords.vertex, d3d12->menu_pipeline_vbo_view.SizeInBytes); + D3D12Unmap(d3d12->menu_pipeline_vbo, 0, NULL); + } + D3D12IASetVertexBuffers(d3d12->queue.cmd, 0, 1, &d3d12->menu_pipeline_vbo_view); + draw->coords->vertices = ca->coords.vertices; + break; + } + + case VIDEO_SHADER_MENU_3: + case VIDEO_SHADER_MENU_4: + case VIDEO_SHADER_MENU_5: + case VIDEO_SHADER_MENU_6: + D3D12IASetVertexBuffers(d3d12->queue.cmd, 0, 1, &d3d12->frame.vbo_view); + draw->coords->vertices = 4; + break; + default: + return; + } + D3D12IASetPrimitiveTopology(d3d12->queue.cmd, D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP); + + d3d12->ubo_values.time += 0.01f; + + { + D3D12_RANGE read_range = { 0, 0 }; + d3d12_uniform_t* mapped_ubo; + D3D12Map(d3d12->ubo, 0, &read_range, (void**)&mapped_ubo); + *mapped_ubo = d3d12->ubo_values; + D3D12Unmap(d3d12->ubo, 0, NULL); + } + D3D12SetGraphicsRootConstantBufferView( + d3d12->queue.cmd, ROOT_ID_UBO, d3d12->ubo_view.BufferLocation); +} + +static void menu_display_d3d12_restore_clear_color(void) {} + +static void menu_display_d3d12_clear_color(menu_display_ctx_clearcolor_t* clearcolor) +{ + d3d12_video_t* d3d12 = (d3d12_video_t*)video_driver_get_ptr(false); + + if (!d3d12 || !clearcolor) + return; + + D3D12ClearRenderTargetView( + d3d12->queue.cmd, d3d12->chain.desc_handles[d3d12->chain.frame_index], (float*)clearcolor, + 0, NULL); +} + +static bool menu_display_d3d12_font_init_first( + void** font_handle, + void* video_data, + const char* font_path, + float font_size, + bool is_threaded) +{ + font_data_t** handle = (font_data_t**)font_handle; + font_data_t* new_handle = font_driver_init_first( + video_data, font_path, font_size, true, is_threaded, FONT_DRIVER_RENDER_D3D12_API); + if (!new_handle) + return false; + *handle = new_handle; + return true; +} + +menu_display_ctx_driver_t menu_display_ctx_d3d12 = { + menu_display_d3d12_draw, + menu_display_d3d12_draw_pipeline, + menu_display_d3d12_viewport, + menu_display_d3d12_blend_begin, + menu_display_d3d12_blend_end, + menu_display_d3d12_restore_clear_color, + menu_display_d3d12_clear_color, + menu_display_d3d12_get_default_mvp, + menu_display_d3d12_get_default_vertices, + menu_display_d3d12_get_default_tex_coords, + menu_display_d3d12_font_init_first, + MENU_VIDEO_DRIVER_DIRECT3D12, + "menu_display_d3d12", +}; diff --git a/menu/menu_driver.c b/menu/menu_driver.c index 787252526e..9675d2ecc5 100644 --- a/menu/menu_driver.c +++ b/menu/menu_driver.c @@ -93,6 +93,9 @@ static menu_display_ctx_driver_t *menu_display_ctx_drivers[] = { #ifdef HAVE_D3D11 &menu_display_ctx_d3d11, #endif +#ifdef HAVE_D3D12 + &menu_display_ctx_d3d12, +#endif #ifdef HAVE_OPENGL &menu_display_ctx_gl, #endif @@ -229,6 +232,10 @@ static bool menu_display_check_compatibility( if (string_is_equal(video_driver, "d3d11")) return true; break; + case MENU_VIDEO_DRIVER_DIRECT3D12: + if (string_is_equal(video_driver, "d3d12")) + return true; + break; case MENU_VIDEO_DRIVER_VITA2D: if (string_is_equal(video_driver, "vita2d")) return true; diff --git a/menu/menu_driver.h b/menu/menu_driver.h index 33a6a551f3..9c2f9cf14c 100644 --- a/menu/menu_driver.h +++ b/menu/menu_driver.h @@ -280,6 +280,7 @@ enum menu_display_driver_type MENU_VIDEO_DRIVER_VULKAN, MENU_VIDEO_DRIVER_DIRECT3D, MENU_VIDEO_DRIVER_DIRECT3D11, + MENU_VIDEO_DRIVER_DIRECT3D12, MENU_VIDEO_DRIVER_VITA2D, MENU_VIDEO_DRIVER_CTR, MENU_VIDEO_DRIVER_WIIU, @@ -735,6 +736,7 @@ extern menu_display_ctx_driver_t menu_display_ctx_gl; extern menu_display_ctx_driver_t menu_display_ctx_vulkan; extern menu_display_ctx_driver_t menu_display_ctx_d3d; extern menu_display_ctx_driver_t menu_display_ctx_d3d11; +extern menu_display_ctx_driver_t menu_display_ctx_d3d12; extern menu_display_ctx_driver_t menu_display_ctx_vita2d; extern menu_display_ctx_driver_t menu_display_ctx_ctr; extern menu_display_ctx_driver_t menu_display_ctx_wiiu;