This is mostly a precursor to the attribute nodes implementation for IE9+ modes later, since most of them are stubs in legacy modes. There's also no way to insert them in legacy modes via node props either, since they don't expose IHTMLDOMNode* interfaces.
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 21 +++++++++++++++++++++ 2 files changed, 26 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 1fe5570feba..84d609ad389 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -208,8 +208,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_expando(IHTMLDOMAttribute2 *iface, V static HRESULT WINAPI HTMLDOMAttribute2_get_nodeType(IHTMLDOMAttribute2 *iface, LONG *p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = 2; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_parentNode(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index af03e660fe5..e6b34b26719 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -9944,6 +9944,22 @@ static void test_elems(IHTMLDocument2 *doc) IHTMLWindow2_Release(window); }
+static void test_attr_node(IHTMLDOMAttribute *test_attr) +{ + IHTMLDOMAttribute2 *attr; + HRESULT hres; + LONG type; + + hres = IHTMLDOMAttribute_QueryInterface(test_attr, &IID_IHTMLDOMAttribute2, (void**)&attr); + ok(hres == S_OK, "Could not get IHTMLDOMAttribute2 iface: %08lx\n", hres); + + hres = IHTMLDOMAttribute2_get_nodeType(attr, &type); + ok(hres == S_OK, "get_nodeType failed: %08lx\n", hres); + ok(type == 2, "nodeType = %ld\n", type); + + IHTMLDOMAttribute2_Release(attr); +} + static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) { IHTMLDOMAttribute *attr, *attr2, *attr3; @@ -9985,6 +10001,7 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) ok(!lstrcmpW(V_BSTR(&v), L"divid3"), "V_BSTR(v) = %s\n", wine_dbgstr_w(V_BSTR(&v))); VariantClear(&v);
+ test_attr_node(attr); IHTMLDOMAttribute_Release(attr);
attr = get_elem_attr_node((IUnknown*)elem, L"emptyattr", TRUE); @@ -10004,6 +10021,7 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) VariantClear(&v);
test_attr_specified(attr, VARIANT_TRUE); + test_attr_node(attr); IHTMLDOMAttribute_Release(attr);
V_VT(&v) = VT_I4; @@ -10026,11 +10044,13 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) ok(!lstrcmpW(V_BSTR(&v), L"160"), "V_BSTR(v) = %s\n", wine_dbgstr_w(V_BSTR(&v))); VariantClear(&v);
+ test_attr_node(attr); IHTMLDOMAttribute_Release(attr);
attr = get_elem_attr_node((IUnknown*)elem, L"tabIndex", TRUE); test_attr_specified(attr, VARIANT_FALSE); test_attr_expando(attr, VARIANT_FALSE); + test_attr_node(attr); IHTMLDOMAttribute_Release(attr);
/* Test created, detached attribute. */ @@ -10102,6 +10122,7 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) test_elem_attr(elem, L"Test", L"new replace value"); test_attr_value(attr, L"new value2"); test_attr_value(attr3, L"new replace value"); + test_attr_node(attr);
/* Attached attributes cause errors. */ hres = IHTMLElement4_setAttributeNode(elem4, attr3, &attr2);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 5 +++++ 2 files changed, 10 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 84d609ad389..01d9773c5b4 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -263,8 +263,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_nextSibling(IHTMLDOMAttribute2 *ifac static HRESULT WINAPI HTMLDOMAttribute2_get_attributes(IHTMLDOMAttribute2 *iface, IDispatch **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_ownerDocument(IHTMLDOMAttribute2 *iface, IDispatch **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index e6b34b26719..a60ede8d21f 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -9947,6 +9947,7 @@ static void test_elems(IHTMLDocument2 *doc) static void test_attr_node(IHTMLDOMAttribute *test_attr) { IHTMLDOMAttribute2 *attr; + IDispatch *disp; HRESULT hres; LONG type;
@@ -9957,6 +9958,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr) ok(hres == S_OK, "get_nodeType failed: %08lx\n", hres); ok(type == 2, "nodeType = %ld\n", type);
+ hres = IHTMLDOMAttribute2_get_attributes(attr, &disp); + ok(hres == S_OK, "get_attributes failed: %08lx\n", hres); + ok(!disp, "attributes != NULL\n"); + IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Simplifies some handling later, and will be needed anyway for IE9+ modes.
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 8 ++++---- dlls/mshtml/mshtml_private.h | 3 ++- 2 files changed, 6 insertions(+), 5 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 01d9773c5b4..87ea6f984fd 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -37,7 +37,7 @@ static inline HTMLDOMAttribute *impl_from_IHTMLDOMAttribute(IHTMLDOMAttribute *i return CONTAINING_RECORD(iface, HTMLDOMAttribute, IHTMLDOMAttribute_iface); }
-DISPEX_IDISPATCH_IMPL(HTMLDOMAttribute, IHTMLDOMAttribute, impl_from_IHTMLDOMAttribute(iface)->dispex) +DISPEX_IDISPATCH_IMPL(HTMLDOMAttribute, IHTMLDOMAttribute, impl_from_IHTMLDOMAttribute(iface)->node.event_target.dispex)
static HRESULT WINAPI HTMLDOMAttribute_get_nodeName(IHTMLDOMAttribute *iface, BSTR *p) { @@ -147,7 +147,7 @@ static inline HTMLDOMAttribute *impl_from_IHTMLDOMAttribute2(IHTMLDOMAttribute2 return CONTAINING_RECORD(iface, HTMLDOMAttribute, IHTMLDOMAttribute2_iface); }
-DISPEX_IDISPATCH_IMPL(HTMLDOMAttribute2, IHTMLDOMAttribute2, impl_from_IHTMLDOMAttribute2(iface)->dispex) +DISPEX_IDISPATCH_IMPL(HTMLDOMAttribute2, IHTMLDOMAttribute2, impl_from_IHTMLDOMAttribute2(iface)->node.event_target.dispex)
static HRESULT WINAPI HTMLDOMAttribute2_get_name(IHTMLDOMAttribute2 *iface, BSTR *p) { @@ -355,7 +355,7 @@ static const IHTMLDOMAttribute2Vtbl HTMLDOMAttribute2Vtbl = {
static inline HTMLDOMAttribute *impl_from_DispatchEx(DispatchEx *iface) { - return CONTAINING_RECORD(iface, HTMLDOMAttribute, dispex); + return CONTAINING_RECORD(iface, HTMLDOMAttribute, node.event_target.dispex); }
static void *HTMLDOMAttribute_query_interface(DispatchEx *dispex, REFIID riid) @@ -440,7 +440,7 @@ HRESULT HTMLDOMAttribute_Create(const WCHAR *name, HTMLElement *elem, DISPID dis ret->dispid = dispid; ret->elem = elem;
- init_dispatch(&ret->dispex, &Attr_dispex, doc->script_global, + init_dispatch(&ret->node.event_target.dispex, &Attr_dispex, doc->script_global, dispex_compat_mode(&doc->script_global->event_target.dispex));
/* For attributes attached to an element, (elem,dispid) pair should be valid used for its operation. */ diff --git a/dlls/mshtml/mshtml_private.h b/dlls/mshtml/mshtml_private.h index c02f4515c7d..bc53333a53f 100644 --- a/dlls/mshtml/mshtml_private.h +++ b/dlls/mshtml/mshtml_private.h @@ -1331,7 +1331,8 @@ struct HTMLAttributeCollection { };
typedef struct { - DispatchEx dispex; + HTMLDOMNode node; + IHTMLDOMAttribute IHTMLDOMAttribute_iface; IHTMLDOMAttribute2 IHTMLDOMAttribute2_iface;
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 13 +++++++++++-- dlls/mshtml/tests/dom.c | 28 ++++++++++++++++++++++------ 2 files changed, 33 insertions(+), 8 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 87ea6f984fd..963909fdc00 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -273,8 +273,12 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_attributes(IHTMLDOMAttribute2 *iface static HRESULT WINAPI HTMLDOMAttribute2_get_ownerDocument(IHTMLDOMAttribute2 *iface, IDispatch **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = (IDispatch*)&This->node.doc->IHTMLDocument2_iface; + IDispatch_AddRef(*p); + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_insertBefore(IHTMLDOMAttribute2 *iface, IHTMLDOMNode *newChild, @@ -373,6 +377,7 @@ static void *HTMLDOMAttribute_query_interface(DispatchEx *dispex, REFIID riid) static void HTMLDOMAttribute_traverse(DispatchEx *dispex, nsCycleCollectionTraversalCallback *cb) { HTMLDOMAttribute *This = impl_from_DispatchEx(dispex); + HTMLDOMNode_traverse(&This->node.event_target.dispex, cb);
if(This->elem) note_cc_edge((nsISupports*)&This->elem->node.IHTMLDOMNode_iface, "elem", cb); @@ -382,6 +387,7 @@ static void HTMLDOMAttribute_traverse(DispatchEx *dispex, nsCycleCollectionTrave static void HTMLDOMAttribute_unlink(DispatchEx *dispex) { HTMLDOMAttribute *This = impl_from_DispatchEx(dispex); + HTMLDOMNode_unlink(&This->node.event_target.dispex);
if(This->elem) { HTMLElement *elem = This->elem; @@ -466,6 +472,9 @@ HRESULT HTMLDOMAttribute_Create(const WCHAR *name, HTMLElement *elem, DISPID dis } }
+ ret->node.doc = doc; + IHTMLDocument2_AddRef(&doc->IHTMLDocument2_iface); + *attr = ret; return S_OK; } diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index a60ede8d21f..4daeb4ff552 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -9944,9 +9944,11 @@ static void test_elems(IHTMLDocument2 *doc) IHTMLWindow2_Release(window); }
-static void test_attr_node(IHTMLDOMAttribute *test_attr) +static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) { IHTMLDOMAttribute2 *attr; + IHTMLDocument2 *doc_node; + IHTMLWindow2 *window; IDispatch *disp; HRESULT hres; LONG type; @@ -9962,6 +9964,20 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr) ok(hres == S_OK, "get_attributes failed: %08lx\n", hres); ok(!disp, "attributes != NULL\n");
+ hres = IHTMLDocument2_get_parentWindow(doc, &window); + ok(hres == S_OK, "get_parentWindow failed: %08lx\n", hres); + hres = IHTMLWindow2_get_document(window, &doc_node); + ok(hres == S_OK, "get_document failed: %08lx\n", hres); + IHTMLWindow2_Release(window); + + hres = IHTMLDOMAttribute2_get_ownerDocument(attr, &disp); + ok(hres == S_OK, "get_ownerDocument failed: %08lx\n", hres); + ok(disp != NULL, "ownerDocument == NULL\n"); + ok(!iface_cmp((IUnknown*)disp, (IUnknown*)doc), "ownerDocument == doc\n"); + ok(iface_cmp((IUnknown*)disp, (IUnknown*)doc_node), "ownerDocument != doc_node\n"); + IHTMLDocument2_Release(doc_node); + IDispatch_Release(disp); + IHTMLDOMAttribute2_Release(attr); }
@@ -10006,7 +10022,7 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) ok(!lstrcmpW(V_BSTR(&v), L"divid3"), "V_BSTR(v) = %s\n", wine_dbgstr_w(V_BSTR(&v))); VariantClear(&v);
- test_attr_node(attr); + test_attr_node(attr, doc); IHTMLDOMAttribute_Release(attr);
attr = get_elem_attr_node((IUnknown*)elem, L"emptyattr", TRUE); @@ -10026,7 +10042,7 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) VariantClear(&v);
test_attr_specified(attr, VARIANT_TRUE); - test_attr_node(attr); + test_attr_node(attr, doc); IHTMLDOMAttribute_Release(attr);
V_VT(&v) = VT_I4; @@ -10049,13 +10065,13 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) ok(!lstrcmpW(V_BSTR(&v), L"160"), "V_BSTR(v) = %s\n", wine_dbgstr_w(V_BSTR(&v))); VariantClear(&v);
- test_attr_node(attr); + test_attr_node(attr, doc); IHTMLDOMAttribute_Release(attr);
attr = get_elem_attr_node((IUnknown*)elem, L"tabIndex", TRUE); test_attr_specified(attr, VARIANT_FALSE); test_attr_expando(attr, VARIANT_FALSE); - test_attr_node(attr); + test_attr_node(attr, doc); IHTMLDOMAttribute_Release(attr);
/* Test created, detached attribute. */ @@ -10127,7 +10143,7 @@ static void test_attr(IHTMLDocument2 *doc, IHTMLElement *elem) test_elem_attr(elem, L"Test", L"new replace value"); test_attr_value(attr, L"new value2"); test_attr_value(attr3, L"new replace value"); - test_attr_node(attr); + test_attr_node(attr, doc);
/* Attached attributes cause errors. */ hres = IHTMLElement4_setAttributeNode(elem4, attr3, &attr2);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 22 ++++++++++++++++++++-- dlls/mshtml/tests/dom.c | 22 ++++++++++++++++++++++ 2 files changed, 42 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 963909fdc00..5b3f070f0a7 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -324,8 +324,26 @@ static HRESULT WINAPI HTMLDOMAttribute2_cloneNode(IHTMLDOMAttribute2 *iface, VAR IHTMLDOMAttribute **clonedNode) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%x %p)\n", This, fDeep, clonedNode); - return E_NOTIMPL; + HTMLDOMAttribute *new_attr; + HRESULT hres; + + TRACE("(%p)->(%x %p)\n", This, fDeep, clonedNode); + + hres = HTMLDOMAttribute_Create(This->name, NULL, 0, This->node.doc, &new_attr); + if(FAILED(hres)) + return hres; + + if(This->elem) + hres = get_elem_attr_value_by_dispid(This->elem, This->dispid, &new_attr->value); + else + hres = VariantCopy(&new_attr->value, &This->value); + if(FAILED(hres)) { + IHTMLDOMAttribute_Release(&new_attr->IHTMLDOMAttribute_iface); + return hres; + } + + *clonedNode = &new_attr->IHTMLDOMAttribute_iface; + return hres; }
static const IHTMLDOMAttribute2Vtbl HTMLDOMAttribute2Vtbl = { diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 4daeb4ff552..ba82a32c05c 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -9947,8 +9947,10 @@ static void test_elems(IHTMLDocument2 *doc) static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) { IHTMLDOMAttribute2 *attr; + IHTMLDOMAttribute *clone; IHTMLDocument2 *doc_node; IHTMLWindow2 *window; + VARIANT v, v_clone; IDispatch *disp; HRESULT hres; LONG type; @@ -9978,6 +9980,26 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) IHTMLDocument2_Release(doc_node); IDispatch_Release(disp);
+ hres = IHTMLDOMAttribute2_cloneNode(attr, VARIANT_TRUE, &clone); + ok(hres == S_OK, "cloneNode failed: %08lx\n", hres); + ok(!iface_cmp((IUnknown*)attr, (IUnknown*)clone), "attr == cloned attr\n"); + + V_VT(&v) = VT_EMPTY; + V_VT(&v_clone) = VT_EMPTY; + hres = IHTMLDOMAttribute_get_nodeValue(test_attr, &v); + ok(hres == S_OK, "get_nodeValue failed: %08lx\n", hres); + hres = IHTMLDOMAttribute_get_nodeValue(clone, &v_clone); + ok(hres == S_OK, "get_nodeValue failed: %08lx\n", hres); + if(V_VT(&v) == VT_BSTR) + ok(VarCmp(&v, &v_clone, 0, 0) == VARCMP_EQ, "attr value %s != cloned attr value %s\n", wine_dbgstr_variant(&v), wine_dbgstr_variant(&v_clone)); + else { + todo_wine + ok(V_VT(&v_clone) == VT_BSTR, "unexpected cloned attr value %s for non-string attr value %s\n", wine_dbgstr_variant(&v), wine_dbgstr_variant(&v_clone)); + } + IHTMLDOMAttribute_Release(clone); + VariantClear(&v_clone); + VariantClear(&v); + IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 8 ++++++-- dlls/mshtml/tests/dom.c | 16 ++++++++++++++++ 2 files changed, 22 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 5b3f070f0a7..3d50b17b5f2 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -309,8 +309,12 @@ static HRESULT WINAPI HTMLDOMAttribute2_appendChild(IHTMLDOMAttribute2 *iface, I IHTMLDOMNode **node) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p %p)\n", This, newChild, node); - return E_NOTIMPL; + + TRACE("(%p)->(%p %p)\n", This, newChild, node); + + /* mostly a stub, doesn't really append anything on native either */ + *node = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_hasChildNodes(IHTMLDOMAttribute2 *iface, VARIANT_BOOL *fChildren) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index ba82a32c05c..b562ca85143 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -9946,13 +9946,16 @@ static void test_elems(IHTMLDocument2 *doc)
static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) { + IHTMLDOMNode *node, *elem_node; IHTMLDOMAttribute2 *attr; IHTMLDOMAttribute *clone; IHTMLDocument2 *doc_node; IHTMLWindow2 *window; + IHTMLElement *elem; VARIANT v, v_clone; IDispatch *disp; HRESULT hres; + BSTR bstr; LONG type;
hres = IHTMLDOMAttribute_QueryInterface(test_attr, &IID_IHTMLDOMAttribute2, (void**)&attr); @@ -10000,6 +10003,19 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) VariantClear(&v_clone); VariantClear(&v);
+ bstr = SysAllocString(L"div"); + hres = IHTMLDocument2_createElement(doc, bstr, &elem); + ok(hres == S_OK, "createElement failed: %08lx\n", hres); + hres = IHTMLElement_QueryInterface(elem, &IID_IHTMLDOMNode, (void**)&elem_node); + ok(hres == S_OK, "Could not get IHTMLDOMNode iface: %08lx\n", hres); + IHTMLElement_Release(elem); + SysFreeString(bstr); + + hres = IHTMLDOMAttribute2_appendChild(attr, elem_node, &node); + ok(hres == S_OK, "appendChild failed: %08lx\n", hres); + ok(!node, "appended child != NULL\n"); + + IHTMLDOMNode_Release(elem_node); IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 8 ++++++-- dlls/mshtml/tests/dom.c | 5 +++++ 2 files changed, 11 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 3d50b17b5f2..c64ac5bad14 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -285,8 +285,12 @@ static HRESULT WINAPI HTMLDOMAttribute2_insertBefore(IHTMLDOMAttribute2 *iface, VARIANT refChild, IHTMLDOMNode **node) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p %s %p)\n", This, newChild, debugstr_variant(&refChild), node); - return E_NOTIMPL; + + TRACE("(%p)->(%p %s %p)\n", This, newChild, debugstr_variant(&refChild), node); + + /* mostly a stub, doesn't really insert anything on native either */ + *node = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_replaceChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode *newChild, diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index b562ca85143..5b043ff4b93 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10015,6 +10015,11 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "appendChild failed: %08lx\n", hres); ok(!node, "appended child != NULL\n");
+ V_VT(&v) = VT_NULL; + hres = IHTMLDOMAttribute2_insertBefore(attr, elem_node, v, &node); + ok(hres == S_OK, "insertBefore failed: %08lx\n", hres); + ok(!node, "inserted node != NULL\n"); + IHTMLDOMNode_Release(elem_node); IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 9 +++++++++ 2 files changed, 14 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index c64ac5bad14..d3577b34096 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -324,8 +324,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_appendChild(IHTMLDOMAttribute2 *iface, I static HRESULT WINAPI HTMLDOMAttribute2_hasChildNodes(IHTMLDOMAttribute2 *iface, VARIANT_BOOL *fChildren) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, fChildren); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, fChildren); + + *fChildren = VARIANT_FALSE; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_cloneNode(IHTMLDOMAttribute2 *iface, VARIANT_BOOL fDeep, diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 5b043ff4b93..a611ff7584a 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -9952,6 +9952,7 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) IHTMLDocument2 *doc_node; IHTMLWindow2 *window; IHTMLElement *elem; + VARIANT_BOOL vbool; VARIANT v, v_clone; IDispatch *disp; HRESULT hres; @@ -10003,6 +10004,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) VariantClear(&v_clone); VariantClear(&v);
+ hres = IHTMLDOMAttribute2_hasChildNodes(attr, &vbool); + ok(hres == S_OK, "hasChildNodes failed: %08lx\n", hres); + ok(vbool == VARIANT_FALSE, "hasChildNodes returned %d\n", vbool); + bstr = SysAllocString(L"div"); hres = IHTMLDocument2_createElement(doc, bstr, &elem); ok(hres == S_OK, "createElement failed: %08lx\n", hres); @@ -10020,6 +10025,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "insertBefore failed: %08lx\n", hres); ok(!node, "inserted node != NULL\n");
+ hres = IHTMLDOMAttribute2_hasChildNodes(attr, &vbool); + ok(hres == S_OK, "hasChildNodes failed: %08lx\n", hres); + ok(vbool == VARIANT_FALSE, "hasChildNodes returned %d\n", vbool); + IHTMLDOMNode_Release(elem_node); IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 4 ++++ 2 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index d3577b34096..84fe3d5ee20 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -228,8 +228,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_parentNode(IHTMLDOMAttribute2 *iface static HRESULT WINAPI HTMLDOMAttribute2_get_childNodes(IHTMLDOMAttribute2 *iface, IDispatch **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_firstChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index a611ff7584a..fdcbeb466aa 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10008,6 +10008,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "hasChildNodes failed: %08lx\n", hres); ok(vbool == VARIANT_FALSE, "hasChildNodes returned %d\n", vbool);
+ hres = IHTMLDOMAttribute2_get_childNodes(attr, &disp); + ok(hres == S_OK, "get_childNodes failed: %08lx\n", hres); + ok(!disp, "childNodes != NULL\n"); + bstr = SysAllocString(L"div"); hres = IHTMLDocument2_createElement(doc, bstr, &elem); ok(hres == S_OK, "createElement failed: %08lx\n", hres);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 8 ++++++++ 2 files changed, 13 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 84fe3d5ee20..3945b10d084 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -238,8 +238,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_childNodes(IHTMLDOMAttribute2 *iface static HRESULT WINAPI HTMLDOMAttribute2_get_firstChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_lastChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index fdcbeb466aa..00ddc44a243 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10012,6 +10012,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "get_childNodes failed: %08lx\n", hres); ok(!disp, "childNodes != NULL\n");
+ hres = IHTMLDOMAttribute2_get_firstChild(attr, &node); + ok(hres == S_OK, "get_firstChild failed: %08lx\n", hres); + ok(!node, "firstChild != NULL\n"); + bstr = SysAllocString(L"div"); hres = IHTMLDocument2_createElement(doc, bstr, &elem); ok(hres == S_OK, "createElement failed: %08lx\n", hres); @@ -10033,6 +10037,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "hasChildNodes failed: %08lx\n", hres); ok(vbool == VARIANT_FALSE, "hasChildNodes returned %d\n", vbool);
+ hres = IHTMLDOMAttribute2_get_firstChild(attr, &node); + ok(hres == S_OK, "get_firstChild failed: %08lx\n", hres); + ok(!node, "firstChild != NULL\n"); + IHTMLDOMNode_Release(elem_node); IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 4 ++++ 2 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 3945b10d084..e8857296464 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -248,8 +248,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_firstChild(IHTMLDOMAttribute2 *iface static HRESULT WINAPI HTMLDOMAttribute2_get_lastChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_previousSibling(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 00ddc44a243..7ff951b8760 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10016,6 +10016,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "get_firstChild failed: %08lx\n", hres); ok(!node, "firstChild != NULL\n");
+ hres = IHTMLDOMAttribute2_get_lastChild(attr, &node); + ok(hres == S_OK, "get_lastChild failed: %08lx\n", hres); + ok(!node, "lastChild != NULL\n"); + bstr = SysAllocString(L"div"); hres = IHTMLDocument2_createElement(doc, bstr, &elem); ok(hres == S_OK, "createElement failed: %08lx\n", hres);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 4 ++++ 2 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index e8857296464..654a78e32da 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -258,8 +258,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_lastChild(IHTMLDOMAttribute2 *iface, static HRESULT WINAPI HTMLDOMAttribute2_get_previousSibling(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_nextSibling(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 7ff951b8760..329849b632f 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10020,6 +10020,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "get_lastChild failed: %08lx\n", hres); ok(!node, "lastChild != NULL\n");
+ hres = IHTMLDOMAttribute2_get_previousSibling(attr, &node); + ok(hres == S_OK, "get_previousSibling failed: %08lx\n", hres); + ok(!node, "previousSibling != NULL\n"); + bstr = SysAllocString(L"div"); hres = IHTMLDocument2_createElement(doc, bstr, &elem); ok(hres == S_OK, "createElement failed: %08lx\n", hres);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 7 +++++-- dlls/mshtml/tests/dom.c | 4 ++++ 2 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 654a78e32da..356195fc1e9 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -268,8 +268,11 @@ static HRESULT WINAPI HTMLDOMAttribute2_get_previousSibling(IHTMLDOMAttribute2 * static HRESULT WINAPI HTMLDOMAttribute2_get_nextSibling(IHTMLDOMAttribute2 *iface, IHTMLDOMNode **p) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_get_attributes(IHTMLDOMAttribute2 *iface, IDispatch **p) diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 329849b632f..db7c2ed3e1e 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10024,6 +10024,10 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "get_previousSibling failed: %08lx\n", hres); ok(!node, "previousSibling != NULL\n");
+ hres = IHTMLDOMAttribute2_get_nextSibling(attr, &node); + ok(hres == S_OK, "get_nextSibling failed: %08lx\n", hres); + ok(!node, "nextSibling != NULL\n"); + bstr = SysAllocString(L"div"); hres = IHTMLDocument2_createElement(doc, bstr, &elem); ok(hres == S_OK, "createElement failed: %08lx\n", hres);
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 8 ++++++-- dlls/mshtml/tests/dom.c | 8 ++++++++ 2 files changed, 14 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 356195fc1e9..65c068a5e5b 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -312,8 +312,12 @@ static HRESULT WINAPI HTMLDOMAttribute2_replaceChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode *oldChild, IHTMLDOMNode **node) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p %p %p)\n", This, newChild, oldChild, node); - return E_NOTIMPL; + + TRACE("(%p)->(%p %p %p)\n", This, newChild, oldChild, node); + + /* mostly a stub, doesn't really replace anything on native either */ + *node = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_removeChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode *oldChild, diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index db7c2ed3e1e..81a1e5c1031 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10053,6 +10053,14 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "get_firstChild failed: %08lx\n", hres); ok(!node, "firstChild != NULL\n");
+ hres = IHTMLDOMAttribute2_replaceChild(attr, elem_node, NULL, &node); + ok(hres == S_OK, "replaceChild failed: %08lx\n", hres); + ok(!node, "replaced node != NULL\n"); + + hres = IHTMLDOMAttribute2_replaceChild(attr, elem_node, elem_node, &node); + ok(hres == S_OK, "replaceChild failed: %08lx\n", hres); + ok(!node, "replaced node != NULL\n"); + IHTMLDOMNode_Release(elem_node); IHTMLDOMAttribute2_Release(attr); }
From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlattr.c | 8 ++++++-- dlls/mshtml/tests/dom.c | 8 ++++++++ 2 files changed, 14 insertions(+), 2 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 65c068a5e5b..bed4829cb59 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -324,8 +324,12 @@ static HRESULT WINAPI HTMLDOMAttribute2_removeChild(IHTMLDOMAttribute2 *iface, I IHTMLDOMNode **node) { HTMLDOMAttribute *This = impl_from_IHTMLDOMAttribute2(iface); - FIXME("(%p)->(%p %p)\n", This, oldChild, node); - return E_NOTIMPL; + + TRACE("(%p)->(%p %p)\n", This, oldChild, node); + + /* mostly a stub, doesn't really remove anything on native either */ + *node = NULL; + return S_OK; }
static HRESULT WINAPI HTMLDOMAttribute2_appendChild(IHTMLDOMAttribute2 *iface, IHTMLDOMNode *newChild, diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 81a1e5c1031..dd987350e72 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -10061,6 +10061,14 @@ static void test_attr_node(IHTMLDOMAttribute *test_attr, IHTMLDocument2 *doc) ok(hres == S_OK, "replaceChild failed: %08lx\n", hres); ok(!node, "replaced node != NULL\n");
+ hres = IHTMLDOMAttribute2_removeChild(attr, NULL, &node); + ok(hres == S_OK, "removeChild failed: %08lx\n", hres); + ok(!node, "removed node != NULL\n"); + + hres = IHTMLDOMAttribute2_removeChild(attr, elem_node, &node); + ok(hres == S_OK, "removeChild failed: %08lx\n", hres); + ok(!node, "removed node != NULL\n"); + IHTMLDOMNode_Release(elem_node); IHTMLDOMAttribute2_Release(attr); }
Jacek Caban (@jacek) commented about dlls/mshtml/mshtml_private.h:
};
typedef struct {
- DispatchEx dispex;
- HTMLDOMNode node;
It's impossible to review that part properly without more context. For example, I could imagine implementing IE9+ attributes as a completely separate object rather than trying to fit everything into the existing one, but I can't say without seeing more context.
In this MR, you're only using it to store the owner document, but you could just as easily store that in the attribute itself or leave the `ownerDocument` patch out of this series altogether. If it turns out to be necessary, we can move it in a later MR that actually makes use of it, when it will be reviewable.
On Wed May 14 07:59:14 2025 +0000, Jacek Caban wrote:
It's impossible to review that part properly without more context. For example, I could imagine implementing IE9+ attributes as a completely separate object rather than trying to fit everything into the existing one, but I can't say without seeing more context. In this MR, you're only using it to store the owner document, but you could just as easily store that in the attribute itself or leave the `ownerDocument` patch out of this series altogether. If it turns out to be necessary, we can move it in a later MR that actually makes use of it, when it will be reviewable.
Separate object might work, but needs a deeper look and will need some reworks, not entirely sure yet if it's a simplification to what I have, but honestly both require special casing anyway, so maybe it is.
Anyway, I made it hold document now without going through the node change.