summaryrefslogtreecommitdiffstats
path: root/video
diff options
context:
space:
mode:
authorNiklas Haas <git@haasn.xyz>2017-09-29 15:08:21 +0200
committerMartin Herkt <652892+lachs0r@users.noreply.github.com>2017-12-25 00:47:53 +0100
commit2d1769a5348ee320b07779177526754f92e624a1 (patch)
tree32d946d4d6dcdd7593e228418432fd3fe50fc714 /video
parenta42b8b1142fd26e82ca0e8b0ea7ab6cafd78776d (diff)
downloadmpv-2d1769a5348ee320b07779177526754f92e624a1.tar.bz2
mpv-2d1769a5348ee320b07779177526754f92e624a1.tar.xz
vo_gpu: vulkan: prefer vkCmdCopyImage over vkCmdBlitImage
blit() implies scaling, copy() is the equivalent command to use when the formats are compatible (same pixel size) and the rects have the same dimensions.
Diffstat (limited to 'video')
-rw-r--r--video/out/vulkan/ra_vk.c39
1 files changed, 31 insertions, 8 deletions
diff --git a/video/out/vulkan/ra_vk.c b/video/out/vulkan/ra_vk.c
index 775fe7eaa5..cd3ad73d5b 100644
--- a/video/out/vulkan/ra_vk.c
+++ b/video/out/vulkan/ra_vk.c
@@ -1684,15 +1684,38 @@ static void vk_blit(struct ra *ra, struct ra_tex *dst, struct ra_tex *src,
VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,
discard);
- VkImageBlit region = {
- .srcSubresource = vk_layers,
- .srcOffsets = {{src_rc->x0, src_rc->y0, 0}, {src_rc->x1, src_rc->y1, 1}},
- .dstSubresource = vk_layers,
- .dstOffsets = {{dst_rc->x0, dst_rc->y0, 0}, {dst_rc->x1, dst_rc->y1, 1}},
- };
+ // Under certain conditions we can use vkCmdCopyImage instead of
+ // vkCmdBlitImage, namely when the blit operation does not require
+ // scaling. and the formats are compatible.
+ if (src->params.format->pixel_size == dst->params.format->pixel_size &&
+ mp_rect_w(*src_rc) == mp_rect_w(*dst_rc) &&
+ mp_rect_h(*src_rc) == mp_rect_h(*dst_rc) &&
+ mp_rect_w(*src_rc) >= 0 && mp_rect_h(*src_rc) >= 0)
+ {
+ VkImageCopy region = {
+ .srcSubresource = vk_layers,
+ .dstSubresource = vk_layers,
+ .srcOffset = {src_rc->x0, src_rc->y0, 0},
+ .dstOffset = {dst_rc->x0, dst_rc->y0, 0},
+ .extent = {mp_rect_w(*src_rc), mp_rect_h(*src_rc), 1},
+ };
- vkCmdBlitImage(cmd->buf, src_vk->img, src_vk->current_layout, dst_vk->img,
- dst_vk->current_layout, 1, &region, VK_FILTER_NEAREST);
+ vkCmdCopyImage(cmd->buf, src_vk->img, src_vk->current_layout,
+ dst_vk->img, dst_vk->current_layout, 1, &region);
+ } else {
+ VkImageBlit region = {
+ .srcSubresource = vk_layers,
+ .dstSubresource = vk_layers,
+ .srcOffsets = {{src_rc->x0, src_rc->y0, 0},
+ {src_rc->x1, src_rc->y1, 1}},
+ .dstOffsets = {{dst_rc->x0, dst_rc->y0, 0},
+ {dst_rc->x1, dst_rc->y1, 1}},
+ };
+
+ vkCmdBlitImage(cmd->buf, src_vk->img, src_vk->current_layout,
+ dst_vk->img, dst_vk->current_layout, 1, &region,
+ VK_FILTER_NEAREST);
+ }
tex_signal(ra, cmd, src, VK_PIPELINE_STAGE_TRANSFER_BIT);
tex_signal(ra, cmd, dst, VK_PIPELINE_STAGE_TRANSFER_BIT);