1 : /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* ***** BEGIN LICENSE BLOCK *****
3 : * Version: MPL 1.1/GPL 2.0/LGPL 2.1
4 : *
5 : * The contents of this file are subject to the Mozilla Public License Version
6 : * 1.1 (the "License"); you may not use this file except in compliance with
7 : * the License. You may obtain a copy of the License at
8 : * http://www.mozilla.org/MPL/
9 : *
10 : * Software distributed under the License is distributed on an "AS IS" basis,
11 : * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
12 : * for the specific language governing rights and limitations under the
13 : * License.
14 : *
15 : * The Original Code is mozilla.org code.
16 : *
17 : * The Initial Developer of the Original Code is
18 : * Netscape Communications Corporation.
19 : * Portions created by the Initial Developer are Copyright (C) 1998
20 : * the Initial Developer. All Rights Reserved.
21 : *
22 : * Contributor(s):
23 : *
24 : * Alternatively, the contents of this file may be used under the terms of
25 : * either of the GNU General Public License Version 2 or later (the "GPL"),
26 : * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
27 : * in which case the provisions of the GPL or the LGPL are applicable instead
28 : * of those above. If you wish to allow use of your version of this file only
29 : * under the terms of either the GPL or the LGPL, and not to allow others to
30 : * use your version of this file under the terms of the MPL, indicate your
31 : * decision by deleting the provisions above and replace them with the notice
32 : * and other provisions required by the GPL or the LGPL. If you do not delete
33 : * the provisions above, a recipient may use your version of this file under
34 : * the terms of any one of the MPL, the GPL or the LGPL.
35 : *
36 : * ***** END LICENSE BLOCK ***** */
37 :
38 : #ifndef nsTextServicesDocument_h__
39 : #define nsTextServicesDocument_h__
40 :
41 : #include "nsCOMPtr.h"
42 : #include "nsIDOMDocument.h"
43 : #include "nsIDOMRange.h"
44 : #include "nsIContent.h"
45 : #include "nsIContentIterator.h"
46 : #include "nsIEditor.h"
47 : #include "nsIEditActionListener.h"
48 : #include "nsITextServicesDocument.h"
49 : #include "nsTArray.h"
50 : #include "nsISelectionController.h"
51 : #include "nsITextServicesFilter.h"
52 : #include "nsWeakReference.h"
53 : #include "nsCycleCollectionParticipant.h"
54 :
55 : class OffsetEntry;
56 :
57 : /** implementation of a text services object.
58 : *
59 : */
60 : class nsTextServicesDocument : public nsITextServicesDocument,
61 : public nsIEditActionListener
62 : {
63 : private:
64 : static nsIAtom *sAAtom;
65 : static nsIAtom *sAddressAtom;
66 : static nsIAtom *sBigAtom;
67 : static nsIAtom *sBlinkAtom;
68 : static nsIAtom *sBAtom;
69 : static nsIAtom *sCiteAtom;
70 : static nsIAtom *sCodeAtom;
71 : static nsIAtom *sDfnAtom;
72 : static nsIAtom *sEmAtom;
73 : static nsIAtom *sFontAtom;
74 : static nsIAtom *sIAtom;
75 : static nsIAtom *sKbdAtom;
76 : static nsIAtom *sKeygenAtom;
77 : static nsIAtom *sNobrAtom;
78 : static nsIAtom *sSAtom;
79 : static nsIAtom *sSampAtom;
80 : static nsIAtom *sSmallAtom;
81 : static nsIAtom *sSpacerAtom;
82 : static nsIAtom *sSpanAtom;
83 : static nsIAtom *sStrikeAtom;
84 : static nsIAtom *sStrongAtom;
85 : static nsIAtom *sSubAtom;
86 : static nsIAtom *sSupAtom;
87 : static nsIAtom *sTtAtom;
88 : static nsIAtom *sUAtom;
89 : static nsIAtom *sVarAtom;
90 : static nsIAtom *sWbrAtom;
91 :
92 : typedef enum { eIsDone=0, // No iterator (I), or iterator doesn't point to anything valid.
93 : eValid, // I points to first text node (TN) in current block (CB).
94 : ePrev, // No TN in CB, I points to first TN in prev block.
95 : eNext // No TN in CB, I points to first TN in next block.
96 : } TSDIteratorStatus;
97 :
98 : nsCOMPtr<nsIDOMDocument> mDOMDocument;
99 : nsCOMPtr<nsISelectionController>mSelCon;
100 : nsWeakPtr mEditor; // avoid a cycle with the spell checker and editor
101 : nsCOMPtr<nsIContentIterator> mIterator;
102 : TSDIteratorStatus mIteratorStatus;
103 : nsCOMPtr<nsIContent> mPrevTextBlock;
104 : nsCOMPtr<nsIContent> mNextTextBlock;
105 : nsTArray<OffsetEntry*> mOffsetTable;
106 :
107 : PRInt32 mSelStartIndex;
108 : PRInt32 mSelStartOffset;
109 : PRInt32 mSelEndIndex;
110 : PRInt32 mSelEndOffset;
111 :
112 : nsCOMPtr<nsIDOMRange> mExtent;
113 :
114 : nsCOMPtr<nsITextServicesFilter> mTxtSvcFilter;
115 :
116 : public:
117 :
118 : /** The default constructor.
119 : */
120 : nsTextServicesDocument();
121 :
122 : /** The default destructor.
123 : */
124 : virtual ~nsTextServicesDocument();
125 :
126 : /** To be called at module init
127 : */
128 : static void RegisterAtoms();
129 :
130 : /* Macro for AddRef(), Release(), and QueryInterface() */
131 0 : NS_DECL_CYCLE_COLLECTING_ISUPPORTS
132 1464 : NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsTextServicesDocument, nsITextServicesDocument)
133 :
134 : /* nsITextServicesDocument method implementations. */
135 : NS_IMETHOD InitWithEditor(nsIEditor *aEditor);
136 : NS_IMETHOD GetDocument(nsIDOMDocument **aDoc);
137 : NS_IMETHOD SetExtent(nsIDOMRange* aDOMRange);
138 : NS_IMETHOD ExpandRangeToWordBoundaries(nsIDOMRange *aRange);
139 : NS_IMETHOD SetFilter(nsITextServicesFilter *aFilter);
140 : NS_IMETHOD GetCurrentTextBlock(nsString *aStr);
141 : NS_IMETHOD FirstBlock();
142 : NS_IMETHOD LastSelectedBlock(TSDBlockSelectionStatus *aSelStatus, PRInt32 *aSelOffset, PRInt32 *aSelLength);
143 : NS_IMETHOD PrevBlock();
144 : NS_IMETHOD NextBlock();
145 : NS_IMETHOD IsDone(bool *aIsDone);
146 : NS_IMETHOD SetSelection(PRInt32 aOffset, PRInt32 aLength);
147 : NS_IMETHOD ScrollSelectionIntoView();
148 : NS_IMETHOD DeleteSelection();
149 : NS_IMETHOD InsertText(const nsString *aText);
150 :
151 : /* nsIEditActionListener method implementations. */
152 : NS_IMETHOD WillInsertNode(nsIDOMNode *aNode,
153 : nsIDOMNode *aParent,
154 : PRInt32 aPosition);
155 : NS_IMETHOD DidInsertNode(nsIDOMNode *aNode,
156 : nsIDOMNode *aParent,
157 : PRInt32 aPosition,
158 : nsresult aResult);
159 :
160 : NS_IMETHOD WillDeleteNode(nsIDOMNode *aChild);
161 : NS_IMETHOD DidDeleteNode(nsIDOMNode *aChild, nsresult aResult);
162 :
163 : NS_IMETHOD WillSplitNode(nsIDOMNode * aExistingRightNode,
164 : PRInt32 aOffset);
165 : NS_IMETHOD DidSplitNode(nsIDOMNode *aExistingRightNode,
166 : PRInt32 aOffset,
167 : nsIDOMNode *aNewLeftNode,
168 : nsresult aResult);
169 :
170 : NS_IMETHOD WillJoinNodes(nsIDOMNode *aLeftNode,
171 : nsIDOMNode *aRightNode,
172 : nsIDOMNode *aParent);
173 : NS_IMETHOD DidJoinNodes(nsIDOMNode *aLeftNode,
174 : nsIDOMNode *aRightNode,
175 : nsIDOMNode *aParent,
176 : nsresult aResult);
177 : // these listen methods are unused:
178 : NS_IMETHOD WillCreateNode(const nsAString& aTag, nsIDOMNode *aParent, PRInt32 aPosition);
179 : NS_IMETHOD DidCreateNode(const nsAString& aTag, nsIDOMNode *aNode, nsIDOMNode *aParent, PRInt32 aPosition, nsresult aResult);
180 : NS_IMETHOD WillInsertText(nsIDOMCharacterData *aTextNode, PRInt32 aOffset, const nsAString &aString);
181 : NS_IMETHOD DidInsertText(nsIDOMCharacterData *aTextNode, PRInt32 aOffset, const nsAString &aString, nsresult aResult);
182 : NS_IMETHOD WillDeleteText(nsIDOMCharacterData *aTextNode, PRInt32 aOffset, PRInt32 aLength);
183 : NS_IMETHOD DidDeleteText(nsIDOMCharacterData *aTextNode, PRInt32 aOffset, PRInt32 aLength, nsresult aResult);
184 : NS_IMETHOD WillDeleteSelection(nsISelection *aSelection);
185 : NS_IMETHOD DidDeleteSelection(nsISelection *aSelection);
186 :
187 : /* Helper functions */
188 : static nsresult GetRangeEndPoints(nsIDOMRange *aRange, nsIDOMNode **aParent1, PRInt32 *aOffset1, nsIDOMNode **aParent2, PRInt32 *aOffset2);
189 : static nsresult CreateRange(nsIDOMNode *aStartParent, PRInt32 aStartOffset, nsIDOMNode *aEndParent, PRInt32 aEndOffset, nsIDOMRange **aRange);
190 :
191 : private:
192 : /* nsTextServicesDocument private methods. */
193 :
194 : nsresult CreateContentIterator(nsIDOMRange *aRange, nsIContentIterator **aIterator);
195 :
196 : nsresult GetDocumentContentRootNode(nsIDOMNode **aNode);
197 : nsresult CreateDocumentContentRange(nsIDOMRange **aRange);
198 : nsresult CreateDocumentContentRootToNodeOffsetRange(nsIDOMNode *aParent, PRInt32 aOffset, bool aToStart, nsIDOMRange **aRange);
199 : nsresult CreateDocumentContentIterator(nsIContentIterator **aIterator);
200 :
201 : nsresult AdjustContentIterator();
202 :
203 : static nsresult FirstTextNode(nsIContentIterator *aIterator, TSDIteratorStatus *IteratorStatus);
204 : static nsresult LastTextNode(nsIContentIterator *aIterator, TSDIteratorStatus *IteratorStatus);
205 :
206 : static nsresult FirstTextNodeInCurrentBlock(nsIContentIterator *aIterator);
207 : static nsresult FirstTextNodeInPrevBlock(nsIContentIterator *aIterator);
208 : static nsresult FirstTextNodeInNextBlock(nsIContentIterator *aIterator);
209 :
210 : nsresult GetFirstTextNodeInPrevBlock(nsIContent **aContent);
211 : nsresult GetFirstTextNodeInNextBlock(nsIContent **aContent);
212 :
213 : static bool IsBlockNode(nsIContent *aContent);
214 : static bool IsTextNode(nsIContent *aContent);
215 : static bool IsTextNode(nsIDOMNode *aNode);
216 :
217 : static bool DidSkip(nsIContentIterator* aFilteredIter);
218 : static void ClearDidSkip(nsIContentIterator* aFilteredIter);
219 :
220 : static bool HasSameBlockNodeParent(nsIContent *aContent1, nsIContent *aContent2);
221 :
222 : nsresult SetSelectionInternal(PRInt32 aOffset, PRInt32 aLength, bool aDoUpdate);
223 : nsresult GetSelection(TSDBlockSelectionStatus *aSelStatus, PRInt32 *aSelOffset, PRInt32 *aSelLength);
224 : nsresult GetCollapsedSelection(TSDBlockSelectionStatus *aSelStatus, PRInt32 *aSelOffset, PRInt32 *aSelLength);
225 : nsresult GetUncollapsedSelection(TSDBlockSelectionStatus *aSelStatus, PRInt32 *aSelOffset, PRInt32 *aSelLength);
226 :
227 : bool SelectionIsCollapsed();
228 : bool SelectionIsValid();
229 :
230 : static nsresult CreateOffsetTable(nsTArray<OffsetEntry*> *aOffsetTable,
231 : nsIContentIterator *aIterator,
232 : TSDIteratorStatus *aIteratorStatus,
233 : nsIDOMRange *aIterRange,
234 : nsString *aStr);
235 : static nsresult ClearOffsetTable(nsTArray<OffsetEntry*> *aOffsetTable);
236 :
237 : static nsresult NodeHasOffsetEntry(nsTArray<OffsetEntry*> *aOffsetTable,
238 : nsIDOMNode *aNode,
239 : bool *aHasEntry,
240 : PRInt32 *aEntryIndex);
241 :
242 : nsresult RemoveInvalidOffsetEntries();
243 : nsresult SplitOffsetEntry(PRInt32 aTableIndex, PRInt32 aOffsetIntoEntry);
244 :
245 : static nsresult FindWordBounds(nsTArray<OffsetEntry*> *offsetTable,
246 : nsString *blockStr,
247 : nsIDOMNode *aNode, PRInt32 aNodeOffset,
248 : nsIDOMNode **aWordStartNode,
249 : PRInt32 *aWordStartOffset,
250 : nsIDOMNode **aWordEndNode,
251 : PRInt32 *aWordEndOffset);
252 :
253 : #ifdef DEBUG_kin
254 : void PrintOffsetTable();
255 : void PrintContentNode(nsIContent *aContent);
256 : #endif
257 : };
258 :
259 : #endif // nsTextServicesDocument_h__
|