blob: 1aa178b5f6123628cb591cd77426c09102bc4fe3 [file] [log] [blame]
Jim Van Verthfd89e0b2020-03-26 15:33:02 -04001/*
2 * Copyright 2020 Google LLC
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#include "src/gpu/d3d/GrD3DTextureRenderTarget.h"
9
10#include "src/gpu/GrTexturePriv.h"
11#include "src/gpu/d3d/GrD3DGpu.h"
12
Jim Van Verth5ce94402020-05-01 14:19:13 -040013GrD3DTextureRenderTarget::GrD3DTextureRenderTarget(
14 GrD3DGpu* gpu, SkBudgeted budgeted, SkISize dimensions, int sampleCnt,
15 const GrD3DTextureResourceInfo& info, sk_sp<GrD3DResourceState> state,
16 const GrD3DTextureResourceInfo& msaaInfo, sk_sp<GrD3DResourceState> msaaState,
17 const D3D12_CPU_DESCRIPTOR_HANDLE& colorRenderTargetView,
18 const D3D12_CPU_DESCRIPTOR_HANDLE& resolveRenderTargetView,
19 GrMipMapsStatus mipMapsStatus)
20 : GrSurface(gpu, dimensions, info.fProtected)
21 , GrD3DTextureResource(info, state)
22 , GrD3DTexture(gpu, dimensions, info, state, mipMapsStatus)
23 , GrD3DRenderTarget(gpu, dimensions, sampleCnt, info, state, msaaInfo,
24 std::move(msaaState), colorRenderTargetView, resolveRenderTargetView) {
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040025 SkASSERT(info.fProtected == msaaInfo.fProtected);
26 this->registerWithCache(budgeted);
27}
28
Jim Van Verth5ce94402020-05-01 14:19:13 -040029GrD3DTextureRenderTarget::GrD3DTextureRenderTarget(
30 GrD3DGpu* gpu, SkBudgeted budgeted, SkISize dimensions,
31 const GrD3DTextureResourceInfo& info, sk_sp<GrD3DResourceState> state,
32 const D3D12_CPU_DESCRIPTOR_HANDLE& renderTargetView,
33 GrMipMapsStatus mipMapsStatus)
34 : GrSurface(gpu, dimensions, info.fProtected)
35 , GrD3DTextureResource(info, state)
36 , GrD3DTexture(gpu, dimensions, info, state, mipMapsStatus)
37 , GrD3DRenderTarget(gpu, dimensions, info, state, renderTargetView) {
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040038 this->registerWithCache(budgeted);
39}
40
Jim Van Verth5ce94402020-05-01 14:19:13 -040041GrD3DTextureRenderTarget::GrD3DTextureRenderTarget(
42 GrD3DGpu* gpu, SkISize dimensions, int sampleCnt,
43 const GrD3DTextureResourceInfo& info, sk_sp<GrD3DResourceState> state,
44 const GrD3DTextureResourceInfo& msaaInfo, sk_sp<GrD3DResourceState> msaaState,
45 const D3D12_CPU_DESCRIPTOR_HANDLE& colorRenderTargetView,
46 const D3D12_CPU_DESCRIPTOR_HANDLE& resolveRenderTargetView,
47 GrMipMapsStatus mipMapsStatus,
48 GrWrapCacheable cacheable)
49 : GrSurface(gpu, dimensions, info.fProtected)
50 , GrD3DTextureResource(info, state)
51 , GrD3DTexture(gpu, dimensions, info, state, mipMapsStatus)
52 , GrD3DRenderTarget(gpu, dimensions, sampleCnt, info, state, msaaInfo,
53 std::move(msaaState), colorRenderTargetView, resolveRenderTargetView) {
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040054 SkASSERT(info.fProtected == msaaInfo.fProtected);
55 this->registerWithCacheWrapped(cacheable);
56}
57
Jim Van Verth5ce94402020-05-01 14:19:13 -040058GrD3DTextureRenderTarget::GrD3DTextureRenderTarget(
59 GrD3DGpu* gpu, SkISize dimensions,
60 const GrD3DTextureResourceInfo& info, sk_sp<GrD3DResourceState> state,
61 const D3D12_CPU_DESCRIPTOR_HANDLE& renderTargetView,
62 GrMipMapsStatus mipMapsStatus,
63 GrWrapCacheable cacheable)
64 : GrSurface(gpu, dimensions, info.fProtected)
65 , GrD3DTextureResource(info, state)
66 , GrD3DTexture(gpu, dimensions, info, state, mipMapsStatus)
67 , GrD3DRenderTarget(gpu, dimensions, info, state, renderTargetView) {
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040068 this->registerWithCacheWrapped(cacheable);
69}
70
71static std::pair<GrD3DTextureResourceInfo, sk_sp<GrD3DResourceState>> create_msaa_resource(
72 GrD3DGpu* gpu, SkISize dimensions, int sampleCnt, const GrD3DTextureResourceInfo& info) {
73 GrD3DTextureResourceInfo msInfo;
74 sk_sp<GrD3DResourceState> msState;
75
76 // create msaa surface
Jim Van Verth2b9f53e2020-04-14 11:47:34 -040077 D3D12_RESOURCE_DESC msTextureDesc = {};
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040078 msTextureDesc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D;
79 msTextureDesc.Alignment = 0; // Default alignment (64KB)
80 msTextureDesc.Width = dimensions.fWidth;
81 msTextureDesc.Height = dimensions.fHeight;
82 msTextureDesc.DepthOrArraySize = 1;
83 msTextureDesc.MipLevels = 1;
84 msTextureDesc.Format = info.fFormat;
85 msTextureDesc.SampleDesc.Count = sampleCnt;
Greg Danielc9624d52020-04-13 15:36:31 -040086 // quality levels are only supported for tiled resources so ignore for now
87 msTextureDesc.SampleDesc.Quality = GrD3DTextureResource::kDefaultQualityLevel;
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040088 msTextureDesc.Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN; // Use default for dxgi format
Jim Van Verth6b1aabd2020-04-22 16:38:55 -040089 msTextureDesc.Flags = D3D12_RESOURCE_FLAG_ALLOW_RENDER_TARGET;
Jim Van Verthfd89e0b2020-03-26 15:33:02 -040090
Jim Van Verth280d4f72020-05-04 10:04:24 -040091 D3D12_CLEAR_VALUE clearValue = {};
92 clearValue.Format = info.fFormat;
93 clearValue.Color[0] = 1;
94 clearValue.Color[1] = 1;
95 clearValue.Color[2] = 1;
96 clearValue.Color[3] = 1;
97
Jim Van Verth2b9f53e2020-04-14 11:47:34 -040098 if (!GrD3DTextureResource::InitTextureResourceInfo(gpu, msTextureDesc,
99 D3D12_RESOURCE_STATE_RENDER_TARGET,
Jim Van Verth280d4f72020-05-04 10:04:24 -0400100 info.fProtected, &clearValue, &msInfo)) {
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400101 return {};
102 }
103
104 msState.reset(new GrD3DResourceState(
105 static_cast<D3D12_RESOURCE_STATES>(msInfo.fResourceState)));
106
107 return std::make_pair(msInfo, msState);
108}
109
110sk_sp<GrD3DTextureRenderTarget> GrD3DTextureRenderTarget::MakeNewTextureRenderTarget(
111 GrD3DGpu* gpu,
112 SkBudgeted budgeted,
113 SkISize dimensions,
114 int sampleCnt,
115 const D3D12_RESOURCE_DESC& resourceDesc,
116 GrProtected isProtected,
117 GrMipMapsStatus mipMapsStatus) {
118
119 GrD3DTextureResourceInfo info;
Jim Van Verth2b9f53e2020-04-14 11:47:34 -0400120 D3D12_RESOURCE_STATES initialState = sampleCnt > 1 ? D3D12_RESOURCE_STATE_RESOLVE_DEST
121 : D3D12_RESOURCE_STATE_RENDER_TARGET;
Jim Van Verth280d4f72020-05-04 10:04:24 -0400122
123 D3D12_CLEAR_VALUE clearValue = {};
124 clearValue.Format = resourceDesc.Format;
125 clearValue.Color[0] = 1;
126 clearValue.Color[1] = 1;
127 clearValue.Color[2] = 1;
128 clearValue.Color[3] = 1;
129
Jim Van Verth2b9f53e2020-04-14 11:47:34 -0400130 if (!GrD3DTextureResource::InitTextureResourceInfo(gpu, resourceDesc, initialState,
Jim Van Verth280d4f72020-05-04 10:04:24 -0400131 isProtected, &clearValue, &info)) {
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400132 return nullptr;
133 }
134 sk_sp<GrD3DResourceState> state(new GrD3DResourceState(
135 static_cast<D3D12_RESOURCE_STATES>(info.fResourceState)));
136
Jim Van Verth5ce94402020-05-01 14:19:13 -0400137 const D3D12_CPU_DESCRIPTOR_HANDLE renderTargetView =
138 gpu->resourceProvider().createRenderTargetView(info.fResource.get());
139
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400140 if (sampleCnt > 1) {
141 GrD3DTextureResourceInfo msInfo;
142 sk_sp<GrD3DResourceState> msState;
143
144 std::tie(msInfo, msState) = create_msaa_resource(gpu, dimensions, sampleCnt, info);
145
Jim Van Verth5ce94402020-05-01 14:19:13 -0400146 const D3D12_CPU_DESCRIPTOR_HANDLE msaaRenderTargetView =
147 gpu->resourceProvider().createRenderTargetView(msInfo.fResource.get());
148
Jim Van Verthaa90dad2020-03-30 15:00:39 -0400149 GrD3DTextureRenderTarget* trt = new GrD3DTextureRenderTarget(
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400150 gpu, budgeted, dimensions, sampleCnt, info, std::move(state),
Jim Van Verth5ce94402020-05-01 14:19:13 -0400151 msInfo, std::move(msState), msaaRenderTargetView, renderTargetView, mipMapsStatus);
Jim Van Verthaa90dad2020-03-30 15:00:39 -0400152 return sk_sp<GrD3DTextureRenderTarget>(trt);
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400153 } else {
Jim Van Verthaa90dad2020-03-30 15:00:39 -0400154 GrD3DTextureRenderTarget* trt = new GrD3DTextureRenderTarget(
Jim Van Verth5ce94402020-05-01 14:19:13 -0400155 gpu, budgeted, dimensions, info, std::move(state), renderTargetView, mipMapsStatus);
Jim Van Verthaa90dad2020-03-30 15:00:39 -0400156 return sk_sp<GrD3DTextureRenderTarget>(trt);
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400157 }
158}
159
160sk_sp<GrD3DTextureRenderTarget> GrD3DTextureRenderTarget::MakeWrappedTextureRenderTarget(
161 GrD3DGpu* gpu,
162 SkISize dimensions,
163 int sampleCnt,
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400164 GrWrapCacheable cacheable,
165 const GrD3DTextureResourceInfo& info,
166 sk_sp<GrD3DResourceState> state) {
167 // TODO: If a client uses their own heap to allocate, how do we manage that?
168 // Adopted textures require both image and allocation because we're responsible for freeing
169 //SkASSERT(VK_NULL_HANDLE != info.fImage &&
170 // (kBorrow_GrWrapOwnership == wrapOwnership || VK_NULL_HANDLE != info.fAlloc.fMemory));
171
172 GrMipMapsStatus mipMapsStatus = info.fLevelCount > 1 ? GrMipMapsStatus::kDirty
173 : GrMipMapsStatus::kNotAllocated;
174
Jim Van Verth5ce94402020-05-01 14:19:13 -0400175 const D3D12_CPU_DESCRIPTOR_HANDLE renderTargetView =
176 gpu->resourceProvider().createRenderTargetView(info.fResource.get());
177
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400178 if (sampleCnt > 1) {
179 GrD3DTextureResourceInfo msInfo;
180 sk_sp<GrD3DResourceState> msState;
181
182 std::tie(msInfo, msState) = create_msaa_resource(gpu, dimensions, sampleCnt, info);
Jim Van Verth5ce94402020-05-01 14:19:13 -0400183 const D3D12_CPU_DESCRIPTOR_HANDLE msaaRenderTargetView =
184 gpu->resourceProvider().createRenderTargetView(msInfo.fResource.get());
185
Jim Van Verthaa90dad2020-03-30 15:00:39 -0400186 GrD3DTextureRenderTarget* trt = new GrD3DTextureRenderTarget(
187 gpu, dimensions, sampleCnt, info, std::move(state), msInfo, std::move(msState),
Jim Van Verth5ce94402020-05-01 14:19:13 -0400188 msaaRenderTargetView, renderTargetView, mipMapsStatus, cacheable);
Jim Van Verthaa90dad2020-03-30 15:00:39 -0400189 return sk_sp<GrD3DTextureRenderTarget>(trt);
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400190 } else {
191 return sk_sp<GrD3DTextureRenderTarget>(new GrD3DTextureRenderTarget(
Jim Van Verth5ce94402020-05-01 14:19:13 -0400192 gpu, dimensions, info, std::move(state), renderTargetView, mipMapsStatus,
193 cacheable));
Jim Van Verthfd89e0b2020-03-26 15:33:02 -0400194 }
195}
196
197size_t GrD3DTextureRenderTarget::onGpuMemorySize() const {
198 int numColorSamples = this->numSamples();
199 if (numColorSamples > 1) {
200 // Add one to account for the resolve VkImage.
201 ++numColorSamples;
202 }
203 const GrCaps& caps = *this->getGpu()->caps();
204 return GrSurface::ComputeSize(caps, this->backendFormat(), this->dimensions(),
205 numColorSamples, // TODO: this still correct?
206 this->texturePriv().mipMapped());
207}