Paul Gofman : mshtml: Add stub object for HTMLElement classList.
Alexandre Julliard
julliard at winehq.org
Mon Jul 19 15:59:16 CDT 2021
Module: wine
Branch: master
Commit: a08d13ddb0365c13265635f8b06e38b3d62135cc
URL: https://source.winehq.org/git/wine.git/?a=commit;h=a08d13ddb0365c13265635f8b06e38b3d62135cc
Author: Paul Gofman <pgofman at codeweavers.com>
Date: Mon Jul 19 15:53:16 2021 +0300
mshtml: Add stub object for HTMLElement classList.
Signed-off-by: Paul Gofman <pgofman at codeweavers.com>
Signed-off-by: Jacek Caban <jacek at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/mshtml/htmlelem.c | 143 ++++++++++++++++++++++++++++++++++-
dlls/mshtml/mshtml_private.h | 1 +
dlls/mshtml/mshtml_private_iface.idl | 11 +++
dlls/mshtml/tests/dom.js | 5 ++
4 files changed, 157 insertions(+), 3 deletions(-)
diff --git a/dlls/mshtml/htmlelem.c b/dlls/mshtml/htmlelem.c
index 961e4e79e08..5bb3f1eaf15 100644
--- a/dlls/mshtml/htmlelem.c
+++ b/dlls/mshtml/htmlelem.c
@@ -6395,6 +6395,142 @@ static event_target_vtbl_t HTMLElement_event_target_vtbl = {
HTMLElement_set_current_event
};
+struct token_list {
+ DispatchEx dispex;
+ IWineDOMTokenList IWineDOMTokenList_iface;
+ IHTMLElement *element;
+
+ LONG ref;
+};
+
+static inline struct token_list *impl_from_IWineDOMTokenList(IWineDOMTokenList *iface)
+{
+ return CONTAINING_RECORD(iface, struct token_list, IWineDOMTokenList_iface);
+}
+
+static HRESULT WINAPI token_list_QueryInterface(IWineDOMTokenList *iface, REFIID riid, void **ppv)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+
+ TRACE("(%p)->(%s %p)\n", token_list, debugstr_mshtml_guid(riid), ppv);
+
+ if(IsEqualGUID(&IID_IUnknown, riid)) {
+ *ppv = &token_list->IWineDOMTokenList_iface;
+ }else if(IsEqualGUID(&IID_IWineDOMTokenList, riid)) {
+ *ppv = &token_list->IWineDOMTokenList_iface;
+ }else if(dispex_query_interface(&token_list->dispex, riid, ppv)) {
+ return *ppv ? S_OK : E_NOINTERFACE;
+ }else {
+ WARN("(%p)->(%s %p)\n", token_list, debugstr_mshtml_guid(riid), ppv);
+ *ppv = NULL;
+ return E_NOINTERFACE;
+ }
+
+ IUnknown_AddRef((IUnknown*)*ppv);
+ return S_OK;
+}
+
+static ULONG WINAPI token_list_AddRef(IWineDOMTokenList *iface)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+ LONG ref = InterlockedIncrement(&token_list->ref);
+
+ TRACE("(%p) ref=%d\n", token_list, ref);
+
+ return ref;
+}
+
+static ULONG WINAPI token_list_Release(IWineDOMTokenList *iface)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+ LONG ref = InterlockedDecrement(&token_list->ref);
+
+ TRACE("(%p) ref=%d\n", token_list, ref);
+
+ if(!ref) {
+ IHTMLElement_Release(token_list->element);
+ release_dispex(&token_list->dispex);
+ heap_free(token_list);
+ }
+
+ return ref;
+}
+
+static HRESULT WINAPI token_list_GetTypeInfoCount(IWineDOMTokenList *iface, UINT *pctinfo)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+ FIXME("(%p)->(%p)\n", token_list, pctinfo);
+ return E_NOTIMPL;
+}
+
+static HRESULT WINAPI token_list_GetTypeInfo(IWineDOMTokenList *iface, UINT iTInfo,
+ LCID lcid, ITypeInfo **ppTInfo)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+
+ return IDispatchEx_GetTypeInfo(&token_list->dispex.IDispatchEx_iface, iTInfo, lcid, ppTInfo);
+}
+
+static HRESULT WINAPI token_list_GetIDsOfNames(IWineDOMTokenList *iface, REFIID riid,
+ LPOLESTR *rgszNames, UINT cNames, LCID lcid, DISPID *rgDispId)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+
+ return IDispatchEx_GetIDsOfNames(&token_list->dispex.IDispatchEx_iface, riid, rgszNames, cNames,
+ lcid, rgDispId);
+}
+
+static HRESULT WINAPI token_list_Invoke(IWineDOMTokenList *iface, DISPID dispIdMember,
+ REFIID riid, LCID lcid, WORD wFlags, DISPPARAMS *pDispParams,
+ VARIANT *pVarResult, EXCEPINFO *pExcepInfo, UINT *puArgErr)
+{
+ struct token_list *token_list = impl_from_IWineDOMTokenList(iface);
+
+ return IDispatchEx_Invoke(&token_list->dispex.IDispatchEx_iface, dispIdMember, riid, lcid, wFlags,
+ pDispParams, pVarResult, pExcepInfo, puArgErr);
+}
+
+static const IWineDOMTokenListVtbl WineDOMTokenListVtbl = {
+ token_list_QueryInterface,
+ token_list_AddRef,
+ token_list_Release,
+ token_list_GetTypeInfoCount,
+ token_list_GetTypeInfo,
+ token_list_GetIDsOfNames,
+ token_list_Invoke,
+};
+
+static const tid_t token_list_iface_tids[] = {
+ IWineDOMTokenList_tid,
+ 0
+};
+static dispex_static_data_t token_list_dispex = {
+ NULL,
+ IWineDOMTokenList_tid,
+ token_list_iface_tids
+};
+
+static HRESULT create_token_list(compat_mode_t compat_mode, IHTMLElement *element, IWineDOMTokenList **ret)
+{
+ struct token_list *obj;
+
+ obj = heap_alloc_zero(sizeof(*obj));
+ if(!obj)
+ {
+ ERR("No memory.\n");
+ return E_OUTOFMEMORY;
+ }
+
+ obj->IWineDOMTokenList_iface.lpVtbl = &WineDOMTokenListVtbl;
+ obj->ref = 1;
+ init_dispatch(&obj->dispex, (IUnknown*)&obj->IWineDOMTokenList_iface, &token_list_dispex, compat_mode);
+ IHTMLElement_AddRef(element);
+ obj->element = element;
+
+ *ret = &obj->IWineDOMTokenList_iface;
+ return S_OK;
+}
+
static inline HTMLElement *impl_from_IWineHTMLElementPrivateVtbl(IWineHTMLElementPrivate *iface)
{
return CONTAINING_RECORD(iface, HTMLElement, IWineHTMLElementPrivate_iface);
@@ -6459,11 +6595,12 @@ static HRESULT WINAPI htmlelement_private_Invoke(IWineHTMLElementPrivate *iface,
static HRESULT WINAPI htmlelement_private_get_classList(IWineHTMLElementPrivate *iface, IDispatch **class_list)
{
- FIXME("iface %p, class_list %p stub.\n", iface, class_list);
+ HTMLElement *This = impl_from_IWineHTMLElementPrivateVtbl(iface);
- *class_list = NULL;
+ TRACE("iface %p, class_list %p.\n", iface, class_list);
- return S_OK;
+ return create_token_list(dispex_compat_mode(&This->node.event_target.dispex), &This->IHTMLElement_iface,
+ (IWineDOMTokenList **)class_list);
}
static const IWineHTMLElementPrivateVtbl WineHTMLElementPrivateVtbl = {
diff --git a/dlls/mshtml/mshtml_private.h b/dlls/mshtml/mshtml_private.h
index 56bef40b4d0..c1e7e78253d 100644
--- a/dlls/mshtml/mshtml_private.h
+++ b/dlls/mshtml/mshtml_private.h
@@ -273,6 +273,7 @@ typedef struct EventTarget EventTarget;
XIID(ISVGTextContentElement)
#define PRIVATE_TID_LIST \
+ XIID(IWineDOMTokenList) \
XIID(IWineHTMLElementPrivate) \
XIID(IWineHTMLWindowPrivate) \
XIID(IWineMSHTMLConsole)
diff --git a/dlls/mshtml/mshtml_private_iface.idl b/dlls/mshtml/mshtml_private_iface.idl
index 9ca7e0d7421..1764b0a8c9d 100644
--- a/dlls/mshtml/mshtml_private_iface.idl
+++ b/dlls/mshtml/mshtml_private_iface.idl
@@ -102,4 +102,15 @@ interface IWineHTMLElementPrivate : IDispatch
HRESULT classList([retval, out] IDispatch **class_list);
}
+[
+ odl,
+ oleautomation,
+ dual,
+ hidden,
+ uuid(08ef0edd-5fb8-4178-a2f0-9f686e00441b)
+]
+interface IWineDOMTokenList : IDispatch
+{
+}
+
} /* library MSHTML_private */
diff --git a/dlls/mshtml/tests/dom.js b/dlls/mshtml/tests/dom.js
index a2c70540eba..f54cb0f7088 100644
--- a/dlls/mshtml/tests/dom.js
+++ b/dlls/mshtml/tests/dom.js
@@ -508,3 +508,8 @@ sync_test("hasAttribute", function() {
r = elem.hasAttribute("attr");
ok(r === false, "hasAttribute(attr) returned " + r);
});
+
+sync_test("classList", function() {
+ var elem = document.createElement("div");
+ var classList = elem.classList;
+});
More information about the wine-cvs
mailing list