2 * Node list implementation
4 * Copyright 2005 Mike McCormack
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
32 #include "msxml_private.h"
34 #include "wine/debug.h"
36 /* This file implements the object returned by childNodes property. Note that this is
37 * not the IXMLDOMNodeList returned by XPath querites - it's implemented in queryresult.c.
38 * They are different because the list returned by childNodes:
39 * - is "live" - changes to the XML tree are automatically reflected in the list
40 * - doesn't supports IXMLDOMSelection
41 * - note that an attribute node have a text child in DOM but not in the XPath data model
42 * thus the child is inaccessible by an XPath query
45 WINE_DEFAULT_DEBUG_CHANNEL(msxml
);
49 typedef struct _xmlnodelist
51 const struct IXMLDOMNodeListVtbl
*lpVtbl
;
57 static inline xmlnodelist
*impl_from_IXMLDOMNodeList( IXMLDOMNodeList
*iface
)
59 return (xmlnodelist
*)((char*)iface
- FIELD_OFFSET(xmlnodelist
, lpVtbl
));
62 static HRESULT WINAPI
xmlnodelist_QueryInterface(
63 IXMLDOMNodeList
*iface
,
67 TRACE("%p %s %p\n", iface
, debugstr_guid(riid
), ppvObject
);
69 if ( IsEqualGUID( riid
, &IID_IUnknown
) ||
70 IsEqualGUID( riid
, &IID_IDispatch
) ||
71 IsEqualGUID( riid
, &IID_IXMLDOMNodeList
) )
77 FIXME("interface %s not implemented\n", debugstr_guid(riid
));
82 IXMLDOMNodeList_AddRef( iface
);
87 static ULONG WINAPI
xmlnodelist_AddRef(
88 IXMLDOMNodeList
*iface
)
90 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
91 return InterlockedIncrement( &This
->ref
);
94 static ULONG WINAPI
xmlnodelist_Release(
95 IXMLDOMNodeList
*iface
)
97 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
100 ref
= InterlockedDecrement( &This
->ref
);
103 xmldoc_release( This
->parent
->doc
);
104 HeapFree( GetProcessHeap(), 0, This
);
110 static HRESULT WINAPI
xmlnodelist_GetTypeInfoCount(
111 IXMLDOMNodeList
*iface
,
114 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
116 TRACE("(%p)->(%p)\n", This
, pctinfo
);
123 static HRESULT WINAPI
xmlnodelist_GetTypeInfo(
124 IXMLDOMNodeList
*iface
,
127 ITypeInfo
** ppTInfo
)
129 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
132 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
134 hr
= get_typeinfo(IXMLDOMNodeList_tid
, ppTInfo
);
139 static HRESULT WINAPI
xmlnodelist_GetIDsOfNames(
140 IXMLDOMNodeList
*iface
,
147 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
151 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
,
154 if(!rgszNames
|| cNames
== 0 || !rgDispId
)
157 hr
= get_typeinfo(IXMLDOMNodeList_tid
, &typeinfo
);
160 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
161 ITypeInfo_Release(typeinfo
);
167 static HRESULT WINAPI
xmlnodelist_Invoke(
168 IXMLDOMNodeList
*iface
,
173 DISPPARAMS
* pDispParams
,
175 EXCEPINFO
* pExcepInfo
,
178 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
182 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
183 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
185 hr
= get_typeinfo(IXMLDOMNodeList_tid
, &typeinfo
);
188 hr
= ITypeInfo_Invoke(typeinfo
, &(This
->lpVtbl
), dispIdMember
, wFlags
, pDispParams
,
189 pVarResult
, pExcepInfo
, puArgErr
);
190 ITypeInfo_Release(typeinfo
);
196 static HRESULT WINAPI
xmlnodelist_get_item(
197 IXMLDOMNodeList
* iface
,
199 IXMLDOMNode
** listItem
)
201 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
205 TRACE("%p %ld\n", This
, index
);
212 curr
= This
->parent
->children
;
215 if(nodeIndex
++ == index
) break;
218 if(!curr
) return S_FALSE
;
220 *listItem
= create_node( curr
);
225 static HRESULT WINAPI
xmlnodelist_get_length(
226 IXMLDOMNodeList
* iface
,
233 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
237 curr
= This
->parent
->children
;
244 *listLength
= nodeCount
;
248 static HRESULT WINAPI
xmlnodelist_nextNode(
249 IXMLDOMNodeList
* iface
,
250 IXMLDOMNode
** nextItem
)
252 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
254 TRACE("%p %p\n", This
, nextItem
);
261 *nextItem
= create_node( This
->current
);
262 This
->current
= This
->current
->next
;
266 static HRESULT WINAPI
xmlnodelist_reset(
267 IXMLDOMNodeList
* iface
)
269 xmlnodelist
*This
= impl_from_IXMLDOMNodeList( iface
);
272 This
->current
= This
->parent
->children
;
276 static HRESULT WINAPI
xmlnodelist__newEnum(
277 IXMLDOMNodeList
* iface
,
285 static const struct IXMLDOMNodeListVtbl xmlnodelist_vtbl
=
287 xmlnodelist_QueryInterface
,
290 xmlnodelist_GetTypeInfoCount
,
291 xmlnodelist_GetTypeInfo
,
292 xmlnodelist_GetIDsOfNames
,
294 xmlnodelist_get_item
,
295 xmlnodelist_get_length
,
296 xmlnodelist_nextNode
,
298 xmlnodelist__newEnum
,
301 IXMLDOMNodeList
* create_children_nodelist( xmlNodePtr node
)
303 xmlnodelist
*nodelist
;
305 nodelist
= HeapAlloc( GetProcessHeap(), 0, sizeof *nodelist
);
309 nodelist
->lpVtbl
= &xmlnodelist_vtbl
;
311 nodelist
->parent
= node
;
312 nodelist
->current
= node
->children
;
314 xmldoc_add_ref( node
->doc
);
316 return (IXMLDOMNodeList
*) &nodelist
->lpVtbl
;