diff --git a/sunshine/nvhttp.cpp b/sunshine/nvhttp.cpp index 544e1877..fcbd69bb 100644 --- a/sunshine/nvhttp.cpp +++ b/sunshine/nvhttp.cpp @@ -33,7 +33,7 @@ constexpr auto PORT_HTTP = 47989; constexpr auto PORT_HTTPS = 47984; constexpr auto VERSION = "7.1.400.0"; -constexpr auto GFE_VERSION = "2.0.0.1"; +constexpr auto GFE_VERSION = "3.12.0.1"; namespace fs = std::filesystem; namespace pt = boost::property_tree; diff --git a/sunshine/platform/windows_dxgi.cpp b/sunshine/platform/windows_dxgi.cpp index 726b17b5..5362b08d 100644 --- a/sunshine/platform/windows_dxgi.cpp +++ b/sunshine/platform/windows_dxgi.cpp @@ -183,7 +183,34 @@ void blend_cursor_monochrome(const cursor_t &cursor, img_t &img) { } } -void blend_cursor_color(const cursor_t &cursor, img_t &img) { +void apply_color_alpha(int *img_pixel_p, int cursor_pixel) { + auto colors_out = (std::uint8_t*)&cursor_pixel; + auto colors_in = (std::uint8_t*)img_pixel_p; + + //TODO: When use of IDXGIOutput5 is implemented, support different color formats + auto alpha = colors_out[3]; + if(alpha == 255) { + *img_pixel_p = cursor_pixel; + } + else { + colors_in[0] = colors_out[0] + (colors_in[0] * (255 - alpha) + 255/2) / 255; + colors_in[1] = colors_out[1] + (colors_in[1] * (255 - alpha) + 255/2) / 255; + colors_in[2] = colors_out[2] + (colors_in[2] * (255 - alpha) + 255/2) / 255; + } +} + +void apply_color_masked(int *img_pixel_p, int cursor_pixel) { + //TODO: When use of IDXGIOutput5 is implemented, support different color formats + auto alpha = ((std::uint8_t*)&cursor_pixel)[3]; + if(alpha == 0xFF) { + *img_pixel_p ^= cursor_pixel; + } + else { + *img_pixel_p = cursor_pixel; + } +} + +void blend_cursor_color(const cursor_t &cursor, img_t &img, const bool masked) { int height = cursor.shape_info.Height; int width = cursor.shape_info.Width; int pitch = cursor.shape_info.Pitch; @@ -219,18 +246,11 @@ void blend_cursor_color(const cursor_t &cursor, img_t &img) { auto img_pixel_p = &img_data[(i + img_skip_y) * (img.row_pitch / img.pixel_pitch) + img_skip_x]; std::for_each(cursor_begin, cursor_end, [&](int cursor_pixel) { - auto colors_out = (std::uint8_t*)&cursor_pixel; - auto colors_in = (std::uint8_t*)img_pixel_p; - - //TODO: When use of IDXGIOutput5 is implemented, support different color formats - auto alpha = colors_out[3]; - if(alpha == 255) { - *img_pixel_p = cursor_pixel; + if(masked) { + apply_color_masked(img_pixel_p, cursor_pixel); } else { - colors_in[0] = colors_out[0] + (colors_in[0] * (255 - alpha) + 255/2) / 255; - colors_in[1] = colors_out[1] + (colors_in[1] * (255 - alpha) + 255/2) / 255; - colors_in[2] = colors_out[2] + (colors_in[2] * (255 - alpha) + 255/2) / 255; + apply_color_alpha(img_pixel_p, cursor_pixel); } ++img_pixel_p; }); @@ -240,12 +260,14 @@ void blend_cursor_color(const cursor_t &cursor, img_t &img) { void blend_cursor(const cursor_t &cursor, img_t &img) { switch(cursor.shape_info.Type) { case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_COLOR: - blend_cursor_color(cursor, img); + blend_cursor_color(cursor, img, false); break; case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MONOCHROME: blend_cursor_monochrome(cursor, img); break; case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MASKED_COLOR: + blend_cursor_color(cursor, img, true); + break; default: BOOST_LOG(warning) << "Unsupported cursor format ["sv << cursor.shape_info.Type << ']'; } diff --git a/sunshine/video.cpp b/sunshine/video.cpp index f7a1e92f..eeddcfc4 100644 --- a/sunshine/video.cpp +++ b/sunshine/video.cpp @@ -684,6 +684,11 @@ void capture( } bool validate_config(const encoder_t &encoder, const config_t &config, platf::display_t &disp) { + // Ensure everything but software fails succesfully, it's not ready yet + if(encoder.dev_type != AV_HWDEVICE_TYPE_NONE) { + return false; + } + auto hwdevice = disp.get_hwdevice(); auto session = make_session(encoder, config, hwdevice.get());