xref: /aoo41x/main/sw/source/core/crsr/trvlreg.cxx (revision cdf0e10c)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_sw.hxx"
30 
31 
32 #include <crsrsh.hxx>
33 #include <doc.hxx>
34 #include <swcrsr.hxx>
35 #include <docary.hxx>
36 #include <fmtcntnt.hxx>
37 #include <viscrs.hxx>
38 #include <callnk.hxx>
39 #include <pamtyp.hxx>
40 #include <section.hxx>
41 
42 
43 
44 sal_Bool GotoPrevRegion( SwPaM& rCurCrsr, SwPosRegion fnPosRegion,
45 						sal_Bool bInReadOnly )
46 {
47 	SwNodeIndex aIdx( rCurCrsr.GetPoint()->nNode );
48 	SwSectionNode* pNd = aIdx.GetNode().FindSectionNode();
49 	if( pNd )
50 		aIdx.Assign( *pNd, - 1 );
51 
52 	do {
53 		while( aIdx.GetIndex() &&
54             0 == ( pNd = aIdx.GetNode().StartOfSectionNode()->GetSectionNode()) )
55 			aIdx--;
56 
57 		if( pNd )		// gibt einen weiteren SectionNode ?
58 		{
59 			if( pNd->GetSection().IsHiddenFlag() ||
60 				( !bInReadOnly &&
61 				  pNd->GetSection().IsProtectFlag() ))
62 			{
63 				// geschuetzte/versteckte ueberspringen wir
64 				aIdx.Assign( *pNd, - 1 );
65 			}
66 			else if( fnPosRegion == fnMoveForward )
67 			{
68 				aIdx = *pNd;
69 				SwCntntNode* pCNd = pNd->GetNodes().GoNextSection( &aIdx,
70 												sal_True, !bInReadOnly );
71 				if( !pCNd )
72 				{
73 					aIdx--;
74 					continue;
75 				}
76 				rCurCrsr.GetPoint()->nContent.Assign( pCNd, 0 );
77 			}
78 			else
79 			{
80 				aIdx = *pNd->EndOfSectionNode();
81 				SwCntntNode* pCNd = pNd->GetNodes().GoPrevSection( &aIdx,
82 												sal_True, !bInReadOnly );
83 				if( !pCNd )
84 				{
85 					aIdx.Assign( *pNd, - 1 );
86 					continue;
87 				}
88 				rCurCrsr.GetPoint()->nContent.Assign( pCNd, pCNd->Len() );
89 			}
90 
91 			rCurCrsr.GetPoint()->nNode = aIdx;
92 			return sal_True;
93 		}
94 	} while( pNd );
95 	return sal_False;
96 }
97 
98 
99 sal_Bool GotoNextRegion( SwPaM& rCurCrsr, SwPosRegion fnPosRegion,
100 						sal_Bool bInReadOnly )
101 {
102 	SwNodeIndex aIdx( rCurCrsr.GetPoint()->nNode );
103 	SwSectionNode* pNd = aIdx.GetNode().FindSectionNode();
104 	if( pNd )
105 		aIdx.Assign( *pNd->EndOfSectionNode(), - 1 );
106 
107 	sal_uLong nEndCount = aIdx.GetNode().GetNodes().Count()-1;
108 	do {
109 		while( aIdx.GetIndex() < nEndCount &&
110 				0 == ( pNd = aIdx.GetNode().GetSectionNode()) )
111 			aIdx++;
112 
113 		if( pNd )		// gibt einen weiteren SectionNode ?
114 		{
115 			if( pNd->GetSection().IsHiddenFlag() ||
116 				( !bInReadOnly &&
117 				  pNd->GetSection().IsProtectFlag() ))
118 			{
119 				// geschuetzte/versteckte ueberspringen wir
120 				aIdx.Assign( *pNd->EndOfSectionNode(), +1 );
121 			}
122 			else if( fnPosRegion == fnMoveForward )
123 			{
124 				aIdx = *pNd;
125 				SwCntntNode* pCNd = pNd->GetNodes().GoNextSection( &aIdx,
126 												sal_True, !bInReadOnly );
127 				if( !pCNd )
128 				{
129 					aIdx.Assign( *pNd->EndOfSectionNode(), +1 );
130 					continue;
131 				}
132 				rCurCrsr.GetPoint()->nContent.Assign( pCNd, 0 );
133 			}
134 			else
135 			{
136 				aIdx = *pNd->EndOfSectionNode();
137 				SwCntntNode* pCNd = pNd->GetNodes().GoPrevSection( &aIdx,
138 												sal_True, !bInReadOnly );
139 				if( !pCNd )
140 				{
141 					aIdx++;
142 					continue;
143 				}
144 				rCurCrsr.GetPoint()->nContent.Assign( pCNd, pCNd->Len() );
145 			}
146 
147 			rCurCrsr.GetPoint()->nNode = aIdx;
148 			return sal_True;
149 		}
150 	} while( pNd );
151 	return sal_False;
152 }
153 
154 
155 sal_Bool GotoCurrRegion( SwPaM& rCurCrsr, SwPosRegion fnPosRegion,
156 						sal_Bool bInReadOnly )
157 {
158 	SwSectionNode* pNd = rCurCrsr.GetNode()->FindSectionNode();
159 	if( !pNd )
160 		return sal_False;
161 
162 	SwPosition* pPos = rCurCrsr.GetPoint();
163 	sal_Bool bMoveBackward = fnPosRegion == fnMoveBackward;
164 
165 	SwCntntNode* pCNd;
166 	if( bMoveBackward )
167 	{
168 		SwNodeIndex aIdx( *pNd->EndOfSectionNode() );
169 		pCNd = pNd->GetNodes().GoPrevSection( &aIdx, sal_True, !bInReadOnly );
170 	}
171 	else
172 	{
173 		SwNodeIndex aIdx( *pNd );
174 		pCNd = pNd->GetNodes().GoNextSection( &aIdx, sal_True, !bInReadOnly );
175 	}
176 
177 	if( pCNd )
178 	{
179 		pPos->nNode = *pCNd;
180 		xub_StrLen nTmpPos = bMoveBackward ? pCNd->Len() : 0;
181 		pPos->nContent.Assign( pCNd, nTmpPos );
182 	}
183 	return 0 != pCNd;
184 }
185 
186 
187 sal_Bool GotoCurrRegionAndSkip( SwPaM& rCurCrsr, SwPosRegion fnPosRegion,
188 								sal_Bool bInReadOnly )
189 {
190 	SwNode* pCurrNd = rCurCrsr.GetNode();
191 	SwSectionNode* pNd = pCurrNd->FindSectionNode();
192 	if( !pNd )
193 		return sal_False;
194 
195 	SwPosition* pPos = rCurCrsr.GetPoint();
196 	xub_StrLen nCurrCnt = pPos->nContent.GetIndex();
197 	sal_Bool bMoveBackward = fnPosRegion == fnMoveBackward;
198 
199 	do {
200 		SwCntntNode* pCNd;
201 		if( bMoveBackward )	// ans Ende vom Bereich
202 		{
203 			SwNodeIndex aIdx( *pNd->EndOfSectionNode() );
204 			pCNd = pNd->GetNodes().GoPrevSection( &aIdx, sal_True, !bInReadOnly );
205 			if( !pCNd )
206 				return sal_False;
207 			pPos->nNode = aIdx;
208 		}
209 		else
210 		{
211 			SwNodeIndex aIdx( *pNd );
212 			pCNd = pNd->GetNodes().GoNextSection( &aIdx, sal_True, !bInReadOnly );
213 			if( !pCNd )
214 				return sal_False;
215 			pPos->nNode = aIdx;
216 		}
217 
218 		xub_StrLen nTmpPos = bMoveBackward ? pCNd->Len() : 0;
219 		pPos->nContent.Assign( pCNd, nTmpPos );
220 
221 		if( &pPos->nNode.GetNode() != pCurrNd ||
222 			pPos->nContent.GetIndex() != nCurrCnt )
223 			// es gab eine Veraenderung
224 			return sal_True;
225 
226 		// dann versuche mal den "Parent" dieser Section
227 		SwSection* pParent = pNd->GetSection().GetParent();
228 		pNd = pParent ? pParent->GetFmt()->GetSectionNode() : 0;
229 	} while( pNd );
230 	return sal_False;
231 }
232 
233 
234 
235 sal_Bool SwCursor::MoveRegion( SwWhichRegion fnWhichRegion, SwPosRegion fnPosRegion )
236 {
237 	SwCrsrSaveState aSaveState( *this );
238     return !dynamic_cast<SwTableCursor*>(this) &&
239 			(*fnWhichRegion)( *this, fnPosRegion, IsReadOnlyAvailable()  ) &&
240 			!IsSelOvr() &&
241 			( GetPoint()->nNode.GetIndex() != pSavePos->nNode ||
242 				GetPoint()->nContent.GetIndex() != pSavePos->nCntnt );
243 }
244 
245 sal_Bool SwCrsrShell::MoveRegion( SwWhichRegion fnWhichRegion, SwPosRegion fnPosRegion )
246 {
247 	SwCallLink aLk( *this );		// Crsr-Moves ueberwachen, evt. Link callen
248 	sal_Bool bRet = !pTblCrsr && pCurCrsr->MoveRegion( fnWhichRegion, fnPosRegion );
249 	if( bRet )
250 		UpdateCrsr();
251 	return bRet;
252 }
253 
254 
255 sal_Bool SwCursor::GotoRegion( const String& rName )
256 {
257 	sal_Bool bRet = sal_False;
258 	const SwSectionFmts& rFmts = GetDoc()->GetSections();
259 	for( sal_uInt16 n = rFmts.Count(); n; )
260 	{
261 		const SwSectionFmt* pFmt = rFmts[ --n ];
262 		const SwNodeIndex* pIdx;
263 		const SwSection* pSect;
264 		if( 0 != ( pSect = pFmt->GetSection() ) &&
265             pSect->GetSectionName() == rName &&
266 			0 != ( pIdx = pFmt->GetCntnt().GetCntntIdx() ) &&
267 			pIdx->GetNode().GetNodes().IsDocNodes() )
268 		{
269 			// ein Bereich im normalen NodesArr
270 			SwCrsrSaveState aSaveState( *this );
271 
272 			GetPoint()->nNode = *pIdx;
273 			Move( fnMoveForward, fnGoCntnt );
274 			bRet = !IsSelOvr();
275 		}
276 	}
277 	return bRet;
278 }
279 
280 sal_Bool SwCrsrShell::GotoRegion( const String& rName )
281 {
282 	SwCallLink aLk( *this );		// Crsr-Moves ueberwachen,
283 	sal_Bool bRet = !pTblCrsr && pCurCrsr->GotoRegion( rName );
284 	if( bRet )
285 		UpdateCrsr( SwCrsrShell::SCROLLWIN | SwCrsrShell::CHKRANGE |
286 					SwCrsrShell::READONLY ); // und den akt. Updaten
287 	return bRet;
288 }
289 
290 
291 
292