vk_presenter: Use correct format for output frame image and view. (#2871)
Some checks are pending
Build and Release / reuse (push) Waiting to run
Build and Release / clang-format (push) Waiting to run
Build and Release / get-info (push) Waiting to run
Build and Release / windows-sdl (push) Blocked by required conditions
Build and Release / windows-qt (push) Blocked by required conditions
Build and Release / macos-sdl (push) Blocked by required conditions
Build and Release / macos-qt (push) Blocked by required conditions
Build and Release / linux-sdl (push) Blocked by required conditions
Build and Release / linux-qt (push) Blocked by required conditions
Build and Release / linux-sdl-gcc (push) Blocked by required conditions
Build and Release / linux-qt-gcc (push) Blocked by required conditions
Build and Release / pre-release (push) Blocked by required conditions

This commit is contained in:
squidbus 2025-05-01 20:10:42 -07:00 committed by GitHub
parent 6c39bf229c
commit eb09c4ccce
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 29 additions and 8 deletions

View file

@ -270,7 +270,25 @@ Frame* Presenter::PrepareLastFrame() {
return frame;
}
Frame* Presenter::PrepareFrameInternal(VideoCore::ImageId image_id, bool is_eop) {
static vk::Format GetFrameViewFormat(const Libraries::VideoOut::PixelFormat format) {
switch (format) {
case Libraries::VideoOut::PixelFormat::A8B8G8R8Srgb:
return vk::Format::eR8G8B8A8Srgb;
case Libraries::VideoOut::PixelFormat::A8R8G8B8Srgb:
return vk::Format::eB8G8R8A8Srgb;
case Libraries::VideoOut::PixelFormat::A2R10G10B10:
case Libraries::VideoOut::PixelFormat::A2R10G10B10Srgb:
case Libraries::VideoOut::PixelFormat::A2R10G10B10Bt2020Pq:
return vk::Format::eA2R10G10B10UnormPack32;
default:
break;
}
UNREACHABLE_MSG("Unknown format={}", static_cast<u32>(format));
return {};
}
Frame* Presenter::PrepareFrameInternal(VideoCore::ImageId image_id,
const Libraries::VideoOut::PixelFormat format, bool is_eop) {
// Request a free presentation frame.
Frame* frame = GetRenderFrame();
@ -324,7 +342,7 @@ Frame* Presenter::PrepareFrameInternal(VideoCore::ImageId image_id, bool is_eop)
cmdbuf);
VideoCore::ImageViewInfo info{};
info.format = image.info.pixel_format;
info.format = GetFrameViewFormat(format);
// Exclude alpha from output frame to avoid blending with UI.
info.mapping = vk::ComponentMapping{
.r = vk::ComponentSwizzle::eIdentity,

View file

@ -70,11 +70,12 @@ public:
auto desc = VideoCore::TextureCache::VideoOutDesc{attribute, cpu_address};
const auto image_id = texture_cache.FindImage(desc);
texture_cache.UpdateImage(image_id, is_eop ? nullptr : &flip_scheduler);
return PrepareFrameInternal(image_id, is_eop);
return PrepareFrameInternal(image_id, attribute.attrib.pixel_format, is_eop);
}
Frame* PrepareBlankFrame(bool is_eop) {
return PrepareFrameInternal(VideoCore::NULL_IMAGE_ID, is_eop);
return PrepareFrameInternal(VideoCore::NULL_IMAGE_ID,
Libraries::VideoOut::PixelFormat::Unknown, is_eop);
}
VideoCore::Image& RegisterVideoOutSurface(
@ -119,7 +120,8 @@ public:
}
private:
Frame* PrepareFrameInternal(VideoCore::ImageId image_id, bool is_eop = true);
Frame* PrepareFrameInternal(VideoCore::ImageId image_id,
Libraries::VideoOut::PixelFormat format, bool is_eop = true);
Frame* GetRenderFrame();
void SetExpectedGameSize(s32 width, s32 height);

View file

@ -16,14 +16,15 @@ using VideoOutFormat = Libraries::VideoOut::PixelFormat;
static vk::Format ConvertPixelFormat(const VideoOutFormat format) {
switch (format) {
case VideoOutFormat::A8R8G8B8Srgb:
return vk::Format::eB8G8R8A8Srgb;
case VideoOutFormat::A8B8G8R8Srgb:
// Remaining formats are mapped to RGBA for internal consistency and changed to BGRA in the
// frame image view.
case VideoOutFormat::A8R8G8B8Srgb:
return vk::Format::eR8G8B8A8Srgb;
case VideoOutFormat::A2R10G10B10:
case VideoOutFormat::A2R10G10B10Srgb:
case VideoOutFormat::A2R10G10B10Bt2020Pq:
return vk::Format::eA2R10G10B10UnormPack32;
return vk::Format::eA2B10G10R10UnormPack32;
default:
break;
}