Example #1
0
static HRESULT STDMETHODCALLTYPE d2d_dc_render_target_BindDC(ID2D1DCRenderTarget *iface,
        const HDC hdc, const RECT *rect)
{
    struct d2d_dc_render_target *render_target = impl_from_ID2D1DCRenderTarget(iface);
    D2D1_BITMAP_PROPERTIES1 bitmap_desc;
    struct d2d_bitmap *bitmap_impl;
    IDXGISurface1 *dxgi_surface;
    ID2D1DeviceContext *context;
    ID3D10Resource *resource;
    D2D1_SIZE_U bitmap_size;
    ID2D1Bitmap *bitmap;
    HRESULT hr;

    TRACE("iface %p, hdc %p, rect %s.\n", iface, hdc, wine_dbgstr_rect(rect));

    if (!hdc)
        return E_INVALIDARG;

    /* Switch dxgi target to new surface. */
    ID2D1RenderTarget_QueryInterface(render_target->dxgi_target, &IID_ID2D1DeviceContext, (void **)&context);

    bitmap_size.width = rect->right - rect->left;
    bitmap_size.height = rect->bottom - rect->top;

    memset(&bitmap_desc, 0, sizeof(bitmap_desc));
    bitmap_desc.pixelFormat = render_target->pixel_format;
    bitmap_desc.bitmapOptions = D2D1_BITMAP_OPTIONS_TARGET | D2D1_BITMAP_OPTIONS_CANNOT_DRAW |
            D2D1_BITMAP_OPTIONS_GDI_COMPATIBLE;
    if (FAILED(hr = ID2D1DeviceContext_CreateBitmap(context, bitmap_size, NULL, 0, &bitmap_desc,
            (ID2D1Bitmap1 **)&bitmap)))
    {
        WARN("Failed to create target bitmap, hr %#x.\n", hr);
        ID2D1DeviceContext_Release(context);
        return hr;
    }

    bitmap_impl = unsafe_impl_from_ID2D1Bitmap(bitmap);
    ID3D10ShaderResourceView_GetResource(bitmap_impl->view, &resource);
    ID3D10Resource_QueryInterface(resource, &IID_IDXGISurface1, (void **)&dxgi_surface);
    ID3D10Resource_Release(resource);

    ID2D1DeviceContext_SetTarget(context, (ID2D1Image *)bitmap);
    ID2D1Bitmap_Release(bitmap);
    ID2D1DeviceContext_Release(context);

    if (render_target->dxgi_surface)
        IDXGISurface1_Release(render_target->dxgi_surface);
    render_target->dxgi_surface = dxgi_surface;

    render_target->hdc = hdc;
    render_target->dst_rect = *rect;

    return hr;
}
Example #2
0
static ULONG STDMETHODCALLTYPE d2d_dc_render_target_Release(ID2D1DCRenderTarget *iface)
{
    struct d2d_dc_render_target *render_target = impl_from_ID2D1DCRenderTarget(iface);
    ULONG refcount = InterlockedDecrement(&render_target->refcount);

    TRACE("%p decreasing refcount to %u.\n", iface, refcount);

    if (!refcount)
    {
        IUnknown_Release(render_target->dxgi_inner);
        if (render_target->dxgi_surface)
            IDXGISurface1_Release(render_target->dxgi_surface);
        ID3D10Device1_Release(render_target->d3d_device);
        heap_free(render_target);
    }

    return refcount;
}
static void test_getdc(void)
{
    struct device_desc device_desc;
    D3D10_TEXTURE2D_DESC desc;
    ID3D10Texture2D *texture;
    IDXGISurface1 *surface1;
    ID3D10Device1 *device;
    ULONG refcount;
    HRESULT hr;
    HDC dc;

    device_desc.feature_level = D3D10_FEATURE_LEVEL_10_1;
    device_desc.flags = D3D10_CREATE_DEVICE_BGRA_SUPPORT;
    if (!(device = create_device(&device_desc)))
    {
        skip("Failed to create device.\n");
        return;
    }

    /* Without D3D10_RESOURCE_MISC_GDI_COMPATIBLE. */
    desc.Width = 512;
    desc.Height = 512;
    desc.MipLevels = 1;
    desc.ArraySize = 1;
    desc.Format = DXGI_FORMAT_B8G8R8A8_UNORM;
    desc.SampleDesc.Count = 1;
    desc.SampleDesc.Quality = 0;
    desc.Usage = D3D10_USAGE_DEFAULT;
    desc.BindFlags = D3D10_BIND_RENDER_TARGET;
    desc.CPUAccessFlags = 0;
    desc.MiscFlags = 0;
    hr = ID3D10Device1_CreateTexture2D(device, &desc, NULL, &texture);
    ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);

    hr = ID3D10Texture2D_QueryInterface(texture, &IID_IDXGISurface1, (void**)&surface1);
    ok(SUCCEEDED(hr), "Failed to get IDXGISurface1 interface, hr %#x.\n", hr);

    hr = IDXGISurface1_GetDC(surface1, FALSE, &dc);
    todo_wine ok(hr == DXGI_ERROR_INVALID_CALL, "Got unexpected hr %#x.\n", hr);

    IDXGISurface1_Release(surface1);
    ID3D10Texture2D_Release(texture);

    desc.MiscFlags = D3D10_RESOURCE_MISC_GDI_COMPATIBLE;
    hr = ID3D10Device1_CreateTexture2D(device, &desc, NULL, &texture);
    ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);

    hr = ID3D10Texture2D_QueryInterface(texture, &IID_IDXGISurface1, (void**)&surface1);
    ok(SUCCEEDED(hr), "Failed to get IDXGISurface1 interface, hr %#x.\n", hr);

    hr = IDXGISurface1_ReleaseDC(surface1, NULL);
    todo_wine ok(hr == DXGI_ERROR_INVALID_CALL, "Got unexpected hr %#x.\n", hr);

    hr = IDXGISurface1_GetDC(surface1, FALSE, &dc);
    todo_wine ok(SUCCEEDED(hr), "Failed to get DC, hr %#x.\n", hr);

    /* One more time. */
    dc = (HDC)0xdeadbeef;
    hr = IDXGISurface1_GetDC(surface1, FALSE, &dc);
    todo_wine ok(hr == DXGI_ERROR_INVALID_CALL, "Got unexpected hr %#x.\n", hr);
    ok(dc == (HDC)0xdeadbeef, "Got unexpected dc %p.\n", dc);

    hr = IDXGISurface1_ReleaseDC(surface1, NULL);
    todo_wine ok(SUCCEEDED(hr), "Failed to release DC, hr %#x.\n", hr);

    hr = IDXGISurface1_ReleaseDC(surface1, NULL);
    todo_wine ok(hr == DXGI_ERROR_INVALID_CALL, "Got unexpected hr %#x.\n", hr);

    IDXGISurface1_Release(surface1);
    ID3D10Texture2D_Release(texture);

    refcount = ID3D10Device1_Release(device);
    ok(!refcount, "Device has %u references left.\n", refcount);
}