Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /* This Source Code Form is subject to the terms of the Mozilla Public
3 : * License, v. 2.0. If a copy of the MPL was not distributed with this
4 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 :
6 : #ifndef mozilla_dom_XPathResult_h
7 : #define mozilla_dom_XPathResult_h
8 :
9 : #include "nsStubMutationObserver.h"
10 : #include "nsAutoPtr.h"
11 : #include "nsCOMPtr.h"
12 : #include "nsCOMArray.h"
13 : #include "nsWeakPtr.h"
14 : #include "nsCycleCollectionParticipant.h"
15 : #include "mozilla/Attributes.h"
16 : #include "mozilla/ErrorResult.h"
17 : #include "nsString.h"
18 : #include "nsWrapperCache.h"
19 : #include "nsINode.h"
20 :
21 : class nsIDocument;
22 : class txAExprResult;
23 :
24 : // {662f2c9a-c7cd-4cab-9349-e733df5a838c}
25 : #define NS_IXPATHRESULT_IID \
26 : { 0x662f2c9a, 0xc7cd, 0x4cab, {0x93, 0x49, 0xe7, 0x33, 0xdf, 0x5a, 0x83, 0x8c }}
27 :
28 0 : class nsIXPathResult : public nsISupports
29 : {
30 : public:
31 : NS_DECLARE_STATIC_IID_ACCESSOR(NS_IXPATHRESULT_IID)
32 : virtual nsresult SetExprResult(txAExprResult *aExprResult,
33 : uint16_t aResultType,
34 : nsINode* aContextNode) = 0;
35 : virtual nsresult GetExprResult(txAExprResult **aExprResult) = 0;
36 : virtual nsresult Clone(nsIXPathResult **aResult) = 0;
37 : };
38 :
39 : NS_DEFINE_STATIC_IID_ACCESSOR(nsIXPathResult, NS_IXPATHRESULT_IID)
40 :
41 : namespace mozilla {
42 : namespace dom {
43 :
44 : /**
45 : * A class for evaluating an XPath expression string
46 : */
47 : class XPathResult final : public nsIXPathResult,
48 : public nsStubMutationObserver,
49 : public nsWrapperCache
50 : {
51 : ~XPathResult();
52 :
53 : public:
54 : explicit XPathResult(nsINode* aParent);
55 : XPathResult(const XPathResult &aResult);
56 :
57 : enum {
58 : ANY_TYPE = 0U,
59 : NUMBER_TYPE = 1U,
60 : STRING_TYPE = 2U,
61 : BOOLEAN_TYPE = 3U,
62 : UNORDERED_NODE_ITERATOR_TYPE = 4U,
63 : ORDERED_NODE_ITERATOR_TYPE = 5U,
64 : UNORDERED_NODE_SNAPSHOT_TYPE = 6U,
65 : ORDERED_NODE_SNAPSHOT_TYPE = 7U,
66 : ANY_UNORDERED_NODE_TYPE = 8U,
67 : FIRST_ORDERED_NODE_TYPE = 9U
68 : };
69 :
70 : // nsISupports interface
71 : NS_DECL_CYCLE_COLLECTING_ISUPPORTS
72 0 : NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_AMBIGUOUS(XPathResult,
73 : nsIXPathResult)
74 :
75 : static XPathResult* FromSupports(nsISupports* aSupports)
76 : {
77 : return static_cast<XPathResult*>(static_cast<nsIXPathResult*>(aSupports));
78 : }
79 :
80 : virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override;
81 0 : nsINode* GetParentObject() const
82 : {
83 0 : return mParent;
84 : }
85 0 : uint16_t ResultType() const
86 : {
87 0 : return mResultType;
88 : }
89 0 : double GetNumberValue(ErrorResult& aRv) const
90 : {
91 0 : if (mResultType != NUMBER_TYPE) {
92 0 : aRv.Throw(NS_ERROR_DOM_TYPE_ERR);
93 0 : return 0;
94 : }
95 :
96 0 : return mNumberResult;
97 : }
98 0 : void GetStringValue(nsAString &aStringValue, ErrorResult& aRv) const
99 : {
100 0 : if (mResultType != STRING_TYPE) {
101 0 : aRv.Throw(NS_ERROR_DOM_TYPE_ERR);
102 0 : return;
103 : }
104 :
105 0 : aStringValue = mStringResult;
106 : }
107 0 : bool GetBooleanValue(ErrorResult& aRv) const
108 : {
109 0 : if (mResultType != BOOLEAN_TYPE) {
110 0 : aRv.Throw(NS_ERROR_DOM_TYPE_ERR);
111 0 : return false;
112 : }
113 :
114 0 : return mBooleanResult;
115 : }
116 0 : nsINode* GetSingleNodeValue(ErrorResult& aRv) const
117 : {
118 0 : if (!isNode()) {
119 0 : aRv.Throw(NS_ERROR_DOM_TYPE_ERR);
120 0 : return nullptr;
121 : }
122 :
123 0 : return mResultNodes.SafeObjectAt(0);
124 : }
125 0 : bool InvalidIteratorState() const
126 : {
127 0 : return isIterator() && mInvalidIteratorState;
128 : }
129 0 : uint32_t GetSnapshotLength(ErrorResult& aRv) const
130 : {
131 0 : if (!isSnapshot()) {
132 0 : aRv.Throw(NS_ERROR_DOM_TYPE_ERR);
133 0 : return 0;
134 : }
135 :
136 0 : return (uint32_t)mResultNodes.Count();
137 : }
138 : nsINode* IterateNext(ErrorResult& aRv);
139 0 : nsINode* SnapshotItem(uint32_t aIndex, ErrorResult& aRv) const
140 : {
141 0 : if (!isSnapshot()) {
142 0 : aRv.Throw(NS_ERROR_DOM_TYPE_ERR);
143 0 : return nullptr;
144 : }
145 :
146 0 : return mResultNodes.SafeObjectAt(aIndex);
147 : }
148 :
149 : // nsIMutationObserver interface
150 : NS_DECL_NSIMUTATIONOBSERVER_CHARACTERDATACHANGED
151 : NS_DECL_NSIMUTATIONOBSERVER_ATTRIBUTECHANGED
152 : NS_DECL_NSIMUTATIONOBSERVER_CONTENTAPPENDED
153 : NS_DECL_NSIMUTATIONOBSERVER_CONTENTINSERTED
154 : NS_DECL_NSIMUTATIONOBSERVER_CONTENTREMOVED
155 : NS_DECL_NSIMUTATIONOBSERVER_NODEWILLBEDESTROYED
156 :
157 : nsresult SetExprResult(txAExprResult *aExprResult, uint16_t aResultType,
158 : nsINode* aContextNode) override;
159 : nsresult GetExprResult(txAExprResult **aExprResult) override;
160 : nsresult Clone(nsIXPathResult **aResult) override;
161 : void RemoveObserver();
162 : private:
163 0 : static bool isSnapshot(uint16_t aResultType)
164 : {
165 0 : return aResultType == UNORDERED_NODE_SNAPSHOT_TYPE ||
166 0 : aResultType == ORDERED_NODE_SNAPSHOT_TYPE;
167 : }
168 0 : static bool isIterator(uint16_t aResultType)
169 : {
170 0 : return aResultType == UNORDERED_NODE_ITERATOR_TYPE ||
171 0 : aResultType == ORDERED_NODE_ITERATOR_TYPE;
172 : }
173 0 : static bool isNode(uint16_t aResultType)
174 : {
175 0 : return aResultType == FIRST_ORDERED_NODE_TYPE ||
176 0 : aResultType == ANY_UNORDERED_NODE_TYPE;
177 : }
178 0 : bool isSnapshot() const
179 : {
180 0 : return isSnapshot(mResultType);
181 : }
182 0 : bool isIterator() const
183 : {
184 0 : return isIterator(mResultType);
185 : }
186 0 : bool isNode() const
187 : {
188 0 : return isNode(mResultType);
189 : }
190 :
191 : void Invalidate(const nsIContent* aChangeRoot);
192 :
193 : nsCOMPtr<nsINode> mParent;
194 : RefPtr<txAExprResult> mResult;
195 : nsCOMArray<nsINode> mResultNodes;
196 : nsCOMPtr<nsIDocument> mDocument;
197 : nsWeakPtr mContextNode;
198 : uint32_t mCurrentPos;
199 : uint16_t mResultType;
200 : bool mInvalidIteratorState;
201 : bool mBooleanResult;
202 : double mNumberResult;
203 : nsString mStringResult;
204 : };
205 :
206 : } // namespace dom
207 : } // namespace mozilla
208 :
209 : #endif /* mozilla_dom_XPathResult_h */
|