|
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
|
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 nsIMutationObserver_h |
|
7 #define nsIMutationObserver_h |
|
8 |
|
9 #include "nsISupports.h" |
|
10 |
|
11 class nsIAtom; |
|
12 class nsIContent; |
|
13 class nsIDocument; |
|
14 class nsINode; |
|
15 |
|
16 namespace mozilla { |
|
17 namespace dom { |
|
18 class Element; |
|
19 } // namespace dom |
|
20 } // namespace mozilla |
|
21 |
|
22 #define NS_IMUTATION_OBSERVER_IID \ |
|
23 { 0x16fe5e3e, 0xeadc, 0x4312, \ |
|
24 { 0x9d, 0x44, 0xb6, 0xbe, 0xdd, 0x6b, 0x54, 0x74 } } |
|
25 |
|
26 /** |
|
27 * Information details about a characterdata change. Basically, we |
|
28 * view all changes as replacements of a length of text at some offset |
|
29 * with some other text (of possibly some other length). |
|
30 */ |
|
31 struct CharacterDataChangeInfo |
|
32 { |
|
33 /** |
|
34 * True if this character data change is just an append. |
|
35 */ |
|
36 bool mAppend; |
|
37 |
|
38 /** |
|
39 * The offset in the text where the change occurred. |
|
40 */ |
|
41 uint32_t mChangeStart; |
|
42 |
|
43 /** |
|
44 * The offset such that mChangeEnd - mChangeStart is equal to the length of |
|
45 * the text we removed. If this was a pure insert or append, this is equal to |
|
46 * mChangeStart. |
|
47 */ |
|
48 uint32_t mChangeEnd; |
|
49 |
|
50 /** |
|
51 * The length of the text that was inserted in place of the removed text. If |
|
52 * this was a pure text removal, this is 0. |
|
53 */ |
|
54 uint32_t mReplaceLength; |
|
55 |
|
56 /** |
|
57 * The net result is that mChangeStart characters at the beginning of the |
|
58 * text remained as they were. The next mChangeEnd - mChangeStart characters |
|
59 * were removed, and mReplaceLength characters were inserted in their place. |
|
60 * The text that used to begin at mChangeEnd now begins at |
|
61 * mChangeStart + mReplaceLength. |
|
62 */ |
|
63 |
|
64 struct Details { |
|
65 enum { |
|
66 eMerge, // two text nodes are merged as a result of normalize() |
|
67 eSplit // a text node is split as a result of splitText() |
|
68 } mType; |
|
69 /** |
|
70 * For eMerge it's the text node that will be removed, for eSplit it's the |
|
71 * new text node. |
|
72 */ |
|
73 nsIContent* mNextSibling; |
|
74 }; |
|
75 |
|
76 /** |
|
77 * Used for splitText() and normalize(), otherwise null. |
|
78 */ |
|
79 Details* mDetails; |
|
80 }; |
|
81 |
|
82 /** |
|
83 * Mutation observer interface |
|
84 * |
|
85 * See nsINode::AddMutationObserver, nsINode::RemoveMutationObserver for how to |
|
86 * attach or remove your observers. |
|
87 * |
|
88 * WARNING: During these notifications, you are not allowed to perform |
|
89 * any mutations to the current or any other document, or start a |
|
90 * network load. If you need to perform such operations do that |
|
91 * during the _last_ nsIDocumentObserver::EndUpdate notification. The |
|
92 * expection for this is ParentChainChanged, where mutations should be |
|
93 * done from an async event, as the notification might not be |
|
94 * surrounded by BeginUpdate/EndUpdate calls. |
|
95 */ |
|
96 class nsIMutationObserver : public nsISupports |
|
97 { |
|
98 public: |
|
99 NS_DECLARE_STATIC_IID_ACCESSOR(NS_IMUTATION_OBSERVER_IID) |
|
100 |
|
101 /** |
|
102 * Notification that the node value of a data node (text, cdata, pi, comment) |
|
103 * will be changed. |
|
104 * |
|
105 * This notification is not sent when a piece of content is |
|
106 * added/removed from the document (the other notifications are used |
|
107 * for that). |
|
108 * |
|
109 * @param aDocument The owner-document of aContent. Can be null. |
|
110 * @param aContent The piece of content that changed. Is never null. |
|
111 * @param aInfo The structure with information details about the change. |
|
112 * |
|
113 * @note Callers of this method might not hold a strong reference to the |
|
114 * observer. The observer is responsible for making sure it stays |
|
115 * alive for the duration of the call as needed. The observer may |
|
116 * assume that this call will happen when there are script blockers on |
|
117 * the stack. |
|
118 */ |
|
119 virtual void CharacterDataWillChange(nsIDocument *aDocument, |
|
120 nsIContent* aContent, |
|
121 CharacterDataChangeInfo* aInfo) = 0; |
|
122 |
|
123 /** |
|
124 * Notification that the node value of a data node (text, cdata, pi, comment) |
|
125 * has changed. |
|
126 * |
|
127 * This notification is not sent when a piece of content is |
|
128 * added/removed from the document (the other notifications are used |
|
129 * for that). |
|
130 * |
|
131 * @param aDocument The owner-document of aContent. Can be null. |
|
132 * @param aContent The piece of content that changed. Is never null. |
|
133 * @param aInfo The structure with information details about the change. |
|
134 * |
|
135 * @note Callers of this method might not hold a strong reference to the |
|
136 * observer. The observer is responsible for making sure it stays |
|
137 * alive for the duration of the call as needed. The observer may |
|
138 * assume that this call will happen when there are script blockers on |
|
139 * the stack. |
|
140 */ |
|
141 virtual void CharacterDataChanged(nsIDocument *aDocument, |
|
142 nsIContent* aContent, |
|
143 CharacterDataChangeInfo* aInfo) = 0; |
|
144 |
|
145 /** |
|
146 * Notification that an attribute of an element will change. This |
|
147 * can happen before the BeginUpdate for the change and may not |
|
148 * always be followed by an AttributeChanged (in particular, if the |
|
149 * attribute doesn't actually change there will be no corresponding |
|
150 * AttributeChanged). |
|
151 * |
|
152 * @param aDocument The owner-document of aContent. Can be null. |
|
153 * @param aContent The element whose attribute will change |
|
154 * @param aNameSpaceID The namespace id of the changing attribute |
|
155 * @param aAttribute The name of the changing attribute |
|
156 * @param aModType Whether or not the attribute will be added, changed, or |
|
157 * removed. The constants are defined in |
|
158 * nsIDOMMutationEvent.h. |
|
159 * |
|
160 * @note Callers of this method might not hold a strong reference to the |
|
161 * observer. The observer is responsible for making sure it stays |
|
162 * alive for the duration of the call as needed. The observer may |
|
163 * assume that this call will happen when there are script blockers on |
|
164 * the stack. |
|
165 */ |
|
166 virtual void AttributeWillChange(nsIDocument* aDocument, |
|
167 mozilla::dom::Element* aElement, |
|
168 int32_t aNameSpaceID, |
|
169 nsIAtom* aAttribute, |
|
170 int32_t aModType) = 0; |
|
171 |
|
172 /** |
|
173 * Notification that an attribute of an element has changed. |
|
174 * |
|
175 * @param aDocument The owner-document of aContent. Can be null. |
|
176 * @param aElement The element whose attribute changed |
|
177 * @param aNameSpaceID The namespace id of the changed attribute |
|
178 * @param aAttribute The name of the changed attribute |
|
179 * @param aModType Whether or not the attribute was added, changed, or |
|
180 * removed. The constants are defined in |
|
181 * nsIDOMMutationEvent.h. |
|
182 * |
|
183 * @note Callers of this method might not hold a strong reference to the |
|
184 * observer. The observer is responsible for making sure it stays |
|
185 * alive for the duration of the call as needed. The observer may |
|
186 * assume that this call will happen when there are script blockers on |
|
187 * the stack. |
|
188 */ |
|
189 virtual void AttributeChanged(nsIDocument* aDocument, |
|
190 mozilla::dom::Element* aElement, |
|
191 int32_t aNameSpaceID, |
|
192 nsIAtom* aAttribute, |
|
193 int32_t aModType) = 0; |
|
194 |
|
195 /** |
|
196 * Notification that an attribute of an element has been |
|
197 * set to the value it already had. |
|
198 * |
|
199 * @param aDocument The owner-document of aContent. |
|
200 * @param aElement The element whose attribute changed |
|
201 * @param aNameSpaceID The namespace id of the changed attribute |
|
202 * @param aAttribute The name of the changed attribute |
|
203 */ |
|
204 virtual void AttributeSetToCurrentValue(nsIDocument* aDocument, |
|
205 mozilla::dom::Element* aElement, |
|
206 int32_t aNameSpaceID, |
|
207 nsIAtom* aAttribute) {} |
|
208 |
|
209 /** |
|
210 * Notification that one or more content nodes have been appended to the |
|
211 * child list of another node in the tree. |
|
212 * |
|
213 * @param aDocument The owner-document of aContent. Can be null. |
|
214 * @param aContainer The container that had new children appended. Is never |
|
215 * null. |
|
216 * @param aFirstNewContent the node at aIndexInContainer in aContainer. |
|
217 * @param aNewIndexInContainer the index in the container of the first |
|
218 * new child |
|
219 * |
|
220 * @note Callers of this method might not hold a strong reference to the |
|
221 * observer. The observer is responsible for making sure it stays |
|
222 * alive for the duration of the call as needed. The observer may |
|
223 * assume that this call will happen when there are script blockers on |
|
224 * the stack. |
|
225 */ |
|
226 virtual void ContentAppended(nsIDocument *aDocument, |
|
227 nsIContent* aContainer, |
|
228 nsIContent* aFirstNewContent, |
|
229 int32_t aNewIndexInContainer) = 0; |
|
230 |
|
231 /** |
|
232 * Notification that a content node has been inserted as child to another |
|
233 * node in the tree. |
|
234 * |
|
235 * @param aDocument The owner-document of aContent, or, when aContainer |
|
236 * is null, the container that had the child inserted. |
|
237 * Can be null. |
|
238 * @param aContainer The container that had new a child inserted. Can be |
|
239 * null to indicate that the child was inserted into |
|
240 * aDocument |
|
241 * @param aChild The newly inserted child. |
|
242 * @param aIndexInContainer The index in the container of the new child. |
|
243 * |
|
244 * @note Callers of this method might not hold a strong reference to the |
|
245 * observer. The observer is responsible for making sure it stays |
|
246 * alive for the duration of the call as needed. The observer may |
|
247 * assume that this call will happen when there are script blockers on |
|
248 * the stack. |
|
249 */ |
|
250 virtual void ContentInserted(nsIDocument *aDocument, |
|
251 nsIContent* aContainer, |
|
252 nsIContent* aChild, |
|
253 int32_t aIndexInContainer) = 0; |
|
254 |
|
255 /** |
|
256 * Notification that a content node has been removed from the child list of |
|
257 * another node in the tree. |
|
258 * |
|
259 * @param aDocument The owner-document of aContent, or, when aContainer |
|
260 * is null, the container that had the child removed. |
|
261 * Can be null. |
|
262 * @param aContainer The container that had new a child removed. Can be |
|
263 * null to indicate that the child was removed from |
|
264 * aDocument. |
|
265 * @param aChild The child that was removed. |
|
266 * @param aIndexInContainer The index in the container which the child used |
|
267 * to have. |
|
268 * @param aPreviousSibling The previous sibling to the child that was removed. |
|
269 * Can be null if there was no previous sibling. |
|
270 * |
|
271 * @note Callers of this method might not hold a strong reference to the |
|
272 * observer. The observer is responsible for making sure it stays |
|
273 * alive for the duration of the call as needed. The observer may |
|
274 * assume that this call will happen when there are script blockers on |
|
275 * the stack. |
|
276 */ |
|
277 virtual void ContentRemoved(nsIDocument *aDocument, |
|
278 nsIContent* aContainer, |
|
279 nsIContent* aChild, |
|
280 int32_t aIndexInContainer, |
|
281 nsIContent* aPreviousSibling) = 0; |
|
282 |
|
283 /** |
|
284 * The node is in the process of being destroyed. Calling QI on the node is |
|
285 * not supported, however it is possible to get children and flags through |
|
286 * nsINode as well as calling IsNodeOfType(eCONTENT) and casting to |
|
287 * nsIContent to get attributes. |
|
288 * |
|
289 * NOTE: This notification is only called on observers registered directly |
|
290 * on the node. This is because when the node is destroyed it can not have |
|
291 * any ancestors. If you want to know when a descendant node is being |
|
292 * removed from the observed node, use the ContentRemoved notification. |
|
293 * |
|
294 * @param aNode The node being destroyed. |
|
295 * |
|
296 * @note Callers of this method might not hold a strong reference to |
|
297 * the observer. The observer is responsible for making sure it |
|
298 * stays alive for the duration of the call as needed. |
|
299 */ |
|
300 virtual void NodeWillBeDestroyed(const nsINode *aNode) = 0; |
|
301 |
|
302 /** |
|
303 * Notification that the node's parent chain has changed. This |
|
304 * happens when either the node or one of its ancestors is inserted |
|
305 * or removed as a child of another node. |
|
306 * |
|
307 * Note that when a node is inserted this notification is sent to |
|
308 * all descendants of that node, since all such nodes have their |
|
309 * parent chain changed. |
|
310 * |
|
311 * @param aContent The piece of content that had its parent changed. |
|
312 * |
|
313 * @note Callers of this method might not hold a strong reference to |
|
314 * the observer. The observer is responsible for making sure it |
|
315 * stays alive for the duration of the call as needed. |
|
316 */ |
|
317 |
|
318 virtual void ParentChainChanged(nsIContent *aContent) = 0; |
|
319 }; |
|
320 |
|
321 NS_DEFINE_STATIC_IID_ACCESSOR(nsIMutationObserver, NS_IMUTATION_OBSERVER_IID) |
|
322 |
|
323 #define NS_DECL_NSIMUTATIONOBSERVER_CHARACTERDATAWILLCHANGE \ |
|
324 virtual void CharacterDataWillChange(nsIDocument* aDocument, \ |
|
325 nsIContent* aContent, \ |
|
326 CharacterDataChangeInfo* aInfo); |
|
327 |
|
328 #define NS_DECL_NSIMUTATIONOBSERVER_CHARACTERDATACHANGED \ |
|
329 virtual void CharacterDataChanged(nsIDocument* aDocument, \ |
|
330 nsIContent* aContent, \ |
|
331 CharacterDataChangeInfo* aInfo); |
|
332 |
|
333 #define NS_DECL_NSIMUTATIONOBSERVER_ATTRIBUTEWILLCHANGE \ |
|
334 virtual void AttributeWillChange(nsIDocument* aDocument, \ |
|
335 mozilla::dom::Element* aElement, \ |
|
336 int32_t aNameSpaceID, \ |
|
337 nsIAtom* aAttribute, \ |
|
338 int32_t aModType); |
|
339 |
|
340 #define NS_DECL_NSIMUTATIONOBSERVER_ATTRIBUTECHANGED \ |
|
341 virtual void AttributeChanged(nsIDocument* aDocument, \ |
|
342 mozilla::dom::Element* aElement, \ |
|
343 int32_t aNameSpaceID, \ |
|
344 nsIAtom* aAttribute, \ |
|
345 int32_t aModType); |
|
346 |
|
347 #define NS_DECL_NSIMUTATIONOBSERVER_CONTENTAPPENDED \ |
|
348 virtual void ContentAppended(nsIDocument* aDocument, \ |
|
349 nsIContent* aContainer, \ |
|
350 nsIContent* aFirstNewContent, \ |
|
351 int32_t aNewIndexInContainer); |
|
352 |
|
353 #define NS_DECL_NSIMUTATIONOBSERVER_CONTENTINSERTED \ |
|
354 virtual void ContentInserted(nsIDocument* aDocument, \ |
|
355 nsIContent* aContainer, \ |
|
356 nsIContent* aChild, \ |
|
357 int32_t aIndexInContainer); |
|
358 |
|
359 #define NS_DECL_NSIMUTATIONOBSERVER_CONTENTREMOVED \ |
|
360 virtual void ContentRemoved(nsIDocument* aDocument, \ |
|
361 nsIContent* aContainer, \ |
|
362 nsIContent* aChild, \ |
|
363 int32_t aIndexInContainer, \ |
|
364 nsIContent* aPreviousSibling); |
|
365 |
|
366 #define NS_DECL_NSIMUTATIONOBSERVER_NODEWILLBEDESTROYED \ |
|
367 virtual void NodeWillBeDestroyed(const nsINode* aNode); |
|
368 |
|
369 #define NS_DECL_NSIMUTATIONOBSERVER_PARENTCHAINCHANGED \ |
|
370 virtual void ParentChainChanged(nsIContent *aContent); |
|
371 |
|
372 #define NS_DECL_NSIMUTATIONOBSERVER \ |
|
373 NS_DECL_NSIMUTATIONOBSERVER_CHARACTERDATAWILLCHANGE \ |
|
374 NS_DECL_NSIMUTATIONOBSERVER_CHARACTERDATACHANGED \ |
|
375 NS_DECL_NSIMUTATIONOBSERVER_ATTRIBUTEWILLCHANGE \ |
|
376 NS_DECL_NSIMUTATIONOBSERVER_ATTRIBUTECHANGED \ |
|
377 NS_DECL_NSIMUTATIONOBSERVER_CONTENTAPPENDED \ |
|
378 NS_DECL_NSIMUTATIONOBSERVER_CONTENTINSERTED \ |
|
379 NS_DECL_NSIMUTATIONOBSERVER_CONTENTREMOVED \ |
|
380 NS_DECL_NSIMUTATIONOBSERVER_NODEWILLBEDESTROYED \ |
|
381 NS_DECL_NSIMUTATIONOBSERVER_PARENTCHAINCHANGED |
|
382 |
|
383 #define NS_IMPL_NSIMUTATIONOBSERVER_CORE_STUB(_class) \ |
|
384 void \ |
|
385 _class::NodeWillBeDestroyed(const nsINode* aNode) \ |
|
386 { \ |
|
387 } |
|
388 |
|
389 #define NS_IMPL_NSIMUTATIONOBSERVER_CONTENT(_class) \ |
|
390 void \ |
|
391 _class::CharacterDataWillChange(nsIDocument* aDocument, \ |
|
392 nsIContent* aContent, \ |
|
393 CharacterDataChangeInfo* aInfo) \ |
|
394 { \ |
|
395 } \ |
|
396 void \ |
|
397 _class::CharacterDataChanged(nsIDocument* aDocument, \ |
|
398 nsIContent* aContent, \ |
|
399 CharacterDataChangeInfo* aInfo) \ |
|
400 { \ |
|
401 } \ |
|
402 void \ |
|
403 _class::AttributeWillChange(nsIDocument* aDocument, \ |
|
404 mozilla::dom::Element* aElement, \ |
|
405 int32_t aNameSpaceID, \ |
|
406 nsIAtom* aAttribute, \ |
|
407 int32_t aModType) \ |
|
408 { \ |
|
409 } \ |
|
410 void \ |
|
411 _class::AttributeChanged(nsIDocument* aDocument, \ |
|
412 mozilla::dom::Element* aElement, \ |
|
413 int32_t aNameSpaceID, \ |
|
414 nsIAtom* aAttribute, \ |
|
415 int32_t aModType) \ |
|
416 { \ |
|
417 } \ |
|
418 void \ |
|
419 _class::ContentAppended(nsIDocument* aDocument, \ |
|
420 nsIContent* aContainer, \ |
|
421 nsIContent* aFirstNewContent, \ |
|
422 int32_t aNewIndexInContainer) \ |
|
423 { \ |
|
424 } \ |
|
425 void \ |
|
426 _class::ContentInserted(nsIDocument* aDocument, \ |
|
427 nsIContent* aContainer, \ |
|
428 nsIContent* aChild, \ |
|
429 int32_t aIndexInContainer) \ |
|
430 { \ |
|
431 } \ |
|
432 void \ |
|
433 _class::ContentRemoved(nsIDocument* aDocument, \ |
|
434 nsIContent* aContainer, \ |
|
435 nsIContent* aChild, \ |
|
436 int32_t aIndexInContainer, \ |
|
437 nsIContent* aPreviousSibling) \ |
|
438 { \ |
|
439 } \ |
|
440 void \ |
|
441 _class::ParentChainChanged(nsIContent *aContent) \ |
|
442 { \ |
|
443 } |
|
444 |
|
445 |
|
446 #endif /* nsIMutationObserver_h */ |