Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/d2d1/bitmap_render_target.c | 8 +++- dlls/d2d1/device.c | 4 +- dlls/d2d1/tests/d2d1.c | 67 ++++++++++++++++++++++++++++++-- 3 files changed, 73 insertions(+), 6 deletions(-)
diff --git a/dlls/d2d1/bitmap_render_target.c b/dlls/d2d1/bitmap_render_target.c index 57f5b23b51..6cea50972f 100644 --- a/dlls/d2d1/bitmap_render_target.c +++ b/dlls/d2d1/bitmap_render_target.c @@ -722,6 +722,11 @@ static const struct ID2D1BitmapRenderTargetVtbl d2d_bitmap_render_target_vtbl = d2d_bitmap_render_target_GetBitmap };
+static const struct d2d_device_context_ops d2d_bitmap_render_target_ops = +{ + NULL, +}; + HRESULT d2d_bitmap_render_target_init(struct d2d_bitmap_render_target *render_target, const struct d2d_device_context *parent_target, const D2D1_SIZE_F *size, const D2D1_SIZE_U *pixel_size, const D2D1_PIXEL_FORMAT *pixel_format, @@ -805,7 +810,8 @@ HRESULT d2d_bitmap_render_target_init(struct d2d_bitmap_render_target *render_ta }
if (FAILED(hr = d2d_d3d_create_render_target(parent_target->factory, dxgi_surface, - (IUnknown *)&render_target->ID2D1BitmapRenderTarget_iface, NULL, + (IUnknown *)&render_target->ID2D1BitmapRenderTarget_iface, + parent_target->ops ? &d2d_bitmap_render_target_ops : NULL, &dxgi_rt_desc, (void **)&render_target->dxgi_inner))) { WARN("Failed to create DXGI surface render target, hr %#x.\n", hr); diff --git a/dlls/d2d1/device.c b/dlls/d2d1/device.c index d20377b5c2..f1d0dad45e 100644 --- a/dlls/d2d1/device.c +++ b/dlls/d2d1/device.c @@ -1515,7 +1515,7 @@ static HRESULT STDMETHODCALLTYPE d2d_device_context_Flush(ID2D1DeviceContext *if
FIXME("iface %p, tag1 %p, tag2 %p stub!\n", iface, tag1, tag2);
- if (context->ops) + if (context->ops && context->ops->device_context_present) context->ops->device_context_present(context->outer_unknown);
return E_NOTIMPL; @@ -1693,7 +1693,7 @@ static HRESULT STDMETHODCALLTYPE d2d_device_context_EndDraw(ID2D1DeviceContext * if (tag2) *tag2 = context->error.tag2;
- if (context->ops) + if (context->ops && context->ops->device_context_present) { if (FAILED(hr = context->ops->device_context_present(context->outer_unknown))) context->error.code = hr; diff --git a/dlls/d2d1/tests/d2d1.c b/dlls/d2d1/tests/d2d1.c index 4136b69885..9e6ce06543 100644 --- a/dlls/d2d1/tests/d2d1.c +++ b/dlls/d2d1/tests/d2d1.c @@ -6705,8 +6705,10 @@ static void check_rt_bitmap_surface_(unsigned int line, ID2D1RenderTarget *rt, B ID2D1RenderTarget *compatible_rt; IWICImagingFactory *wic_factory; ID2D1DeviceContext *context; + ID2D1DCRenderTarget *dc_rt; IWICBitmap *wic_bitmap; ID2D1Bitmap *bitmap; + ID2D1Image *target; D2D1_SIZE_U size; HRESULT hr;
@@ -6749,13 +6751,37 @@ static void check_rt_bitmap_surface_(unsigned int line, ID2D1RenderTarget *rt, B
CoUninitialize();
- if (FAILED(ID2D1RenderTarget_QueryInterface(rt, &IID_ID2D1DeviceContext, (void **)&context))) + /* Compatible target follows its parent. */ + hr = ID2D1RenderTarget_QueryInterface(rt, &IID_ID2D1DeviceContext, (void **)&context); + ok_(__FILE__, line)(SUCCEEDED(hr), "Failed to get device context, hr %#x.\n", hr); + + dc_rt = NULL; + ID2D1RenderTarget_QueryInterface(rt, &IID_ID2D1DCRenderTarget, (void **)&dc_rt); + + bitmap = NULL; + target = NULL; + ID2D1DeviceContext_GetTarget(context, &target); + if (target && FAILED(ID2D1Image_QueryInterface(target, &IID_ID2D1Bitmap, (void **)&bitmap))) + { + ID2D1Image_Release(target); + target = NULL; + } + if (bitmap) + ID2D1Bitmap_Release(bitmap); + + /* Pixel format is not defined until target is set, for DC target it's specified on creation. */ + if (target || dc_rt) { - /* Compatible target follows its parent. */ + ID2D1DeviceContext *context2; + hr = ID2D1RenderTarget_CreateCompatibleRenderTarget(rt, NULL, NULL, NULL, D2D1_COMPATIBLE_RENDER_TARGET_OPTIONS_NONE, (ID2D1BitmapRenderTarget **)&compatible_rt); ok_(__FILE__, line)(SUCCEEDED(hr), "Failed to create compatible render target, hr %#x.\n", hr);
+ hr = ID2D1RenderTarget_QueryInterface(compatible_rt, &IID_ID2D1DeviceContext, (void **)&context2); + ok_(__FILE__, line)(SUCCEEDED(hr), "Failed to get device context, hr %#x.\n", hr); + ID2D1DeviceContext_Release(context2); + hr = ID2D1RenderTarget_CreateBitmap(compatible_rt, size, bitmap_data, sizeof(*bitmap_data), &bitmap_desc, &bitmap); ok_(__FILE__, line)(SUCCEEDED(hr), "Failed to create bitmap, hr %#x.\n", hr);
@@ -6765,7 +6791,18 @@ static void check_rt_bitmap_surface_(unsigned int line, ID2D1RenderTarget *rt, B ID2D1Bitmap_Release(bitmap); } else - ID2D1DeviceContext_Release(context); + { + hr = ID2D1RenderTarget_CreateCompatibleRenderTarget(rt, NULL, NULL, NULL, + D2D1_COMPATIBLE_RENDER_TARGET_OPTIONS_NONE, (ID2D1BitmapRenderTarget **)&compatible_rt); + todo_wine + ok_(__FILE__, line)(hr == WINCODEC_ERR_UNSUPPORTEDPIXELFORMAT, " --- Unexpected hr %#x.\n", hr); + } + + ID2D1DeviceContext_Release(context); + if (target) + ID2D1Image_Release(target); + if (dc_rt) + ID2D1DCRenderTarget_Release(dc_rt); }
static void test_bitmap_surface(void) @@ -6782,6 +6819,7 @@ static void test_bitmap_surface(void) IDXGISurface *surface; ID2D1Bitmap1 *bitmap; ID2D1Device *device; + ID2D1Image *target; HWND window; HRESULT hr;
@@ -6809,7 +6847,23 @@ static void test_bitmap_surface(void) rt = create_render_target(surface); ok(!!rt, "Failed to create render target.\n");
+ hr = ID2D1RenderTarget_QueryInterface(rt, &IID_ID2D1DeviceContext, (void **)&device_context); + ok(SUCCEEDED(hr), "Failed to get device context, hr %#x.\n", hr); + + bitmap = NULL; + ID2D1DeviceContext_GetTarget(device_context, (ID2D1Image **)&bitmap); +todo_wine + ok(!!bitmap, "Unexpected target.\n"); + +if (bitmap) +{ + check_bitmap_surface((ID2D1Bitmap *)bitmap, TRUE, D2D1_BITMAP_OPTIONS_TARGET | D2D1_BITMAP_OPTIONS_CANNOT_DRAW); + ID2D1Bitmap1_Release(bitmap); +} check_rt_bitmap_surface(rt, TRUE, D2D1_BITMAP_OPTIONS_NONE); + + ID2D1DeviceContext_Release(device_context); + ID2D1RenderTarget_Release(rt);
/* Bitmap created from DXGI surface. */ @@ -6836,7 +6890,14 @@ if (SUCCEEDED(hr)) check_bitmap_surface((ID2D1Bitmap *)bitmap, TRUE, D2D1_BITMAP_OPTIONS_TARGET | D2D1_BITMAP_OPTIONS_CANNOT_DRAW); check_rt_bitmap_surface((ID2D1RenderTarget *)device_context, TRUE, D2D1_BITMAP_OPTIONS_NONE);
+ ID2D1DeviceContext_SetTarget(device_context, (ID2D1Image *)bitmap); + ID2D1DeviceContext_GetTarget(device_context, &target); + ok(target == (ID2D1Image *)bitmap, "Unexpected target.\n"); + + check_rt_bitmap_surface((ID2D1RenderTarget *)device_context, TRUE, D2D1_BITMAP_OPTIONS_NONE); + ID2D1DeviceContext_Release(device_context); + ID2D1Bitmap1_Release(bitmap); } ID2D1Device_Release(device); IDXGIDevice_Release(dxgi_device);
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/d2d1/tests/d2d1.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
diff --git a/dlls/d2d1/tests/d2d1.c b/dlls/d2d1/tests/d2d1.c index 9e6ce06543..65ab5c258b 100644 --- a/dlls/d2d1/tests/d2d1.c +++ b/dlls/d2d1/tests/d2d1.c @@ -6772,14 +6772,26 @@ static void check_rt_bitmap_surface_(unsigned int line, ID2D1RenderTarget *rt, B /* Pixel format is not defined until target is set, for DC target it's specified on creation. */ if (target || dc_rt) { + ID2D1Device *device = NULL, *device2 = NULL; ID2D1DeviceContext *context2;
+ ID2D1DeviceContext_GetDevice(context, &device); + hr = ID2D1RenderTarget_CreateCompatibleRenderTarget(rt, NULL, NULL, NULL, D2D1_COMPATIBLE_RENDER_TARGET_OPTIONS_NONE, (ID2D1BitmapRenderTarget **)&compatible_rt); ok_(__FILE__, line)(SUCCEEDED(hr), "Failed to create compatible render target, hr %#x.\n", hr);
hr = ID2D1RenderTarget_QueryInterface(compatible_rt, &IID_ID2D1DeviceContext, (void **)&context2); ok_(__FILE__, line)(SUCCEEDED(hr), "Failed to get device context, hr %#x.\n", hr); + + ID2D1DeviceContext_GetDevice(context2, &device2); + ok_(__FILE__, line)(device == device2, "Unexpected device.\n"); + + if (device) + ID2D1Device_Release(device); + if (device2) + ID2D1Device_Release(device2); + ID2D1DeviceContext_Release(context2);
hr = ID2D1RenderTarget_CreateBitmap(compatible_rt, size, bitmap_data, sizeof(*bitmap_data), &bitmap_desc, &bitmap);
Signed-off-by: Henri Verbeet hverbeet@codeweavers.com
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/d2d1/bitmap.c | 10 ++--- dlls/d2d1/bitmap_render_target.c | 4 +- dlls/d2d1/brush.c | 2 +- dlls/d2d1/d2d1_private.h | 17 ++++---- dlls/d2d1/dc_render_target.c | 28 +++++++++--- dlls/d2d1/device.c | 74 ++++++++++++++++++-------------- dlls/d2d1/factory.c | 28 ++++++++++-- dlls/d2d1/hwnd_render_target.c | 33 +++++++++++--- dlls/d2d1/tests/d2d1.c | 8 ++-- dlls/d2d1/wic_render_target.c | 33 +++++++++++--- 10 files changed, 161 insertions(+), 76 deletions(-)
diff --git a/dlls/d2d1/bitmap.c b/dlls/d2d1/bitmap.c index 01dc829a1c..c8d099c7df 100644 --- a/dlls/d2d1/bitmap.c +++ b/dlls/d2d1/bitmap.c @@ -330,14 +330,14 @@ HRESULT d2d_bitmap_create(struct d2d_device_context *context, D2D1_SIZE_U size, resource_data.pSysMem = src_data; resource_data.SysMemPitch = pitch;
- if (FAILED(hr = ID3D10Device_CreateTexture2D(context->device, &texture_desc, + if (FAILED(hr = ID3D10Device_CreateTexture2D(context->d3d_device, &texture_desc, src_data ? &resource_data : NULL, &texture))) { ERR("Failed to create texture, hr %#x.\n", hr); return hr; }
- hr = ID3D10Device_CreateShaderResourceView(context->device, (ID3D10Resource *)texture, NULL, &view); + hr = ID3D10Device_CreateShaderResourceView(context->d3d_device, (ID3D10Resource *)texture, NULL, &view); ID3D10Texture2D_Release(texture); if (FAILED(hr)) { @@ -375,7 +375,7 @@ HRESULT d2d_bitmap_create_shared(struct d2d_device_context *context, REFIID iid,
ID3D10ShaderResourceView_GetDevice(src_impl->view, &device); ID3D10Device_Release(device); - if (device != context->device) + if (device != context->d3d_device) { hr = D2DERR_UNSUPPORTED_OPERATION; goto failed; @@ -430,13 +430,13 @@ HRESULT d2d_bitmap_create_shared(struct d2d_device_context *context, REFIID iid,
ID3D10Resource_GetDevice(resource, &device); ID3D10Device_Release(device); - if (device != context->device) + if (device != context->d3d_device) { ID3D10Resource_Release(resource); return D2DERR_UNSUPPORTED_OPERATION; }
- hr = ID3D10Device_CreateShaderResourceView(context->device, resource, NULL, &view); + hr = ID3D10Device_CreateShaderResourceView(context->d3d_device, resource, NULL, &view); ID3D10Resource_Release(resource); if (FAILED(hr)) { diff --git a/dlls/d2d1/bitmap_render_target.c b/dlls/d2d1/bitmap_render_target.c index 6cea50972f..7411d48892 100644 --- a/dlls/d2d1/bitmap_render_target.c +++ b/dlls/d2d1/bitmap_render_target.c @@ -795,7 +795,7 @@ HRESULT d2d_bitmap_render_target_init(struct d2d_bitmap_render_target *render_ta texture_desc.CPUAccessFlags = 0; texture_desc.MiscFlags = 0;
- if (FAILED(hr = ID3D10Device_CreateTexture2D(parent_target->device, &texture_desc, NULL, &texture))) + if (FAILED(hr = ID3D10Device_CreateTexture2D(parent_target->d3d_device, &texture_desc, NULL, &texture))) { WARN("Failed to create texture, hr %#x.\n", hr); return hr; @@ -809,7 +809,7 @@ HRESULT d2d_bitmap_render_target_init(struct d2d_bitmap_render_target *render_ta return hr; }
- if (FAILED(hr = d2d_d3d_create_render_target(parent_target->factory, dxgi_surface, + if (FAILED(hr = d2d_d3d_create_render_target(parent_target->device, dxgi_surface, (IUnknown *)&render_target->ID2D1BitmapRenderTarget_iface, parent_target->ops ? &d2d_bitmap_render_target_ops : NULL, &dxgi_rt_desc, (void **)&render_target->dxgi_inner))) diff --git a/dlls/d2d1/brush.c b/dlls/d2d1/brush.c index b03af89211..30a4235cda 100644 --- a/dlls/d2d1/brush.c +++ b/dlls/d2d1/brush.c @@ -1288,7 +1288,7 @@ HRESULT d2d_brush_get_ps_cb(struct d2d_brush *brush, struct d2d_brush *opacity_b buffer_data.SysMemPitch = 0; buffer_data.SysMemSlicePitch = 0;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, ps_cb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, ps_cb))) ERR("Failed to create constant buffer, hr %#x.\n", hr);
return hr; diff --git a/dlls/d2d1/d2d1_private.h b/dlls/d2d1/d2d1_private.h index d7989f93a2..2d3acd5997 100644 --- a/dlls/d2d1/d2d1_private.h +++ b/dlls/d2d1/d2d1_private.h @@ -134,7 +134,8 @@ struct d2d_device_context const struct d2d_device_context_ops *ops;
ID2D1Factory *factory; - ID3D10Device *device; + ID2D1Device *device; + ID3D10Device *d3d_device; ID3D10RenderTargetView *view; ID3D10StateBlock *stateblock; struct d2d_shape_resources shape_resources[D2D_SHAPE_TYPE_COUNT]; @@ -155,7 +156,7 @@ struct d2d_device_context struct d2d_clip_stack clip_stack; };
-HRESULT d2d_d3d_create_render_target(ID2D1Factory *factory, IDXGISurface *surface, IUnknown *outer_unknown, +HRESULT d2d_d3d_create_render_target(ID2D1Device *device, IDXGISurface *surface, IUnknown *outer_unknown, const struct d2d_device_context_ops *ops, const D2D1_RENDER_TARGET_PROPERTIES *desc, void **render_target) DECLSPEC_HIDDEN; HRESULT d2d_d3d_render_target_create_rtv(ID2D1RenderTarget *render_target, IDXGISurface1 *surface) DECLSPEC_HIDDEN; @@ -181,8 +182,8 @@ struct d2d_wic_render_target unsigned int bpp; };
-HRESULT d2d_wic_render_target_init(struct d2d_wic_render_target *render_target, ID2D1Factory *factory, - ID3D10Device1 *device, IWICBitmap *bitmap, const D2D1_RENDER_TARGET_PROPERTIES *desc) DECLSPEC_HIDDEN; +HRESULT d2d_wic_render_target_init(struct d2d_wic_render_target *render_target, ID2D1Factory1 *factory, + ID3D10Device1 *d3d_device, IWICBitmap *bitmap, const D2D1_RENDER_TARGET_PROPERTIES *desc) DECLSPEC_HIDDEN;
struct d2d_dc_render_target { @@ -197,8 +198,8 @@ struct d2d_dc_render_target HDC hdc; };
-HRESULT d2d_dc_render_target_init(struct d2d_dc_render_target *render_target, ID2D1Factory *factory, - ID3D10Device1 *device, const D2D1_RENDER_TARGET_PROPERTIES *desc) DECLSPEC_HIDDEN; +HRESULT d2d_dc_render_target_init(struct d2d_dc_render_target *render_target, ID2D1Factory1 *factory, + ID3D10Device1 *d3d_device, const D2D1_RENDER_TARGET_PROPERTIES *desc) DECLSPEC_HIDDEN;
struct d2d_hwnd_render_target { @@ -212,8 +213,8 @@ struct d2d_hwnd_render_target HWND hwnd; };
-HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target, ID2D1Factory *factory, - ID3D10Device1 *device, const D2D1_RENDER_TARGET_PROPERTIES *desc, +HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target, ID2D1Factory1 *factory, + ID3D10Device1 *d3d_device, const D2D1_RENDER_TARGET_PROPERTIES *desc, const D2D1_HWND_RENDER_TARGET_PROPERTIES *hwnd_desc) DECLSPEC_HIDDEN;
struct d2d_bitmap_render_target diff --git a/dlls/d2d1/dc_render_target.c b/dlls/d2d1/dc_render_target.c index 8e43bcc307..050adf6dd6 100644 --- a/dlls/d2d1/dc_render_target.c +++ b/dlls/d2d1/dc_render_target.c @@ -813,11 +813,13 @@ static const struct d2d_device_context_ops d2d_dc_render_target_ops = d2d_dc_render_target_present, };
-HRESULT d2d_dc_render_target_init(struct d2d_dc_render_target *render_target, ID2D1Factory *factory, - ID3D10Device1 *device, const D2D1_RENDER_TARGET_PROPERTIES *desc) +HRESULT d2d_dc_render_target_init(struct d2d_dc_render_target *render_target, ID2D1Factory1 *factory, + ID3D10Device1 *d3d_device, const D2D1_RENDER_TARGET_PROPERTIES *desc) { D3D10_TEXTURE2D_DESC texture_desc; ID3D10Texture2D *texture; + IDXGIDevice *dxgi_device; + ID2D1Device *device; HRESULT hr;
render_target->ID2D1DCRenderTarget_iface.lpVtbl = &d2d_dc_render_target_vtbl; @@ -852,7 +854,7 @@ HRESULT d2d_dc_render_target_init(struct d2d_dc_render_target *render_target, ID texture_desc.CPUAccessFlags = 0; texture_desc.MiscFlags = D3D10_RESOURCE_MISC_GDI_COMPATIBLE;
- if (FAILED(hr = ID3D10Device1_CreateTexture2D(device, &texture_desc, NULL, &texture))) + if (FAILED(hr = ID3D10Device1_CreateTexture2D(d3d_device, &texture_desc, NULL, &texture))) { WARN("Failed to create texture, hr %#x.\n", hr); return hr; @@ -866,9 +868,25 @@ HRESULT d2d_dc_render_target_init(struct d2d_dc_render_target *render_target, ID return hr; }
- if (FAILED(hr = d2d_d3d_create_render_target(factory, (IDXGISurface *)render_target->dxgi_surface, + if (FAILED(hr = ID3D10Device1_QueryInterface(d3d_device, &IID_IDXGIDevice, (void **)&dxgi_device))) + { + WARN("Failed to get DXGI device interface, hr %#x.\n", hr); + return hr; + } + + hr = ID2D1Factory1_CreateDevice(factory, dxgi_device, &device); + IDXGIDevice_Release(dxgi_device); + if (FAILED(hr)) + { + WARN("Failed to create D2D device, hr %#x.\n", hr); + return hr; + } + + hr = d2d_d3d_create_render_target(device, (IDXGISurface *)render_target->dxgi_surface, (IUnknown *)&render_target->ID2D1DCRenderTarget_iface, &d2d_dc_render_target_ops, - desc, (void **)&render_target->dxgi_inner))) + desc, (void **)&render_target->dxgi_inner); + ID2D1Device_Release(device); + if (FAILED(hr)) { WARN("Failed to create DXGI surface render target, hr %#x.\n", hr); IDXGISurface1_Release(render_target->dxgi_surface); diff --git a/dlls/d2d1/device.c b/dlls/d2d1/device.c index f1d0dad45e..be8b7eab03 100644 --- a/dlls/d2d1/device.c +++ b/dlls/d2d1/device.c @@ -123,7 +123,7 @@ static void d2d_device_context_draw(struct d2d_device_context *render_target, en ID3D10Buffer *vs_cb, ID3D10Buffer *ps_cb, struct d2d_brush *brush, struct d2d_brush *opacity_brush) { struct d2d_shape_resources *shape_resources = &render_target->shape_resources[shape_type]; - ID3D10Device *device = render_target->device; + ID3D10Device *device = render_target->d3d_device; D3D10_RECT scissor_rect; unsigned int offset; D3D10_VIEWPORT vp; @@ -273,8 +273,9 @@ static ULONG STDMETHODCALLTYPE d2d_device_context_inner_Release(IUnknown *iface) } context->stateblock->lpVtbl->Release(context->stateblock); ID3D10RenderTargetView_Release(context->view); - ID3D10Device_Release(context->device); + ID3D10Device_Release(context->d3d_device); ID2D1Factory_Release(context->factory); + ID2D1Device_Release(context->device); heap_free(context); }
@@ -441,7 +442,7 @@ static HRESULT STDMETHODCALLTYPE d2d_device_context_CreateGradientStopCollection TRACE("iface %p, stops %p, stop_count %u, gamma %#x, extend_mode %#x, gradient %p.\n", iface, stops, stop_count, gamma, extend_mode, gradient);
- if (SUCCEEDED(hr = d2d_gradient_create(render_target->factory, render_target->device, + if (SUCCEEDED(hr = d2d_gradient_create(render_target->factory, render_target->d3d_device, stops, stop_count, gamma, extend_mode, &object))) *gradient = &object->ID2D1GradientStopCollection_iface;
@@ -746,7 +747,7 @@ static void d2d_device_context_draw_geometry(struct d2d_device_context *render_t buffer_data.SysMemPitch = 0; buffer_data.SysMemSlicePitch = 0;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vs_cb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vs_cb))) { WARN("Failed to create constant buffer, hr %#x.\n", hr); return; @@ -765,7 +766,7 @@ static void d2d_device_context_draw_geometry(struct d2d_device_context *render_t buffer_desc.BindFlags = D3D10_BIND_INDEX_BUFFER; buffer_data.pSysMem = geometry->outline.faces;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &ib))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &ib))) { WARN("Failed to create index buffer, hr %#x.\n", hr); goto done; @@ -775,7 +776,7 @@ static void d2d_device_context_draw_geometry(struct d2d_device_context *render_t buffer_desc.BindFlags = D3D10_BIND_VERTEX_BUFFER; buffer_data.pSysMem = geometry->outline.vertices;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vb))) { ERR("Failed to create vertex buffer, hr %#x.\n", hr); ID3D10Buffer_Release(ib); @@ -795,7 +796,7 @@ static void d2d_device_context_draw_geometry(struct d2d_device_context *render_t buffer_desc.BindFlags = D3D10_BIND_INDEX_BUFFER; buffer_data.pSysMem = geometry->outline.bezier_faces;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &ib))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &ib))) { WARN("Failed to create beziers index buffer, hr %#x.\n", hr); goto done; @@ -805,7 +806,7 @@ static void d2d_device_context_draw_geometry(struct d2d_device_context *render_t buffer_desc.BindFlags = D3D10_BIND_VERTEX_BUFFER; buffer_data.pSysMem = geometry->outline.beziers;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vb))) { ERR("Failed to create beziers vertex buffer, hr %#x.\n", hr); ID3D10Buffer_Release(ib); @@ -894,7 +895,7 @@ static void d2d_device_context_fill_geometry(struct d2d_device_context *render_t buffer_data.SysMemPitch = 0; buffer_data.SysMemSlicePitch = 0;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vs_cb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vs_cb))) { WARN("Failed to create constant buffer, hr %#x.\n", hr); return; @@ -913,7 +914,7 @@ static void d2d_device_context_fill_geometry(struct d2d_device_context *render_t buffer_desc.BindFlags = D3D10_BIND_INDEX_BUFFER; buffer_data.pSysMem = geometry->fill.faces;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &ib))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &ib))) { WARN("Failed to create index buffer, hr %#x.\n", hr); goto done; @@ -923,7 +924,7 @@ static void d2d_device_context_fill_geometry(struct d2d_device_context *render_t buffer_desc.BindFlags = D3D10_BIND_VERTEX_BUFFER; buffer_data.pSysMem = geometry->fill.vertices;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vb))) { ERR("Failed to create vertex buffer, hr %#x.\n", hr); ID3D10Buffer_Release(ib); @@ -942,7 +943,7 @@ static void d2d_device_context_fill_geometry(struct d2d_device_context *render_t buffer_desc.ByteWidth = geometry->fill.bezier_vertex_count * sizeof(*geometry->fill.bezier_vertices); buffer_data.pSysMem = geometry->fill.bezier_vertices;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vb))) { ERR("Failed to create beziers vertex buffer, hr %#x.\n", hr); goto done; @@ -1634,7 +1635,7 @@ static void STDMETHODCALLTYPE d2d_device_context_Clear(ID2D1DeviceContext *iface buffer_data.SysMemPitch = 0; buffer_data.SysMemSlicePitch = 0;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &vs_cb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &vs_cb))) { WARN("Failed to create constant buffer, hr %#x.\n", hr); return; @@ -1657,7 +1658,7 @@ static void STDMETHODCALLTYPE d2d_device_context_Clear(ID2D1DeviceContext *iface buffer_desc.ByteWidth = sizeof(ps_cb_data); buffer_data.pSysMem = &ps_cb_data;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, &buffer_desc, &buffer_data, &ps_cb))) + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &ps_cb))) { WARN("Failed to create constant buffer, hr %#x.\n", hr); ID3D10Buffer_Release(vs_cb); @@ -1952,7 +1953,12 @@ static HRESULT STDMETHODCALLTYPE d2d_device_context_GetGlyphRunWorldBounds(ID2D1
static void STDMETHODCALLTYPE d2d_device_context_GetDevice(ID2D1DeviceContext *iface, ID2D1Device **device) { - FIXME("iface %p, device %p stub!\n", iface, device); + struct d2d_device_context *context = impl_from_ID2D1DeviceContext(iface); + + TRACE("iface %p, device %p.\n", iface, device); + + *device = context->device; + ID2D1Device_AddRef(*device); }
static void STDMETHODCALLTYPE d2d_device_context_SetTarget(ID2D1DeviceContext *iface, ID2D1Image *target) @@ -2574,7 +2580,7 @@ static const struct ID2D1GdiInteropRenderTargetVtbl d2d_gdi_interop_render_targe d2d_gdi_interop_render_target_ReleaseDC, };
-static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, ID2D1Factory *factory, +static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, ID2D1Device *device, IDXGISurface *surface, IUnknown *outer_unknown, const struct d2d_device_context_ops *ops, const D2D1_RENDER_TARGET_PROPERTIES *desc) { @@ -3460,13 +3466,14 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, render_target->IDWriteTextRenderer_iface.lpVtbl = &d2d_text_renderer_vtbl; render_target->IUnknown_iface.lpVtbl = &d2d_device_context_inner_unknown_vtbl; render_target->refcount = 1; - render_target->factory = factory; - ID2D1Factory_AddRef(render_target->factory); + ID2D1Device_GetFactory(device, &render_target->factory); + render_target->device = device; + ID2D1Device_AddRef(render_target->device);
render_target->outer_unknown = outer_unknown ? outer_unknown : &render_target->IUnknown_iface; render_target->ops = ops;
- if (FAILED(hr = IDXGISurface_GetDevice(surface, &IID_ID3D10Device, (void **)&render_target->device))) + if (FAILED(hr = IDXGISurface_GetDevice(surface, &IID_ID3D10Device, (void **)&render_target->d3d_device))) { WARN("Failed to get device interface, hr %#x.\n", hr); ID2D1Factory_Release(render_target->factory); @@ -3479,7 +3486,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, goto err; }
- hr = ID3D10Device_CreateRenderTargetView(render_target->device, resource, NULL, &render_target->view); + hr = ID3D10Device_CreateRenderTargetView(render_target->d3d_device, resource, NULL, &render_target->view); ID3D10Resource_Release(resource); if (FAILED(hr)) { @@ -3493,7 +3500,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, goto err; }
- if (FAILED(hr = D3D10CreateStateBlock(render_target->device, &state_mask, &render_target->stateblock))) + if (FAILED(hr = D3D10CreateStateBlock(render_target->d3d_device, &state_mask, &render_target->stateblock))) { WARN("Failed to create stateblock, hr %#x.\n", hr); goto err; @@ -3503,14 +3510,14 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, { const struct shape_info *si = &shape_info[i];
- if (FAILED(hr = ID3D10Device_CreateInputLayout(render_target->device, si->il_desc, si->il_element_count, + if (FAILED(hr = ID3D10Device_CreateInputLayout(render_target->d3d_device, si->il_desc, si->il_element_count, si->vs_code, si->vs_code_size, &render_target->shape_resources[si->shape_type].il))) { WARN("Failed to create input layout for shape type %#x, hr %#x.\n", si->shape_type, hr); goto err; }
- if (FAILED(hr = ID3D10Device_CreateVertexShader(render_target->device, si->vs_code, + if (FAILED(hr = ID3D10Device_CreateVertexShader(render_target->d3d_device, si->vs_code, si->vs_code_size, &render_target->shape_resources[si->shape_type].vs))) { WARN("Failed to create vertex shader for shape type %#x, hr %#x.\n", si->shape_type, hr); @@ -3519,7 +3526,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target,
}
- if (FAILED(hr = ID3D10Device_CreatePixelShader(render_target->device, + if (FAILED(hr = ID3D10Device_CreatePixelShader(render_target->d3d_device, ps_code, sizeof(ps_code), &render_target->ps))) { WARN("Failed to create pixel shader, hr %#x.\n", hr); @@ -3536,7 +3543,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, buffer_data.SysMemPitch = 0; buffer_data.SysMemSlicePitch = 0;
- if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &render_target->ib))) { WARN("Failed to create clear index buffer, hr %#x.\n", hr); @@ -3548,7 +3555,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, buffer_data.pSysMem = quad;
render_target->vb_stride = sizeof(*quad); - if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->device, + if (FAILED(hr = ID3D10Device_CreateBuffer(render_target->d3d_device, &buffer_desc, &buffer_data, &render_target->vb))) { WARN("Failed to create clear vertex buffer, hr %#x.\n", hr); @@ -3565,7 +3572,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, rs_desc.ScissorEnable = TRUE; rs_desc.MultisampleEnable = FALSE; rs_desc.AntialiasedLineEnable = FALSE; - if (FAILED(hr = ID3D10Device_CreateRasterizerState(render_target->device, &rs_desc, &render_target->rs))) + if (FAILED(hr = ID3D10Device_CreateRasterizerState(render_target->d3d_device, &rs_desc, &render_target->rs))) { WARN("Failed to create clear rasterizer state, hr %#x.\n", hr); goto err; @@ -3588,7 +3595,7 @@ static HRESULT d2d_device_context_init(struct d2d_device_context *render_target, } blend_desc.BlendOpAlpha = D3D10_BLEND_OP_ADD; blend_desc.RenderTargetWriteMask[0] = D3D10_COLOR_WRITE_ENABLE_ALL; - if (FAILED(hr = ID3D10Device_CreateBlendState(render_target->device, &blend_desc, &render_target->bs))) + if (FAILED(hr = ID3D10Device_CreateBlendState(render_target->d3d_device, &blend_desc, &render_target->bs))) { WARN("Failed to create blend state, hr %#x.\n", hr); goto err; @@ -3656,13 +3663,14 @@ err: render_target->stateblock->lpVtbl->Release(render_target->stateblock); if (render_target->view) ID3D10RenderTargetView_Release(render_target->view); - if (render_target->device) - ID3D10Device_Release(render_target->device); + if (render_target->d3d_device) + ID3D10Device_Release(render_target->d3d_device); + ID2D1Device_Release(render_target->device); ID2D1Factory_Release(render_target->factory); return hr; }
-HRESULT d2d_d3d_create_render_target(ID2D1Factory *factory, IDXGISurface *surface, IUnknown *outer_unknown, +HRESULT d2d_d3d_create_render_target(ID2D1Device *device, IDXGISurface *surface, IUnknown *outer_unknown, const struct d2d_device_context_ops *ops, const D2D1_RENDER_TARGET_PROPERTIES *desc, void **render_target) { struct d2d_device_context *object; @@ -3671,7 +3679,7 @@ HRESULT d2d_d3d_create_render_target(ID2D1Factory *factory, IDXGISurface *surfac if (!(object = heap_alloc_zero(sizeof(*object)))) return E_OUTOFMEMORY;
- if (FAILED(hr = d2d_device_context_init(object, factory, surface, outer_unknown, ops, desc))) + if (FAILED(hr = d2d_device_context_init(object, device, surface, outer_unknown, ops, desc))) { WARN("Failed to initialize render target, hr %#x.\n", hr); heap_free(object); @@ -3711,7 +3719,7 @@ HRESULT d2d_d3d_render_target_create_rtv(ID2D1RenderTarget *iface, IDXGISurface1 return hr; }
- hr = ID3D10Device_CreateRenderTargetView(render_target->device, resource, NULL, &view); + hr = ID3D10Device_CreateRenderTargetView(render_target->d3d_device, resource, NULL, &view); ID3D10Resource_Release(resource); if (FAILED(hr)) { diff --git a/dlls/d2d1/factory.c b/dlls/d2d1/factory.c index 5ce21f6f15..29038ec91e 100644 --- a/dlls/d2d1/factory.c +++ b/dlls/d2d1/factory.c @@ -300,7 +300,7 @@ static HRESULT STDMETHODCALLTYPE d2d_factory_CreateWicBitmapRenderTarget(ID2D1Fa return hr; }
- if (FAILED(hr = d2d_wic_render_target_init(object, (ID2D1Factory *)iface, device, target, desc))) + if (FAILED(hr = d2d_wic_render_target_init(object, iface, device, target, desc))) { WARN("Failed to initialize render target, hr %#x.\n", hr); heap_free(object); @@ -330,7 +330,7 @@ static HRESULT STDMETHODCALLTYPE d2d_factory_CreateHwndRenderTarget(ID2D1Factory if (!(object = heap_alloc_zero(sizeof(*object)))) return E_OUTOFMEMORY;
- if (FAILED(hr = d2d_hwnd_render_target_init(object, (ID2D1Factory *)iface, device, desc, hwnd_rt_desc))) + if (FAILED(hr = d2d_hwnd_render_target_init(object, iface, device, desc, hwnd_rt_desc))) { WARN("Failed to initialize render target, hr %#x.\n", hr); heap_free(object); @@ -346,9 +346,29 @@ static HRESULT STDMETHODCALLTYPE d2d_factory_CreateHwndRenderTarget(ID2D1Factory static HRESULT STDMETHODCALLTYPE d2d_factory_CreateDxgiSurfaceRenderTarget(ID2D1Factory1 *iface, IDXGISurface *surface, const D2D1_RENDER_TARGET_PROPERTIES *desc, ID2D1RenderTarget **render_target) { + IDXGIDevice *dxgi_device; + ID2D1Device *device; + HRESULT hr; + TRACE("iface %p, surface %p, desc %p, render_target %p.\n", iface, surface, desc, render_target);
- return d2d_d3d_create_render_target((ID2D1Factory *)iface, surface, NULL, NULL, desc, (void **)render_target); + if (FAILED(hr = IDXGISurface_GetDevice(surface, &IID_IDXGIDevice, (void **)&dxgi_device))) + { + WARN("Failed to get DXGI device, hr %#x.\n", hr); + return hr; + } + + hr = ID2D1Factory1_CreateDevice(iface, dxgi_device, &device); + IDXGIDevice_Release(dxgi_device); + if (FAILED(hr)) + { + WARN("Failed to create D2D device, hr %#x.\n", hr); + return hr; + } + + hr = d2d_d3d_create_render_target(device, surface, NULL, NULL, desc, (void **)render_target); + ID2D1Device_Release(device); + return hr; }
static HRESULT STDMETHODCALLTYPE d2d_factory_CreateDCRenderTarget(ID2D1Factory1 *iface, @@ -367,7 +387,7 @@ static HRESULT STDMETHODCALLTYPE d2d_factory_CreateDCRenderTarget(ID2D1Factory1 if (!(object = heap_alloc_zero(sizeof(*object)))) return E_OUTOFMEMORY;
- if (FAILED(hr = d2d_dc_render_target_init(object, (ID2D1Factory *)iface, device, desc))) + if (FAILED(hr = d2d_dc_render_target_init(object, iface, device, desc))) { WARN("Failed to initialize render target, hr %#x.\n", hr); heap_free(object); diff --git a/dlls/d2d1/hwnd_render_target.c b/dlls/d2d1/hwnd_render_target.c index 1e76326119..2c9481e576 100644 --- a/dlls/d2d1/hwnd_render_target.c +++ b/dlls/d2d1/hwnd_render_target.c @@ -776,8 +776,8 @@ static const struct d2d_device_context_ops d2d_hwnd_render_target_ops = d2d_hwnd_render_target_present, };
-HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target, ID2D1Factory *factory, - ID3D10Device1 *device, const D2D1_RENDER_TARGET_PROPERTIES *desc, +HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target, ID2D1Factory1 *factory, + ID3D10Device1 *d3d_device, const D2D1_RENDER_TARGET_PROPERTIES *desc, const D2D1_HWND_RENDER_TARGET_PROPERTIES *hwnd_rt_desc) { D2D1_RENDER_TARGET_PROPERTIES dxgi_rt_desc; @@ -786,6 +786,7 @@ HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target IDXGIFactory *dxgi_factory; IDXGISurface *dxgi_surface; IDXGIDevice *dxgi_device; + ID2D1Device *device; HRESULT hr;
if (!IsWindow(hwnd_rt_desc->hwnd)) @@ -795,7 +796,7 @@ HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target render_target->hwnd = hwnd_rt_desc->hwnd; render_target->sync_interval = hwnd_rt_desc->presentOptions & D2D1_PRESENT_OPTIONS_IMMEDIATELY ? 0 : 1;
- if (FAILED(hr = ID3D10Device1_QueryInterface(device, &IID_IDXGIDevice, (void **)&dxgi_device))) + if (FAILED(hr = ID3D10Device1_QueryInterface(d3d_device, &IID_IDXGIDevice, (void **)&dxgi_device))) { WARN("Failed to get IDXGIDevice interface, hr %#x.\n", hr); return hr; @@ -819,7 +820,7 @@ HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target
dxgi_rt_desc = *desc; if (dxgi_rt_desc.dpiX == 0.0f && dxgi_rt_desc.dpiY == 0.0f) - ID2D1Factory_GetDesktopDpi(factory, &dxgi_rt_desc.dpiX, &dxgi_rt_desc.dpiY); + ID2D1Factory1_GetDesktopDpi(factory, &dxgi_rt_desc.dpiX, &dxgi_rt_desc.dpiY);
if (dxgi_rt_desc.pixelFormat.format == DXGI_FORMAT_UNKNOWN) { @@ -844,7 +845,7 @@ HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target DXGI_SWAP_EFFECT_SEQUENTIAL : DXGI_SWAP_EFFECT_DISCARD; swapchain_desc.Flags = DXGI_SWAP_CHAIN_FLAG_GDI_COMPATIBLE;
- hr = IDXGIFactory_CreateSwapChain(dxgi_factory, (IUnknown *)device, &swapchain_desc, &render_target->swapchain); + hr = IDXGIFactory_CreateSwapChain(dxgi_factory, (IUnknown *)d3d_device, &swapchain_desc, &render_target->swapchain); IDXGIFactory_Release(dxgi_factory); if (FAILED(hr)) { @@ -860,10 +861,30 @@ HRESULT d2d_hwnd_render_target_init(struct d2d_hwnd_render_target *render_target }
render_target->ID2D1HwndRenderTarget_iface.lpVtbl = &d2d_hwnd_render_target_vtbl; - hr = d2d_d3d_create_render_target(factory, dxgi_surface, + + if (FAILED(hr = IDXGISurface_GetDevice(dxgi_surface, &IID_IDXGIDevice, (void **)&dxgi_device))) + { + WARN("Failed to get DXGI device, hr %#X.\n", hr); + IDXGISurface_Release(dxgi_surface); + IDXGISwapChain_Release(render_target->swapchain); + return hr; + } + + hr = ID2D1Factory1_CreateDevice(factory, dxgi_device, &device); + IDXGIDevice_Release(dxgi_device); + if (FAILED(hr)) + { + WARN("Failed to create D2D device, hr %#X.\n", hr); + IDXGISurface_Release(dxgi_surface); + IDXGISwapChain_Release(render_target->swapchain); + return hr; + } + + hr = d2d_d3d_create_render_target(device, dxgi_surface, (IUnknown *)&render_target->ID2D1HwndRenderTarget_iface, &d2d_hwnd_render_target_ops, &dxgi_rt_desc, (void **)&render_target->dxgi_inner); IDXGISurface_Release(dxgi_surface); + ID2D1Device_Release(device); if (FAILED(hr)) { WARN("Failed to create DXGI surface render target, hr %#x.\n", hr); diff --git a/dlls/d2d1/tests/d2d1.c b/dlls/d2d1/tests/d2d1.c index 65ab5c258b..eaa0b64a3d 100644 --- a/dlls/d2d1/tests/d2d1.c +++ b/dlls/d2d1/tests/d2d1.c @@ -6772,7 +6772,7 @@ static void check_rt_bitmap_surface_(unsigned int line, ID2D1RenderTarget *rt, B /* Pixel format is not defined until target is set, for DC target it's specified on creation. */ if (target || dc_rt) { - ID2D1Device *device = NULL, *device2 = NULL; + ID2D1Device *device, *device2; ID2D1DeviceContext *context2;
ID2D1DeviceContext_GetDevice(context, &device); @@ -6787,10 +6787,8 @@ static void check_rt_bitmap_surface_(unsigned int line, ID2D1RenderTarget *rt, B ID2D1DeviceContext_GetDevice(context2, &device2); ok_(__FILE__, line)(device == device2, "Unexpected device.\n");
- if (device) - ID2D1Device_Release(device); - if (device2) - ID2D1Device_Release(device2); + ID2D1Device_Release(device); + ID2D1Device_Release(device2);
ID2D1DeviceContext_Release(context2);
diff --git a/dlls/d2d1/wic_render_target.c b/dlls/d2d1/wic_render_target.c index 27236e2963..21a1fa170e 100644 --- a/dlls/d2d1/wic_render_target.c +++ b/dlls/d2d1/wic_render_target.c @@ -152,11 +152,13 @@ static const struct d2d_device_context_ops d2d_wic_render_target_ops = d2d_wic_render_target_present, };
-HRESULT d2d_wic_render_target_init(struct d2d_wic_render_target *render_target, ID2D1Factory *factory, - ID3D10Device1 *device, IWICBitmap *bitmap, const D2D1_RENDER_TARGET_PROPERTIES *desc) +HRESULT d2d_wic_render_target_init(struct d2d_wic_render_target *render_target, ID2D1Factory1 *factory, + ID3D10Device1 *d3d_device, IWICBitmap *bitmap, const D2D1_RENDER_TARGET_PROPERTIES *desc) { D3D10_TEXTURE2D_DESC texture_desc; ID3D10Texture2D *texture; + IDXGIDevice *dxgi_device; + ID2D1Device *device; HRESULT hr;
render_target->IUnknown_iface.lpVtbl = &d2d_wic_render_target_vtbl; @@ -214,7 +216,7 @@ HRESULT d2d_wic_render_target_init(struct d2d_wic_render_target *render_target, texture_desc.MiscFlags = desc->usage & D2D1_RENDER_TARGET_USAGE_GDI_COMPATIBLE ? D3D10_RESOURCE_MISC_GDI_COMPATIBLE : 0;
- if (FAILED(hr = ID3D10Device1_CreateTexture2D(device, &texture_desc, NULL, &texture))) + if (FAILED(hr = ID3D10Device1_CreateTexture2D(d3d_device, &texture_desc, NULL, &texture))) { WARN("Failed to create texture, hr %#x.\n", hr); return hr; @@ -233,16 +235,33 @@ HRESULT d2d_wic_render_target_init(struct d2d_wic_render_target *render_target, texture_desc.CPUAccessFlags = D3D10_CPU_ACCESS_READ; texture_desc.MiscFlags = 0;
- if (FAILED(hr = ID3D10Device1_CreateTexture2D(device, &texture_desc, NULL, &render_target->readback_texture))) + if (FAILED(hr = ID3D10Device1_CreateTexture2D(d3d_device, &texture_desc, NULL, &render_target->readback_texture))) { WARN("Failed to create readback texture, hr %#x.\n", hr); IDXGISurface_Release(render_target->dxgi_surface); return hr; }
- if (FAILED(hr = d2d_d3d_create_render_target(factory, render_target->dxgi_surface, - &render_target->IUnknown_iface, &d2d_wic_render_target_ops, - desc, (void **)&render_target->dxgi_inner))) + if (FAILED(hr = ID3D10Device1_QueryInterface(d3d_device, &IID_IDXGIDevice, (void **)&dxgi_device))) + { + WARN("Failed to get DXGI device, hr %#x.\n", hr); + IDXGISurface_Release(render_target->dxgi_surface); + return hr; + } + + hr = ID2D1Factory1_CreateDevice(factory, dxgi_device, &device); + IDXGIDevice_Release(dxgi_device); + if (FAILED(hr)) + { + WARN("Failed to create D2D device, hr %#x.\n", hr); + IDXGISurface_Release(render_target->dxgi_surface); + return hr; + } + + hr = d2d_d3d_create_render_target(device, render_target->dxgi_surface, &render_target->IUnknown_iface, + &d2d_wic_render_target_ops, desc, (void **)&render_target->dxgi_inner); + ID2D1Device_Release(device); + if (FAILED(hr)) { WARN("Failed to create DXGI surface render target, hr %#x.\n", hr); ID3D10Texture2D_Release(render_target->readback_texture);
Signed-off-by: Henri Verbeet hverbeet@codeweavers.com