Connor McAdams : oleacc: Add IServiceProvider interface to default accessible objects.
Alexandre Julliard
julliard at winehq.org
Tue Apr 26 16:25:25 CDT 2022
Module: wine
Branch: master
Commit: 46a2f3e42fbabdb2cb0b5da20698b4a7390108a1
URL: https://source.winehq.org/git/wine.git/?a=commit;h=46a2f3e42fbabdb2cb0b5da20698b4a7390108a1
Author: Connor McAdams <cmcadams at codeweavers.com>
Date: Mon Apr 25 15:08:01 2022 -0400
oleacc: Add IServiceProvider interface to default accessible objects.
Signed-off-by: Connor McAdams <cmcadams at codeweavers.com>
Signed-off-by: Piotr Caban <piotr at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/oleacc/client.c | 48 ++++++++++++++++++++++++++++++++++++++++++++
dlls/oleacc/oleacc_private.h | 1 +
dlls/oleacc/tests/main.c | 26 +++++++++++-------------
dlls/oleacc/window.c | 48 ++++++++++++++++++++++++++++++++++++++++++++
4 files changed, 109 insertions(+), 14 deletions(-)
diff --git a/dlls/oleacc/client.c b/dlls/oleacc/client.c
index 20993109d28..8a8fd3d240d 100644
--- a/dlls/oleacc/client.c
+++ b/dlls/oleacc/client.c
@@ -32,6 +32,7 @@ typedef struct {
IAccessible IAccessible_iface;
IOleWindow IOleWindow_iface;
IEnumVARIANT IEnumVARIANT_iface;
+ IServiceProvider IServiceProvider_iface;
LONG ref;
@@ -114,6 +115,8 @@ static HRESULT WINAPI Client_QueryInterface(IAccessible *iface, REFIID riid, voi
*ppv = &This->IOleWindow_iface;
}else if(IsEqualIID(riid, &IID_IEnumVARIANT)) {
*ppv = &This->IEnumVARIANT_iface;
+ }else if(IsEqualIID(riid, &IID_IServiceProvider)) {
+ *ppv = &This->IServiceProvider_iface;
}else {
WARN("no interface: %s\n", debugstr_guid(riid));
*ppv = NULL;
@@ -703,6 +706,50 @@ static const IEnumVARIANTVtbl ClientEnumVARIANTVtbl = {
Client_EnumVARIANT_Clone
};
+static inline Client* impl_from_Client_ServiceProvider(IServiceProvider *iface)
+{
+ return CONTAINING_RECORD(iface, Client, IServiceProvider_iface);
+}
+
+static HRESULT WINAPI Client_ServiceProvider_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv)
+{
+ Client *This = impl_from_Client_ServiceProvider(iface);
+ return IAccessible_QueryInterface(&This->IAccessible_iface, riid, ppv);
+}
+
+static ULONG WINAPI Client_ServiceProvider_AddRef(IServiceProvider *iface)
+{
+ Client *This = impl_from_Client_ServiceProvider(iface);
+ return IAccessible_AddRef(&This->IAccessible_iface);
+}
+
+static ULONG WINAPI Client_ServiceProvider_Release(IServiceProvider *iface)
+{
+ Client *This = impl_from_Client_ServiceProvider(iface);
+ return IAccessible_Release(&This->IAccessible_iface);
+}
+
+static HRESULT WINAPI Client_ServiceProvider_QueryService(IServiceProvider *iface, REFGUID guid_service,
+ REFIID riid, void **ppv)
+{
+ Client *This = impl_from_Client_ServiceProvider(iface);
+
+ TRACE("(%p)->(%s %s %p)\n", This, debugstr_guid(guid_service), debugstr_guid(riid), ppv);
+
+ *ppv = NULL;
+ if (IsEqualIID(guid_service, &IIS_IsOleaccProxy))
+ return IAccessible_QueryInterface(&This->IAccessible_iface, riid, ppv);
+
+ return E_INVALIDARG;
+}
+
+static const IServiceProviderVtbl ClientServiceProviderVtbl = {
+ Client_ServiceProvider_QueryInterface,
+ Client_ServiceProvider_AddRef,
+ Client_ServiceProvider_Release,
+ Client_ServiceProvider_QueryService
+};
+
static void edit_init(Client *client)
{
client->role = ROLE_SYSTEM_TEXT;
@@ -872,6 +919,7 @@ HRESULT create_client_object(HWND hwnd, const IID *iid, void **obj)
client->IAccessible_iface.lpVtbl = &ClientVtbl;
client->IOleWindow_iface.lpVtbl = &ClientOleWindowVtbl;
client->IEnumVARIANT_iface.lpVtbl = &ClientEnumVARIANTVtbl;
+ client->IServiceProvider_iface.lpVtbl = &ClientServiceProviderVtbl;
client->ref = 1;
client->hwnd = hwnd;
client->enum_pos = 0;
diff --git a/dlls/oleacc/oleacc_private.h b/dlls/oleacc/oleacc_private.h
index a01fc3615fe..c91b1465a79 100644
--- a/dlls/oleacc/oleacc_private.h
+++ b/dlls/oleacc/oleacc_private.h
@@ -17,6 +17,7 @@
*/
#include "oleacc_classes.h"
+#include "servprov.h"
struct win_class_data {
const WCHAR *name;
diff --git a/dlls/oleacc/tests/main.c b/dlls/oleacc/tests/main.c
index ba7ac3cc3ac..7854764ec08 100644
--- a/dlls/oleacc/tests/main.c
+++ b/dlls/oleacc/tests/main.c
@@ -1419,21 +1419,19 @@ static void check_acc_proxy_service_(IAccessible *acc, int line)
HRESULT hr;
hr = IAccessible_QueryInterface(acc, &IID_IServiceProvider, (void **)&service);
- todo_wine ok(hr == S_OK, "got %#lx\n", hr);
- if (SUCCEEDED(hr))
- {
- hr = IServiceProvider_QueryService(service, &IIS_IsOleaccProxy, &IID_IUnknown, (void **)&unk);
- ok(hr == S_OK, "got %#lx\n", hr);
- ok(!!unk, "unk == NULL\n");
- ok(iface_cmp(unk, (IUnknown*)acc), "unk != acc\n");
- IUnknown_Release(unk);
+ ok(hr == S_OK, "got %#lx\n", hr);
- unk = (IUnknown*)0xdeadbeef;
- hr = IServiceProvider_QueryService(service, &IID_IUnknown, &IID_IUnknown, (void **)&unk);
- ok(hr == E_INVALIDARG, "got %#lx\n", hr);
- ok(!unk, "unk != NULL\n");
- IServiceProvider_Release(service);
- }
+ hr = IServiceProvider_QueryService(service, &IIS_IsOleaccProxy, &IID_IUnknown, (void **)&unk);
+ ok(hr == S_OK, "got %#lx\n", hr);
+ ok(!!unk, "unk == NULL\n");
+ ok(iface_cmp(unk, (IUnknown*)acc), "unk != acc\n");
+ IUnknown_Release(unk);
+
+ unk = (IUnknown*)0xdeadbeef;
+ hr = IServiceProvider_QueryService(service, &IID_IUnknown, &IID_IUnknown, (void **)&unk);
+ ok(hr == E_INVALIDARG, "got %#lx\n", hr);
+ ok(!unk, "unk != NULL\n");
+ IServiceProvider_Release(service);
}
static void test_CreateStdAccessibleObject_classes(void)
diff --git a/dlls/oleacc/window.c b/dlls/oleacc/window.c
index 470bfd5b362..6a7aa3d0318 100644
--- a/dlls/oleacc/window.c
+++ b/dlls/oleacc/window.c
@@ -30,6 +30,7 @@ typedef struct {
IAccessible IAccessible_iface;
IOleWindow IOleWindow_iface;
IEnumVARIANT IEnumVARIANT_iface;
+ IServiceProvider IServiceProvider_iface;
LONG ref;
@@ -55,6 +56,8 @@ static HRESULT WINAPI Window_QueryInterface(IAccessible *iface, REFIID riid, voi
*ppv = &This->IOleWindow_iface;
}else if(IsEqualIID(riid, &IID_IEnumVARIANT)) {
*ppv = &This->IEnumVARIANT_iface;
+ }else if(IsEqualIID(riid, &IID_IServiceProvider)) {
+ *ppv = &This->IServiceProvider_iface;
}else {
WARN("no interface: %s\n", debugstr_guid(riid));
*ppv = NULL;
@@ -444,6 +447,50 @@ static const IEnumVARIANTVtbl WindowEnumVARIANTVtbl = {
Window_EnumVARIANT_Clone
};
+static inline Window* impl_from_Window_ServiceProvider(IServiceProvider *iface)
+{
+ return CONTAINING_RECORD(iface, Window, IServiceProvider_iface);
+}
+
+static HRESULT WINAPI Window_ServiceProvider_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv)
+{
+ Window *This = impl_from_Window_ServiceProvider(iface);
+ return IAccessible_QueryInterface(&This->IAccessible_iface, riid, ppv);
+}
+
+static ULONG WINAPI Window_ServiceProvider_AddRef(IServiceProvider *iface)
+{
+ Window *This = impl_from_Window_ServiceProvider(iface);
+ return IAccessible_AddRef(&This->IAccessible_iface);
+}
+
+static ULONG WINAPI Window_ServiceProvider_Release(IServiceProvider *iface)
+{
+ Window *This = impl_from_Window_ServiceProvider(iface);
+ return IAccessible_Release(&This->IAccessible_iface);
+}
+
+static HRESULT WINAPI Window_ServiceProvider_QueryService(IServiceProvider *iface, REFGUID guid_service,
+ REFIID riid, void **ppv)
+{
+ Window *This = impl_from_Window_ServiceProvider(iface);
+
+ TRACE("(%p)->(%s %s %p)\n", This, debugstr_guid(guid_service), debugstr_guid(riid), ppv);
+
+ *ppv = NULL;
+ if (IsEqualIID(guid_service, &IIS_IsOleaccProxy))
+ return IAccessible_QueryInterface(&This->IAccessible_iface, riid, ppv);
+
+ return E_INVALIDARG;
+}
+
+static const IServiceProviderVtbl WindowServiceProviderVtbl = {
+ Window_ServiceProvider_QueryInterface,
+ Window_ServiceProvider_AddRef,
+ Window_ServiceProvider_Release,
+ Window_ServiceProvider_QueryService
+};
+
static const struct win_class_data classes[] = {
{WC_LISTBOXW, 0x10000, TRUE},
{L"#32768", 0x10001, TRUE}, /* menu */
@@ -467,6 +514,7 @@ HRESULT create_window_object(HWND hwnd, const IID *iid, void **obj)
window->IAccessible_iface.lpVtbl = &WindowVtbl;
window->IOleWindow_iface.lpVtbl = &WindowOleWindowVtbl;
window->IEnumVARIANT_iface.lpVtbl = &WindowEnumVARIANTVtbl;
+ window->IServiceProvider_iface.lpVtbl = &WindowServiceProviderVtbl;
window->ref = 1;
window->hwnd = hwnd;
More information about the wine-cvs
mailing list