xref: /aosp_15_r20/external/angle/src/libANGLE/renderer/vulkan/OverlayVk.cpp (revision 8975f5c5ed3d1c378011245431ada316dfb6f244)
1*8975f5c5SAndroid Build Coastguard Worker //
2*8975f5c5SAndroid Build Coastguard Worker // Copyright 2019 The ANGLE Project Authors. All rights reserved.
3*8975f5c5SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be
4*8975f5c5SAndroid Build Coastguard Worker // found in the LICENSE file.
5*8975f5c5SAndroid Build Coastguard Worker //
6*8975f5c5SAndroid Build Coastguard Worker // OverlayVk.cpp:
7*8975f5c5SAndroid Build Coastguard Worker //    Implements the OverlayVk class.
8*8975f5c5SAndroid Build Coastguard Worker //
9*8975f5c5SAndroid Build Coastguard Worker 
10*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/renderer/vulkan/OverlayVk.h"
11*8975f5c5SAndroid Build Coastguard Worker 
12*8975f5c5SAndroid Build Coastguard Worker #include "common/system_utils.h"
13*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/Context.h"
14*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/Overlay_font_autogen.h"
15*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/renderer/vulkan/ContextVk.h"
16*8975f5c5SAndroid Build Coastguard Worker 
17*8975f5c5SAndroid Build Coastguard Worker #include <numeric>
18*8975f5c5SAndroid Build Coastguard Worker 
19*8975f5c5SAndroid Build Coastguard Worker namespace rx
20*8975f5c5SAndroid Build Coastguard Worker {
OverlayVk(const gl::OverlayState & state)21*8975f5c5SAndroid Build Coastguard Worker OverlayVk::OverlayVk(const gl::OverlayState &state) : OverlayImpl(state) {}
22*8975f5c5SAndroid Build Coastguard Worker OverlayVk::~OverlayVk() = default;
23*8975f5c5SAndroid Build Coastguard Worker 
onDestroy(const gl::Context * context)24*8975f5c5SAndroid Build Coastguard Worker void OverlayVk::onDestroy(const gl::Context *context)
25*8975f5c5SAndroid Build Coastguard Worker {
26*8975f5c5SAndroid Build Coastguard Worker     vk::Renderer *renderer = vk::GetImpl(context)->getRenderer();
27*8975f5c5SAndroid Build Coastguard Worker     VkDevice device        = renderer->getDevice();
28*8975f5c5SAndroid Build Coastguard Worker 
29*8975f5c5SAndroid Build Coastguard Worker     mFontImage.destroy(renderer);
30*8975f5c5SAndroid Build Coastguard Worker     mFontImageView.destroy(device);
31*8975f5c5SAndroid Build Coastguard Worker }
32*8975f5c5SAndroid Build Coastguard Worker 
createFont(ContextVk * contextVk)33*8975f5c5SAndroid Build Coastguard Worker angle::Result OverlayVk::createFont(ContextVk *contextVk)
34*8975f5c5SAndroid Build Coastguard Worker {
35*8975f5c5SAndroid Build Coastguard Worker     vk::Renderer *renderer = contextVk->getRenderer();
36*8975f5c5SAndroid Build Coastguard Worker 
37*8975f5c5SAndroid Build Coastguard Worker     // Create a buffer to stage font data upload.
38*8975f5c5SAndroid Build Coastguard Worker     VkBufferCreateInfo bufferCreateInfo = {};
39*8975f5c5SAndroid Build Coastguard Worker     bufferCreateInfo.sType              = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
40*8975f5c5SAndroid Build Coastguard Worker     bufferCreateInfo.size               = gl::overlay::kFontTotalDataSize;
41*8975f5c5SAndroid Build Coastguard Worker     bufferCreateInfo.usage              = VK_BUFFER_USAGE_TRANSFER_SRC_BIT;
42*8975f5c5SAndroid Build Coastguard Worker     bufferCreateInfo.sharingMode        = VK_SHARING_MODE_EXCLUSIVE;
43*8975f5c5SAndroid Build Coastguard Worker 
44*8975f5c5SAndroid Build Coastguard Worker     vk::RendererScoped<vk::BufferHelper> fontDataBuffer(renderer);
45*8975f5c5SAndroid Build Coastguard Worker 
46*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(fontDataBuffer.get().init(contextVk, bufferCreateInfo,
47*8975f5c5SAndroid Build Coastguard Worker                                         VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT));
48*8975f5c5SAndroid Build Coastguard Worker 
49*8975f5c5SAndroid Build Coastguard Worker     uint8_t *mappedFontData;
50*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(fontDataBuffer.get().map(contextVk, &mappedFontData));
51*8975f5c5SAndroid Build Coastguard Worker 
52*8975f5c5SAndroid Build Coastguard Worker     const uint8_t *fontData = mState.getFontData();
53*8975f5c5SAndroid Build Coastguard Worker     memcpy(mappedFontData, fontData, gl::overlay::kFontTotalDataSize * sizeof(*fontData));
54*8975f5c5SAndroid Build Coastguard Worker 
55*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(fontDataBuffer.get().flush(renderer, 0, fontDataBuffer.get().getSize()));
56*8975f5c5SAndroid Build Coastguard Worker     fontDataBuffer.get().unmap(renderer);
57*8975f5c5SAndroid Build Coastguard Worker 
58*8975f5c5SAndroid Build Coastguard Worker     // Don't use robust resource init for overlay widgets.
59*8975f5c5SAndroid Build Coastguard Worker     constexpr bool kNoRobustInit = false;
60*8975f5c5SAndroid Build Coastguard Worker 
61*8975f5c5SAndroid Build Coastguard Worker     // Create the font image.
62*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(mFontImage.init(
63*8975f5c5SAndroid Build Coastguard Worker         contextVk, gl::TextureType::_2D,
64*8975f5c5SAndroid Build Coastguard Worker         VkExtent3D{gl::overlay::kFontGlyphWidth, gl::overlay::kFontGlyphHeight, 1},
65*8975f5c5SAndroid Build Coastguard Worker         renderer->getFormat(angle::FormatID::R8_UNORM), 1,
66*8975f5c5SAndroid Build Coastguard Worker         VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_SAMPLED_BIT, gl::LevelIndex(0),
67*8975f5c5SAndroid Build Coastguard Worker         gl::overlay::kFontMipCount, gl::overlay::kFontCharacters, kNoRobustInit, false));
68*8975f5c5SAndroid Build Coastguard Worker 
69*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(contextVk->initImageAllocation(&mFontImage, false, renderer->getMemoryProperties(),
70*8975f5c5SAndroid Build Coastguard Worker                                              VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT,
71*8975f5c5SAndroid Build Coastguard Worker                                              vk::MemoryAllocationType::FontImage));
72*8975f5c5SAndroid Build Coastguard Worker 
73*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(mFontImage.initLayerImageView(
74*8975f5c5SAndroid Build Coastguard Worker         contextVk, gl::TextureType::_2DArray, VK_IMAGE_ASPECT_COLOR_BIT, gl::SwizzleState(),
75*8975f5c5SAndroid Build Coastguard Worker         &mFontImageView, vk::LevelIndex(0), gl::overlay::kFontMipCount, 0,
76*8975f5c5SAndroid Build Coastguard Worker         mFontImage.getLayerCount()));
77*8975f5c5SAndroid Build Coastguard Worker 
78*8975f5c5SAndroid Build Coastguard Worker     // Copy font data from staging buffer.
79*8975f5c5SAndroid Build Coastguard Worker     vk::CommandBufferAccess access;
80*8975f5c5SAndroid Build Coastguard Worker     access.onBufferTransferRead(&fontDataBuffer.get());
81*8975f5c5SAndroid Build Coastguard Worker     access.onImageTransferWrite(gl::LevelIndex(0), gl::overlay::kFontMipCount, 0,
82*8975f5c5SAndroid Build Coastguard Worker                                 gl::overlay::kFontCharacters, VK_IMAGE_ASPECT_COLOR_BIT,
83*8975f5c5SAndroid Build Coastguard Worker                                 &mFontImage);
84*8975f5c5SAndroid Build Coastguard Worker     vk::OutsideRenderPassCommandBuffer *fontDataUpload;
85*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(contextVk->getOutsideRenderPassCommandBuffer(access, &fontDataUpload));
86*8975f5c5SAndroid Build Coastguard Worker 
87*8975f5c5SAndroid Build Coastguard Worker     VkBufferImageCopy copy           = {};
88*8975f5c5SAndroid Build Coastguard Worker     copy.imageSubresource.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
89*8975f5c5SAndroid Build Coastguard Worker     copy.imageSubresource.layerCount = gl::overlay::kFontCharacters;
90*8975f5c5SAndroid Build Coastguard Worker     copy.imageExtent.depth           = 1;
91*8975f5c5SAndroid Build Coastguard Worker 
92*8975f5c5SAndroid Build Coastguard Worker     for (uint32_t mip = 0; mip < gl::overlay::kFontMipCount; ++mip)
93*8975f5c5SAndroid Build Coastguard Worker     {
94*8975f5c5SAndroid Build Coastguard Worker         copy.bufferOffset              = gl::overlay::kFontMipDataOffset[mip];
95*8975f5c5SAndroid Build Coastguard Worker         copy.bufferRowLength           = gl::overlay::kFontGlyphWidth >> mip;
96*8975f5c5SAndroid Build Coastguard Worker         copy.bufferImageHeight         = gl::overlay::kFontGlyphHeight >> mip;
97*8975f5c5SAndroid Build Coastguard Worker         copy.imageSubresource.mipLevel = mip;
98*8975f5c5SAndroid Build Coastguard Worker         copy.imageExtent.width         = gl::overlay::kFontGlyphWidth >> mip;
99*8975f5c5SAndroid Build Coastguard Worker         copy.imageExtent.height        = gl::overlay::kFontGlyphHeight >> mip;
100*8975f5c5SAndroid Build Coastguard Worker 
101*8975f5c5SAndroid Build Coastguard Worker         fontDataUpload->copyBufferToImage(fontDataBuffer.get().getBuffer().getHandle(),
102*8975f5c5SAndroid Build Coastguard Worker                                           mFontImage.getImage(),
103*8975f5c5SAndroid Build Coastguard Worker                                           VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &copy);
104*8975f5c5SAndroid Build Coastguard Worker     }
105*8975f5c5SAndroid Build Coastguard Worker 
106*8975f5c5SAndroid Build Coastguard Worker     return angle::Result::Continue;
107*8975f5c5SAndroid Build Coastguard Worker }
108*8975f5c5SAndroid Build Coastguard Worker 
onPresent(ContextVk * contextVk,vk::ImageHelper * imageToPresent,const vk::ImageView * imageToPresentView,bool is90DegreeRotation)109*8975f5c5SAndroid Build Coastguard Worker angle::Result OverlayVk::onPresent(ContextVk *contextVk,
110*8975f5c5SAndroid Build Coastguard Worker                                    vk::ImageHelper *imageToPresent,
111*8975f5c5SAndroid Build Coastguard Worker                                    const vk::ImageView *imageToPresentView,
112*8975f5c5SAndroid Build Coastguard Worker                                    bool is90DegreeRotation)
113*8975f5c5SAndroid Build Coastguard Worker {
114*8975f5c5SAndroid Build Coastguard Worker     if (mState.getEnabledWidgetCount() == 0)
115*8975f5c5SAndroid Build Coastguard Worker     {
116*8975f5c5SAndroid Build Coastguard Worker         return angle::Result::Continue;
117*8975f5c5SAndroid Build Coastguard Worker     }
118*8975f5c5SAndroid Build Coastguard Worker 
119*8975f5c5SAndroid Build Coastguard Worker     // Lazily initialize the font on first use
120*8975f5c5SAndroid Build Coastguard Worker     if (!mFontImage.valid())
121*8975f5c5SAndroid Build Coastguard Worker     {
122*8975f5c5SAndroid Build Coastguard Worker         ANGLE_TRY(createFont(contextVk));
123*8975f5c5SAndroid Build Coastguard Worker     }
124*8975f5c5SAndroid Build Coastguard Worker 
125*8975f5c5SAndroid Build Coastguard Worker     vk::Renderer *renderer = contextVk->getRenderer();
126*8975f5c5SAndroid Build Coastguard Worker 
127*8975f5c5SAndroid Build Coastguard Worker     vk::RendererScoped<vk::BufferHelper> textDataBuffer(renderer);
128*8975f5c5SAndroid Build Coastguard Worker     vk::RendererScoped<vk::BufferHelper> graphDataBuffer(renderer);
129*8975f5c5SAndroid Build Coastguard Worker 
130*8975f5c5SAndroid Build Coastguard Worker     VkBufferCreateInfo textBufferCreateInfo = {};
131*8975f5c5SAndroid Build Coastguard Worker     textBufferCreateInfo.sType              = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
132*8975f5c5SAndroid Build Coastguard Worker     textBufferCreateInfo.size               = mState.getTextWidgetsBufferSize();
133*8975f5c5SAndroid Build Coastguard Worker     textBufferCreateInfo.usage              = VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT;
134*8975f5c5SAndroid Build Coastguard Worker     textBufferCreateInfo.sharingMode        = VK_SHARING_MODE_EXCLUSIVE;
135*8975f5c5SAndroid Build Coastguard Worker 
136*8975f5c5SAndroid Build Coastguard Worker     VkBufferCreateInfo graphBufferCreateInfo = textBufferCreateInfo;
137*8975f5c5SAndroid Build Coastguard Worker     graphBufferCreateInfo.size               = mState.getGraphWidgetsBufferSize();
138*8975f5c5SAndroid Build Coastguard Worker 
139*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(textDataBuffer.get().init(contextVk, textBufferCreateInfo,
140*8975f5c5SAndroid Build Coastguard Worker                                         VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT));
141*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(graphDataBuffer.get().init(contextVk, graphBufferCreateInfo,
142*8975f5c5SAndroid Build Coastguard Worker                                          VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT));
143*8975f5c5SAndroid Build Coastguard Worker 
144*8975f5c5SAndroid Build Coastguard Worker     uint8_t *textData;
145*8975f5c5SAndroid Build Coastguard Worker     uint8_t *graphData;
146*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(textDataBuffer.get().map(contextVk, &textData));
147*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(graphDataBuffer.get().map(contextVk, &graphData));
148*8975f5c5SAndroid Build Coastguard Worker 
149*8975f5c5SAndroid Build Coastguard Worker     uint32_t textWidgetCount  = 0;
150*8975f5c5SAndroid Build Coastguard Worker     uint32_t graphWidgetCount = 0;
151*8975f5c5SAndroid Build Coastguard Worker 
152*8975f5c5SAndroid Build Coastguard Worker     gl::Extents presentImageExtents(imageToPresent->getExtents().width,
153*8975f5c5SAndroid Build Coastguard Worker                                     imageToPresent->getExtents().height, 1);
154*8975f5c5SAndroid Build Coastguard Worker     mState.fillWidgetData(presentImageExtents, textData, graphData, &textWidgetCount,
155*8975f5c5SAndroid Build Coastguard Worker                           &graphWidgetCount);
156*8975f5c5SAndroid Build Coastguard Worker 
157*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(textDataBuffer.get().flush(renderer, 0, textDataBuffer.get().getSize()));
158*8975f5c5SAndroid Build Coastguard Worker     ANGLE_TRY(graphDataBuffer.get().flush(renderer, 0, graphDataBuffer.get().getSize()));
159*8975f5c5SAndroid Build Coastguard Worker     textDataBuffer.get().unmap(renderer);
160*8975f5c5SAndroid Build Coastguard Worker     graphDataBuffer.get().unmap(renderer);
161*8975f5c5SAndroid Build Coastguard Worker 
162*8975f5c5SAndroid Build Coastguard Worker     UtilsVk::OverlayDrawParameters params;
163*8975f5c5SAndroid Build Coastguard Worker     params.textWidgetCount  = textWidgetCount;
164*8975f5c5SAndroid Build Coastguard Worker     params.graphWidgetCount = graphWidgetCount;
165*8975f5c5SAndroid Build Coastguard Worker     params.rotateXY         = is90DegreeRotation;
166*8975f5c5SAndroid Build Coastguard Worker 
167*8975f5c5SAndroid Build Coastguard Worker     return contextVk->getUtils().drawOverlay(contextVk, &textDataBuffer.get(),
168*8975f5c5SAndroid Build Coastguard Worker                                              &graphDataBuffer.get(), &mFontImage, &mFontImageView,
169*8975f5c5SAndroid Build Coastguard Worker                                              imageToPresent, imageToPresentView, params);
170*8975f5c5SAndroid Build Coastguard Worker }
171*8975f5c5SAndroid Build Coastguard Worker 
172*8975f5c5SAndroid Build Coastguard Worker }  // namespace rx
173