xref: /aoo41x/main/sc/source/ui/view/tabview2.cxx (revision 0deba7fb)
1b3f79822SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3b3f79822SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4b3f79822SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5b3f79822SAndrew Rist  * distributed with this work for additional information
6b3f79822SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7b3f79822SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8b3f79822SAndrew Rist  * "License"); you may not use this file except in compliance
9b3f79822SAndrew Rist  * with the License.  You may obtain a copy of the License at
10b3f79822SAndrew Rist  *
11b3f79822SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12b3f79822SAndrew Rist  *
13b3f79822SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14b3f79822SAndrew Rist  * software distributed under the License is distributed on an
15b3f79822SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16b3f79822SAndrew Rist  * KIND, either express or implied.  See the License for the
17b3f79822SAndrew Rist  * specific language governing permissions and limitations
18b3f79822SAndrew Rist  * under the License.
19b3f79822SAndrew Rist  *
20b3f79822SAndrew Rist  *************************************************************/
21b3f79822SAndrew Rist 
22b3f79822SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_sc.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir 
28cdf0e10cSrcweir 
29cdf0e10cSrcweir // INCLUDE ---------------------------------------------------------------
30cdf0e10cSrcweir 
31cdf0e10cSrcweir #include "scitems.hxx"
32cdf0e10cSrcweir #include <editeng/eeitem.hxx>
33cdf0e10cSrcweir 
34cdf0e10cSrcweir 
35cdf0e10cSrcweir #include <vcl/timer.hxx>
36cdf0e10cSrcweir #include <vcl/msgbox.hxx>
37cdf0e10cSrcweir #include <sfx2/app.hxx>
38cdf0e10cSrcweir #include <sfx2/viewfrm.hxx>
39cdf0e10cSrcweir #include <sfx2/bindings.hxx>
40cdf0e10cSrcweir #include <sfx2/childwin.hxx>
41cdf0e10cSrcweir 
42cdf0e10cSrcweir #include "attrib.hxx"
43cdf0e10cSrcweir #include "pagedata.hxx"
44cdf0e10cSrcweir #include "tabview.hxx"
45cdf0e10cSrcweir #include "tabvwsh.hxx"
46cdf0e10cSrcweir #include "printfun.hxx"
47cdf0e10cSrcweir #include "stlpool.hxx"
48cdf0e10cSrcweir #include "docsh.hxx"
49cdf0e10cSrcweir #include "gridwin.hxx"
50cdf0e10cSrcweir #include "olinewin.hxx"
51cdf0e10cSrcweir #include "uiitems.hxx"
52cdf0e10cSrcweir #include "sc.hrc"
53cdf0e10cSrcweir #include "viewutil.hxx"
54cdf0e10cSrcweir #include "colrowba.hxx"
55cdf0e10cSrcweir #include "waitoff.hxx"
56cdf0e10cSrcweir #include "globstr.hrc"
57cdf0e10cSrcweir #include "scmod.hxx"
58cdf0e10cSrcweir 
59cdf0e10cSrcweir #define SC_BLOCKMODE_NONE		0
60cdf0e10cSrcweir #define SC_BLOCKMODE_NORMAL		1
61cdf0e10cSrcweir #define SC_BLOCKMODE_OWN		2
62cdf0e10cSrcweir 
63cdf0e10cSrcweir 
64cdf0e10cSrcweir 
65cdf0e10cSrcweir //
66cdf0e10cSrcweir //          Markier - Funktionen
67cdf0e10cSrcweir //
68cdf0e10cSrcweir 
69cdf0e10cSrcweir void ScTabView::PaintMarks(SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow )
70cdf0e10cSrcweir {
71cdf0e10cSrcweir 	if (!ValidCol(nStartCol)) nStartCol = MAXCOL;
72cdf0e10cSrcweir 	if (!ValidRow(nStartRow)) nStartRow = MAXROW;
73cdf0e10cSrcweir 	if (!ValidCol(nEndCol)) nEndCol = MAXCOL;
74cdf0e10cSrcweir 	if (!ValidRow(nEndRow)) nEndRow = MAXROW;
75cdf0e10cSrcweir 
76cdf0e10cSrcweir 	sal_Bool bLeft = (nStartCol==0 && nEndCol==MAXCOL);
77cdf0e10cSrcweir 	sal_Bool bTop = (nStartRow==0 && nEndRow==MAXROW);
78cdf0e10cSrcweir 
79cdf0e10cSrcweir 	if (bLeft)
80cdf0e10cSrcweir 		PaintLeftArea( nStartRow, nEndRow );
81cdf0e10cSrcweir 	if (bTop)
82cdf0e10cSrcweir 		PaintTopArea( nStartCol, nEndCol );
83cdf0e10cSrcweir 
84cdf0e10cSrcweir 	aViewData.GetDocument()->ExtendMerge( nStartCol, nStartRow, nEndCol, nEndRow,
85cdf0e10cSrcweir 											aViewData.GetTabNo() );
86cdf0e10cSrcweir 	PaintArea( nStartCol, nStartRow, nEndCol, nEndRow, SC_UPDATE_MARKS );
87cdf0e10cSrcweir }
88cdf0e10cSrcweir 
89cdf0e10cSrcweir sal_Bool ScTabView::IsMarking( SCCOL nCol, SCROW nRow, SCTAB nTab ) const
90cdf0e10cSrcweir {
91cdf0e10cSrcweir 	return bIsBlockMode
92cdf0e10cSrcweir 		&& nBlockStartX == nCol
93cdf0e10cSrcweir 		&& nBlockStartY == nRow
94cdf0e10cSrcweir 		&& nBlockStartZ == nTab;
95cdf0e10cSrcweir }
96cdf0e10cSrcweir 
97cdf0e10cSrcweir void ScTabView::InitOwnBlockMode()
98cdf0e10cSrcweir {
99cdf0e10cSrcweir 	if (!bIsBlockMode)
100cdf0e10cSrcweir 	{
101cdf0e10cSrcweir 		//	Wenn keine (alte) Markierung mehr da ist, Anker in SelectionEngine loeschen:
102cdf0e10cSrcweir 
103cdf0e10cSrcweir 		ScMarkData& rMark = aViewData.GetMarkData();
104cdf0e10cSrcweir 		if (!rMark.IsMarked() && !rMark.IsMultiMarked())
105cdf0e10cSrcweir 			GetSelEngine()->CursorPosChanging( sal_False, sal_False );
106cdf0e10cSrcweir 
107cdf0e10cSrcweir //		bIsBlockMode = sal_True;
108cdf0e10cSrcweir 		bIsBlockMode = SC_BLOCKMODE_OWN;			//! Variable umbenennen!
109cdf0e10cSrcweir 		nBlockStartX = 0;
110cdf0e10cSrcweir 		nBlockStartY = 0;
111cdf0e10cSrcweir 		nBlockStartZ = 0;
112cdf0e10cSrcweir 		nBlockEndX = 0;
113cdf0e10cSrcweir 		nBlockEndY = 0;
114cdf0e10cSrcweir 		nBlockEndZ = 0;
115cdf0e10cSrcweir 
116cdf0e10cSrcweir 		SelectionChanged();		// Status wird mit gesetzer Markierung abgefragt
117cdf0e10cSrcweir 	}
118cdf0e10cSrcweir }
119cdf0e10cSrcweir 
120cdf0e10cSrcweir void ScTabView::InitBlockMode( SCCOL nCurX, SCROW nCurY, SCTAB nCurZ,
121*0deba7fbSSteve Yin 								sal_Bool bTestNeg, sal_Bool bCols, sal_Bool bRows, sal_Bool bForceNeg )
122cdf0e10cSrcweir {
123cdf0e10cSrcweir 	if (!bIsBlockMode)
124cdf0e10cSrcweir 	{
125cdf0e10cSrcweir 		if (!ValidCol(nCurX)) nCurX = MAXCOL;
126cdf0e10cSrcweir 		if (!ValidRow(nCurY)) nCurY = MAXROW;
127cdf0e10cSrcweir 
128cdf0e10cSrcweir 		ScMarkData& rMark = aViewData.GetMarkData();
129cdf0e10cSrcweir 		SCTAB nTab = aViewData.GetTabNo();
130cdf0e10cSrcweir 
131cdf0e10cSrcweir 		//	Teil von Markierung aufheben?
132*0deba7fbSSteve Yin //IAccessibility2 Implementation 2009-----
133*0deba7fbSSteve Yin 		if (bForceNeg)
134*0deba7fbSSteve Yin 			bBlockNeg = sal_True;
135*0deba7fbSSteve Yin //-----IAccessibility2 Implementation 2009
136*0deba7fbSSteve Yin 		else if (bTestNeg)
137cdf0e10cSrcweir 		{
138cdf0e10cSrcweir 			if ( bCols )
139cdf0e10cSrcweir 				bBlockNeg = rMark.IsColumnMarked( nCurX );
140cdf0e10cSrcweir 			else if ( bRows )
141cdf0e10cSrcweir 				bBlockNeg = rMark.IsRowMarked( nCurY );
142cdf0e10cSrcweir 			else
143cdf0e10cSrcweir 				bBlockNeg = rMark.IsCellMarked( nCurX, nCurY );
144cdf0e10cSrcweir 		}
145cdf0e10cSrcweir 		else
146cdf0e10cSrcweir 			bBlockNeg = sal_False;
147cdf0e10cSrcweir 		rMark.SetMarkNegative(bBlockNeg);
148cdf0e10cSrcweir 
149cdf0e10cSrcweir //		bIsBlockMode = sal_True;
150cdf0e10cSrcweir 		bIsBlockMode = SC_BLOCKMODE_NORMAL;			//! Variable umbenennen!
151cdf0e10cSrcweir 		bBlockCols = bCols;
152cdf0e10cSrcweir 		bBlockRows = bRows;
153cdf0e10cSrcweir 		nBlockStartX = nBlockStartXOrig = nCurX;
154cdf0e10cSrcweir 		nBlockStartY = nBlockStartYOrig = nCurY;
155cdf0e10cSrcweir 		nBlockStartZ = nCurZ;
156cdf0e10cSrcweir 		nBlockEndX = nOldCurX = nBlockStartX;
157cdf0e10cSrcweir 		nBlockEndY = nOldCurY = nBlockStartY;
158cdf0e10cSrcweir 		nBlockEndZ = nBlockStartZ;
159cdf0e10cSrcweir 
160cdf0e10cSrcweir 		if (bBlockCols)
161cdf0e10cSrcweir 		{
162cdf0e10cSrcweir 			nBlockStartY = nBlockStartYOrig = 0;
163cdf0e10cSrcweir 			nBlockEndY = MAXROW;
164cdf0e10cSrcweir 		}
165cdf0e10cSrcweir 
166cdf0e10cSrcweir 		if (bBlockRows)
167cdf0e10cSrcweir 		{
168cdf0e10cSrcweir 			nBlockStartX = nBlockStartXOrig = 0;
169cdf0e10cSrcweir 			nBlockEndX = MAXCOL;
170cdf0e10cSrcweir 		}
171cdf0e10cSrcweir 
172cdf0e10cSrcweir 		rMark.SetMarkArea( ScRange( nBlockStartX,nBlockStartY, nTab, nBlockEndX,nBlockEndY, nTab ) );
173cdf0e10cSrcweir 
174cdf0e10cSrcweir #ifdef OLD_SELECTION_PAINT
175cdf0e10cSrcweir 		InvertBlockMark( nBlockStartX,nBlockStartY,nBlockEndX,nBlockEndY );
176cdf0e10cSrcweir #endif
177cdf0e10cSrcweir 		UpdateSelectionOverlay();
178cdf0e10cSrcweir 
179cdf0e10cSrcweir 		bNewStartIfMarking = sal_False;		// use only once
180cdf0e10cSrcweir 	}
181cdf0e10cSrcweir }
182cdf0e10cSrcweir 
183cdf0e10cSrcweir void ScTabView::SetNewStartIfMarking()
184cdf0e10cSrcweir {
185cdf0e10cSrcweir 	bNewStartIfMarking = sal_True;
186cdf0e10cSrcweir }
187cdf0e10cSrcweir 
188cdf0e10cSrcweir void ScTabView::DoneBlockMode( sal_Bool bContinue )            // Default FALSE
189cdf0e10cSrcweir {
190cdf0e10cSrcweir 	//	Wenn zwischen Tabellen- und Header SelectionEngine gewechselt wird,
191cdf0e10cSrcweir 	//	wird evtl. DeselectAll gerufen, weil die andere Engine keinen Anker hat.
192cdf0e10cSrcweir 	//	Mit bMoveIsShift wird verhindert, dass dann die Selektion aufgehoben wird.
193cdf0e10cSrcweir 
194cdf0e10cSrcweir 	if (bIsBlockMode && !bMoveIsShift)
195cdf0e10cSrcweir 	{
196cdf0e10cSrcweir 		ScMarkData& rMark = aViewData.GetMarkData();
197cdf0e10cSrcweir 		sal_Bool bFlag = rMark.GetMarkingFlag();
198cdf0e10cSrcweir 		rMark.SetMarking(sal_False);
199cdf0e10cSrcweir 
200cdf0e10cSrcweir 		if (bBlockNeg && !bContinue)
201cdf0e10cSrcweir 			rMark.MarkToMulti();
202cdf0e10cSrcweir 
203cdf0e10cSrcweir 		if (bContinue)
204cdf0e10cSrcweir 			rMark.MarkToMulti();
205cdf0e10cSrcweir 		else
206cdf0e10cSrcweir 		{
207cdf0e10cSrcweir 			//	Die Tabelle kann an dieser Stelle ungueltig sein, weil DoneBlockMode
208cdf0e10cSrcweir 			//	aus SetTabNo aufgerufen wird
209cdf0e10cSrcweir 			//	(z.B. wenn die aktuelle Tabelle von einer anderen View aus geloescht wird)
210cdf0e10cSrcweir 
211cdf0e10cSrcweir 			SCTAB nTab = aViewData.GetTabNo();
212cdf0e10cSrcweir 			ScDocument* pDoc = aViewData.GetDocument();
213cdf0e10cSrcweir 			if ( pDoc->HasTable(nTab) )
214cdf0e10cSrcweir 				PaintBlock( sal_True );								// sal_True -> Block loeschen
215cdf0e10cSrcweir 			else
216cdf0e10cSrcweir 				rMark.ResetMark();
217cdf0e10cSrcweir 		}
218cdf0e10cSrcweir //		bIsBlockMode = sal_False;
219cdf0e10cSrcweir 		bIsBlockMode = SC_BLOCKMODE_NONE;			//! Variable umbenennen!
220cdf0e10cSrcweir 
221cdf0e10cSrcweir 		rMark.SetMarking(bFlag);
222cdf0e10cSrcweir 		rMark.SetMarkNegative(sal_False);
223cdf0e10cSrcweir 	}
224cdf0e10cSrcweir }
225cdf0e10cSrcweir 
226cdf0e10cSrcweir void ScTabView::MarkCursor( SCCOL nCurX, SCROW nCurY, SCTAB nCurZ,
227cdf0e10cSrcweir                             sal_Bool bCols, sal_Bool bRows, sal_Bool bCellSelection )
228cdf0e10cSrcweir {
229cdf0e10cSrcweir 	if (!ValidCol(nCurX)) nCurX = MAXCOL;
230cdf0e10cSrcweir 	if (!ValidRow(nCurY)) nCurY = MAXROW;
231cdf0e10cSrcweir 
232cdf0e10cSrcweir 	if (!bIsBlockMode)
233cdf0e10cSrcweir 	{
234cdf0e10cSrcweir 		DBG_ERROR( "MarkCursor nicht im BlockMode" );
235cdf0e10cSrcweir 		InitBlockMode( nCurX, nCurY, nCurZ, sal_False, bCols, bRows );
236cdf0e10cSrcweir 	}
237cdf0e10cSrcweir 
238cdf0e10cSrcweir 	if (bCols)
239cdf0e10cSrcweir 		nCurY = MAXROW;
240cdf0e10cSrcweir 	if (bRows)
241cdf0e10cSrcweir 		nCurX = MAXCOL;
242cdf0e10cSrcweir 
243cdf0e10cSrcweir 	ScMarkData& rMark = aViewData.GetMarkData();
244cdf0e10cSrcweir 	DBG_ASSERT(rMark.IsMarked() || rMark.IsMultiMarked(), "MarkCursor, !IsMarked()");
245cdf0e10cSrcweir 	ScRange aMarkRange;
246cdf0e10cSrcweir 	rMark.GetMarkArea(aMarkRange);
247cdf0e10cSrcweir 	if (( aMarkRange.aStart.Col() != nBlockStartX && aMarkRange.aEnd.Col() != nBlockStartX ) ||
248cdf0e10cSrcweir 		( aMarkRange.aStart.Row() != nBlockStartY && aMarkRange.aEnd.Row() != nBlockStartY ) ||
249cdf0e10cSrcweir 		( bIsBlockMode == SC_BLOCKMODE_OWN ))
250cdf0e10cSrcweir 	{
251cdf0e10cSrcweir 		//	Markierung ist veraendert worden
252cdf0e10cSrcweir 		//	(z.B. MarkToSimple, wenn per negativ alles bis auf ein Rechteck geloescht wurde)
253cdf0e10cSrcweir 		//	oder nach InitOwnBlockMode wird mit Shift-Klick weitermarkiert...
254cdf0e10cSrcweir 
255cdf0e10cSrcweir 		sal_Bool bOldShift = bMoveIsShift;
256cdf0e10cSrcweir 		bMoveIsShift = sal_False;				//	wirklich umsetzen
257cdf0e10cSrcweir 		DoneBlockMode(sal_False);				//!	direkt Variablen setzen? (-> kein Geflacker)
258cdf0e10cSrcweir 		bMoveIsShift = bOldShift;
259cdf0e10cSrcweir 
260cdf0e10cSrcweir 		InitBlockMode( aMarkRange.aStart.Col(), aMarkRange.aStart.Row(),
261cdf0e10cSrcweir 						nBlockStartZ, rMark.IsMarkNegative(), bCols, bRows );
262cdf0e10cSrcweir 	}
263cdf0e10cSrcweir 
264cdf0e10cSrcweir 	SCCOL nOldBlockEndX = nBlockEndX;
265cdf0e10cSrcweir 	SCROW nOldBlockEndY = nBlockEndY;
266cdf0e10cSrcweir 
267cdf0e10cSrcweir 	if ( nCurX != nOldCurX || nCurY != nOldCurY )
268cdf0e10cSrcweir 	{
269cdf0e10cSrcweir         // Current cursor has moved
270cdf0e10cSrcweir 
271cdf0e10cSrcweir 		SCTAB		nTab = nCurZ;
272cdf0e10cSrcweir 
273cdf0e10cSrcweir #ifdef OLD_SELECTION_PAINT
274cdf0e10cSrcweir 		SCCOL		nDrawStartCol;
275cdf0e10cSrcweir 		SCROW		nDrawStartRow;
276cdf0e10cSrcweir 		SCCOL		nDrawEndCol;
277cdf0e10cSrcweir 		SCROW		nDrawEndRow;
278cdf0e10cSrcweir #endif
279cdf0e10cSrcweir 
280cdf0e10cSrcweir         // Set old selection area
281cdf0e10cSrcweir 		ScUpdateRect aRect( nBlockStartX, nBlockStartY, nOldBlockEndX, nOldBlockEndY );
282cdf0e10cSrcweir 
283cdf0e10cSrcweir         if ( bCellSelection )
284cdf0e10cSrcweir         {
285cdf0e10cSrcweir             // Expand selection area accordingly when the current selection ends
286cdf0e10cSrcweir             // with a merged cell.
287cdf0e10cSrcweir             SCsCOL nCurXOffset = 0;
288cdf0e10cSrcweir             SCsCOL nBlockStartXOffset = 0;
289cdf0e10cSrcweir             SCsROW nCurYOffset = 0;
290cdf0e10cSrcweir             SCsROW nBlockStartYOffset = 0;
291cdf0e10cSrcweir             sal_Bool bBlockStartMerged = sal_False;
292cdf0e10cSrcweir             const ScMergeAttr* pMergeAttr = NULL;
293cdf0e10cSrcweir             ScDocument* pDocument = aViewData.GetDocument();
294cdf0e10cSrcweir 
295cdf0e10cSrcweir             // The following block checks whether or not the "BlockStart" (anchor)
296cdf0e10cSrcweir             // cell is merged.  If it's merged, it'll then move the position of the
297cdf0e10cSrcweir             // anchor cell to the corner that's diagonally opposite of the
298cdf0e10cSrcweir             // direction of a current selection area.  For instance, if a current
299cdf0e10cSrcweir             // selection is moving in the upperleft direction, the anchor cell will
300cdf0e10cSrcweir             // move to the lower-right corner of the merged anchor cell, and so on.
301cdf0e10cSrcweir 
302cdf0e10cSrcweir             pMergeAttr = static_cast<const ScMergeAttr*>(
303cdf0e10cSrcweir                 pDocument->GetAttr( nBlockStartXOrig, nBlockStartYOrig, nTab, ATTR_MERGE ) );
304cdf0e10cSrcweir             if ( pMergeAttr->IsMerged() )
305cdf0e10cSrcweir             {
306cdf0e10cSrcweir                 SCsCOL nColSpan = pMergeAttr->GetColMerge();
307cdf0e10cSrcweir                 SCsROW nRowSpan = pMergeAttr->GetRowMerge();
308cdf0e10cSrcweir 
309cdf0e10cSrcweir                 if ( !( nCurX >= nBlockStartXOrig + nColSpan - 1 && nCurY >= nBlockStartYOrig + nRowSpan - 1 ) )
310cdf0e10cSrcweir                 {
311cdf0e10cSrcweir                     nBlockStartX = nCurX >= nBlockStartXOrig ? nBlockStartXOrig : nBlockStartXOrig + nColSpan - 1;
312cdf0e10cSrcweir                     nBlockStartY = nCurY >= nBlockStartYOrig ? nBlockStartYOrig : nBlockStartYOrig + nRowSpan - 1;
313cdf0e10cSrcweir                     nCurXOffset  = nCurX >= nBlockStartXOrig && nCurX < nBlockStartXOrig + nColSpan - 1 ?
314cdf0e10cSrcweir                         nBlockStartXOrig - nCurX + nColSpan - 1 : 0;
315cdf0e10cSrcweir                     nCurYOffset  = nCurY >= nBlockStartYOrig && nCurY < nBlockStartYOrig + nRowSpan - 1 ?
316cdf0e10cSrcweir                         nBlockStartYOrig - nCurY + nRowSpan - 1 : 0;
317cdf0e10cSrcweir                     bBlockStartMerged = sal_True;
318cdf0e10cSrcweir                 }
319cdf0e10cSrcweir             }
320cdf0e10cSrcweir 
321cdf0e10cSrcweir             // The following block checks whether or not the current cell is
322cdf0e10cSrcweir             // merged.  If it is, it'll then set the appropriate X & Y offset
323cdf0e10cSrcweir             // values (nCurXOffset & nCurYOffset) such that the selection area will
324cdf0e10cSrcweir             // grow by those specified offset amounts.  Note that the values of
325cdf0e10cSrcweir             // nCurXOffset/nCurYOffset may also be specified in the previous code
326cdf0e10cSrcweir             // block, in which case whichever value is greater will take on.
327cdf0e10cSrcweir 
328cdf0e10cSrcweir             pMergeAttr = static_cast<const ScMergeAttr*>(
329cdf0e10cSrcweir                 pDocument->GetAttr( nCurX, nCurY, nTab, ATTR_MERGE ) );
330cdf0e10cSrcweir             if ( pMergeAttr->IsMerged() )
331cdf0e10cSrcweir             {
332cdf0e10cSrcweir                 SCsCOL nColSpan = pMergeAttr->GetColMerge();
333cdf0e10cSrcweir                 SCsROW nRowSpan = pMergeAttr->GetRowMerge();
334cdf0e10cSrcweir 
335cdf0e10cSrcweir                 if ( !( nBlockStartX >= nCurX + nColSpan - 1 && nBlockStartY >= nCurY + nRowSpan - 1 ) )
336cdf0e10cSrcweir                 {
337cdf0e10cSrcweir                     if ( nBlockStartX <= nCurX + nColSpan - 1 )
338cdf0e10cSrcweir                     {
339cdf0e10cSrcweir                         SCsCOL nCurXOffsetTemp = nCurX < nCurX + nColSpan - 1 ? nColSpan - 1 : 0;
340cdf0e10cSrcweir                         nCurXOffset = nCurXOffset > nCurXOffsetTemp ? nCurXOffset : nCurXOffsetTemp;
341cdf0e10cSrcweir                     }
342cdf0e10cSrcweir                     if ( nBlockStartY <= nCurY + nRowSpan - 1 )
343cdf0e10cSrcweir                     {
344cdf0e10cSrcweir                         SCsROW nCurYOffsetTemp = nCurY < nCurY + nRowSpan - 1 ? nRowSpan - 1 : 0;
345cdf0e10cSrcweir                         nCurYOffset = nCurYOffset > nCurYOffsetTemp ? nCurYOffset : nCurYOffsetTemp;
346cdf0e10cSrcweir                     }
347cdf0e10cSrcweir                     if ( !( nBlockStartX <= nCurX && nBlockStartY <= nCurY ) &&
348cdf0e10cSrcweir                          !( nBlockStartX > nCurX + nColSpan - 1 && nBlockStartY > nCurY + nRowSpan - 1 ) )
349cdf0e10cSrcweir                     {
350cdf0e10cSrcweir                         nBlockStartXOffset = nBlockStartX > nCurX && nBlockStartX <= nCurX + nColSpan - 1 ? nCurX - nBlockStartX : 0;
351cdf0e10cSrcweir                         nBlockStartYOffset = nBlockStartY > nCurY && nBlockStartY <= nCurY + nRowSpan - 1 ? nCurY - nBlockStartY : 0;
352cdf0e10cSrcweir                     }
353cdf0e10cSrcweir                 }
354cdf0e10cSrcweir             }
355cdf0e10cSrcweir             else
356cdf0e10cSrcweir             {
357cdf0e10cSrcweir                 // The current cell is not merged.  Move the anchor cell to its
358cdf0e10cSrcweir                 // original position.
359cdf0e10cSrcweir                 if ( !bBlockStartMerged )
360cdf0e10cSrcweir                 {
361cdf0e10cSrcweir                     nBlockStartX = nBlockStartXOrig;
362cdf0e10cSrcweir                     nBlockStartY = nBlockStartYOrig;
363cdf0e10cSrcweir                 }
364cdf0e10cSrcweir             }
365cdf0e10cSrcweir 
366cdf0e10cSrcweir             nBlockStartX = nBlockStartX + nBlockStartXOffset >= 0 ? nBlockStartX + nBlockStartXOffset : 0;
367cdf0e10cSrcweir             nBlockStartY = nBlockStartY + nBlockStartYOffset >= 0 ? nBlockStartY + nBlockStartYOffset : 0;
368cdf0e10cSrcweir             nBlockEndX = nCurX + nCurXOffset > MAXCOL ? MAXCOL : nCurX + nCurXOffset;
369cdf0e10cSrcweir             nBlockEndY = nCurY + nCurYOffset > MAXROW ? MAXROW : nCurY + nCurYOffset;
370cdf0e10cSrcweir         }
371cdf0e10cSrcweir         else
372cdf0e10cSrcweir         {
373cdf0e10cSrcweir             nBlockEndX = nCurX;
374cdf0e10cSrcweir             nBlockEndY = nCurY;
375cdf0e10cSrcweir         }
376cdf0e10cSrcweir         // end of "if ( bCellSelection )"
377cdf0e10cSrcweir 
378cdf0e10cSrcweir         // Set new selection area
379cdf0e10cSrcweir 		aRect.SetNew( nBlockStartX, nBlockStartY, nBlockEndX, nBlockEndY );
380cdf0e10cSrcweir 		rMark.SetMarkArea( ScRange( nBlockStartX, nBlockStartY, nTab, nBlockEndX, nBlockEndY, nTab ) );
381cdf0e10cSrcweir 
382cdf0e10cSrcweir #ifdef OLD_SELECTION_PAINT
383cdf0e10cSrcweir 		sal_Bool bCont;
384cdf0e10cSrcweir 		sal_Bool bDraw = aRect.GetXorDiff( nDrawStartCol, nDrawStartRow,
385cdf0e10cSrcweir 										nDrawEndCol, nDrawEndRow, bCont );
386cdf0e10cSrcweir 		if ( bDraw )
387cdf0e10cSrcweir 		{
388cdf0e10cSrcweir //?			PutInOrder( nDrawStartCol, nDrawEndCol );
389cdf0e10cSrcweir //?			PutInOrder( nDrawStartRow, nDrawEndRow );
390cdf0e10cSrcweir 
391cdf0e10cSrcweir 			HideAllCursors();
392cdf0e10cSrcweir 			InvertBlockMark( nDrawStartCol, nDrawStartRow, nDrawEndCol, nDrawEndRow );
393cdf0e10cSrcweir 			if (bCont)
394cdf0e10cSrcweir 			{
395cdf0e10cSrcweir 				aRect.GetContDiff( nDrawStartCol, nDrawStartRow, nDrawEndCol, nDrawEndRow );
396cdf0e10cSrcweir 				InvertBlockMark( nDrawStartCol, nDrawStartRow, nDrawEndCol, nDrawEndRow );
397cdf0e10cSrcweir 			}
398cdf0e10cSrcweir 			ShowAllCursors();
399cdf0e10cSrcweir 		}
400cdf0e10cSrcweir #endif
401cdf0e10cSrcweir         UpdateSelectionOverlay();
402cdf0e10cSrcweir 
403cdf0e10cSrcweir         nOldCurX = nCurX;
404cdf0e10cSrcweir         nOldCurY = nCurY;
405cdf0e10cSrcweir 
406cdf0e10cSrcweir 		aViewData.GetViewShell()->UpdateInputHandler();
407cdf0e10cSrcweir //		InvalidateAttribs();
408cdf0e10cSrcweir 	}
409cdf0e10cSrcweir 
410cdf0e10cSrcweir 	if ( !bCols && !bRows )
411cdf0e10cSrcweir 		aHdrFunc.SetAnchorFlag( sal_False );
412cdf0e10cSrcweir }
413cdf0e10cSrcweir 
414cdf0e10cSrcweir void ScTabView::UpdateSelectionOverlay()
415cdf0e10cSrcweir {
416cdf0e10cSrcweir     for (sal_uInt16 i=0; i<4; i++)
417cdf0e10cSrcweir         if ( pGridWin[i] && pGridWin[i]->IsVisible() )
418cdf0e10cSrcweir             pGridWin[i]->UpdateSelectionOverlay();
419cdf0e10cSrcweir }
420cdf0e10cSrcweir 
421cdf0e10cSrcweir void ScTabView::UpdateShrinkOverlay()
422cdf0e10cSrcweir {
423cdf0e10cSrcweir     for (sal_uInt16 i=0; i<4; i++)
424cdf0e10cSrcweir         if ( pGridWin[i] && pGridWin[i]->IsVisible() )
425cdf0e10cSrcweir             pGridWin[i]->UpdateShrinkOverlay();
426cdf0e10cSrcweir }
427cdf0e10cSrcweir 
428cdf0e10cSrcweir void ScTabView::UpdateAllOverlays()
429cdf0e10cSrcweir {
430cdf0e10cSrcweir     for (sal_uInt16 i=0; i<4; i++)
431cdf0e10cSrcweir         if ( pGridWin[i] && pGridWin[i]->IsVisible() )
432cdf0e10cSrcweir             pGridWin[i]->UpdateAllOverlays();
433cdf0e10cSrcweir }
434cdf0e10cSrcweir 
435cdf0e10cSrcweir //!
436cdf0e10cSrcweir //!	PaintBlock in zwei Methoden aufteilen: RepaintBlock und RemoveBlock o.ae.
437cdf0e10cSrcweir //!
438cdf0e10cSrcweir 
439cdf0e10cSrcweir void ScTabView::PaintBlock( sal_Bool bReset )
440cdf0e10cSrcweir {
441cdf0e10cSrcweir 	ScDocument* pDoc = aViewData.GetDocument();
442cdf0e10cSrcweir 	ScMarkData& rMark = aViewData.GetMarkData();
443cdf0e10cSrcweir 	SCTAB nTab = aViewData.GetTabNo();
444cdf0e10cSrcweir 	sal_Bool bMark = rMark.IsMarked();
445cdf0e10cSrcweir 	sal_Bool bMulti = rMark.IsMultiMarked();
446cdf0e10cSrcweir 	if (bMark || bMulti)
447cdf0e10cSrcweir 	{
448cdf0e10cSrcweir 		ScRange aMarkRange;
449cdf0e10cSrcweir 		HideAllCursors();
450cdf0e10cSrcweir 		if (bMulti)
451cdf0e10cSrcweir 		{
452cdf0e10cSrcweir 			sal_Bool bFlag = rMark.GetMarkingFlag();
453cdf0e10cSrcweir 			rMark.SetMarking(sal_False);
454cdf0e10cSrcweir 			rMark.MarkToMulti();
455cdf0e10cSrcweir 			rMark.GetMultiMarkArea(aMarkRange);
456cdf0e10cSrcweir 			rMark.MarkToSimple();
457cdf0e10cSrcweir 			rMark.SetMarking(bFlag);
458cdf0e10cSrcweir 
459cdf0e10cSrcweir 			bMark = rMark.IsMarked();
460cdf0e10cSrcweir 			bMulti = rMark.IsMultiMarked();
461cdf0e10cSrcweir 		}
462cdf0e10cSrcweir 		else
463cdf0e10cSrcweir 			rMark.GetMarkArea(aMarkRange);
464cdf0e10cSrcweir 
465cdf0e10cSrcweir 		nBlockStartX = aMarkRange.aStart.Col();
466cdf0e10cSrcweir 		nBlockStartY = aMarkRange.aStart.Row();
467cdf0e10cSrcweir 		nBlockStartZ = aMarkRange.aStart.Tab();
468cdf0e10cSrcweir 		nBlockEndX = aMarkRange.aEnd.Col();
469cdf0e10cSrcweir 		nBlockEndY = aMarkRange.aEnd.Row();
470cdf0e10cSrcweir 		nBlockEndZ = aMarkRange.aEnd.Tab();
471cdf0e10cSrcweir 
472cdf0e10cSrcweir 		sal_Bool bDidReset = sal_False;
473cdf0e10cSrcweir 
474cdf0e10cSrcweir 		if ( nTab>=nBlockStartZ && nTab<=nBlockEndZ )
475cdf0e10cSrcweir 		{
476cdf0e10cSrcweir 			if ( bReset )
477cdf0e10cSrcweir 			{
478cdf0e10cSrcweir 				// Invertieren beim Loeschen nur auf aktiver View
479cdf0e10cSrcweir 				if ( aViewData.IsActive() )
480cdf0e10cSrcweir 				{
481cdf0e10cSrcweir 					sal_uInt16 i;
482cdf0e10cSrcweir 					if ( bMulti )
483cdf0e10cSrcweir 					{
484cdf0e10cSrcweir #ifdef OLD_SELECTION_PAINT
485cdf0e10cSrcweir 						for (i=0; i<4; i++)
486cdf0e10cSrcweir 							if (pGridWin[i] && pGridWin[i]->IsVisible())
487cdf0e10cSrcweir 								pGridWin[i]->InvertSimple( nBlockStartX, nBlockStartY,
488cdf0e10cSrcweir 															nBlockEndX, nBlockEndY,
489cdf0e10cSrcweir 															sal_True, sal_True );
490cdf0e10cSrcweir #endif
491cdf0e10cSrcweir 						rMark.ResetMark();
492cdf0e10cSrcweir                         UpdateSelectionOverlay();
493cdf0e10cSrcweir 						bDidReset = sal_True;
494cdf0e10cSrcweir 					}
495cdf0e10cSrcweir 					else
496cdf0e10cSrcweir 					{
497cdf0e10cSrcweir #ifdef OLD_SELECTION_PAINT
498cdf0e10cSrcweir 						// (mis)use InvertBlockMark to remove all of the selection
499cdf0e10cSrcweir 						// -> set bBlockNeg (like when removing parts of a selection)
500cdf0e10cSrcweir 						//	  and convert everything to Multi
501cdf0e10cSrcweir 
502cdf0e10cSrcweir 						rMark.MarkToMulti();
503cdf0e10cSrcweir 						sal_Bool bOld = bBlockNeg;
504cdf0e10cSrcweir 						bBlockNeg = sal_True;
505cdf0e10cSrcweir 						// #73130# (negative) MarkArea must be set in case of repaint
506cdf0e10cSrcweir 						rMark.SetMarkArea( ScRange( nBlockStartX,nBlockStartY, nTab,
507cdf0e10cSrcweir 													nBlockEndX,nBlockEndY, nTab ) );
508cdf0e10cSrcweir 
509cdf0e10cSrcweir 						InvertBlockMark( nBlockStartX, nBlockStartY, nBlockEndX, nBlockEndY );
510cdf0e10cSrcweir 
511cdf0e10cSrcweir 						bBlockNeg = bOld;
512cdf0e10cSrcweir #endif
513cdf0e10cSrcweir 						rMark.ResetMark();
514cdf0e10cSrcweir                         UpdateSelectionOverlay();
515cdf0e10cSrcweir 						bDidReset = sal_True;
516cdf0e10cSrcweir 					}
517cdf0e10cSrcweir 
518cdf0e10cSrcweir 					//	repaint if controls are touched (#69680# in both cases)
519cdf0e10cSrcweir 					// #i74768# Forms are rendered by DrawingLayer's EndDrawLayers()
520cdf0e10cSrcweir 					static bool bSuppressControlExtraStuff(true);
521cdf0e10cSrcweir 
522cdf0e10cSrcweir 					if(!bSuppressControlExtraStuff)
523cdf0e10cSrcweir 					{
524cdf0e10cSrcweir 						Rectangle aMMRect = pDoc->GetMMRect(nBlockStartX,nBlockStartY,nBlockEndX,nBlockEndY, nTab);
525cdf0e10cSrcweir 						if (pDoc->HasControl( nTab, aMMRect ))
526cdf0e10cSrcweir 						{
527cdf0e10cSrcweir 							for (i=0; i<4; i++)
528cdf0e10cSrcweir 							{
529cdf0e10cSrcweir 								if (pGridWin[i] && pGridWin[i]->IsVisible())
530cdf0e10cSrcweir 								{
531cdf0e10cSrcweir 									//	MapMode muss logischer (1/100mm) sein !!!
532cdf0e10cSrcweir 									pDoc->InvalidateControls( pGridWin[i], nTab, aMMRect );
533cdf0e10cSrcweir 									pGridWin[i]->Update();
534cdf0e10cSrcweir 								}
535cdf0e10cSrcweir 							}
536cdf0e10cSrcweir 						}
537cdf0e10cSrcweir 					}
538cdf0e10cSrcweir 				}
539cdf0e10cSrcweir 			}
540cdf0e10cSrcweir 			else
541cdf0e10cSrcweir 				PaintMarks( nBlockStartX, nBlockStartY, nBlockEndX, nBlockEndY );
542cdf0e10cSrcweir 		}
543cdf0e10cSrcweir 
544cdf0e10cSrcweir 		if ( bReset && !bDidReset )
545cdf0e10cSrcweir 			rMark.ResetMark();
546cdf0e10cSrcweir 
547cdf0e10cSrcweir 		ShowAllCursors();
548cdf0e10cSrcweir 	}
549cdf0e10cSrcweir }
550cdf0e10cSrcweir 
551cdf0e10cSrcweir void ScTabView::SelectAll( sal_Bool bContinue )
552cdf0e10cSrcweir {
553cdf0e10cSrcweir 	ScMarkData& rMark = aViewData.GetMarkData();
554cdf0e10cSrcweir 	SCTAB nTab = aViewData.GetTabNo();
555cdf0e10cSrcweir 
556cdf0e10cSrcweir 	if (rMark.IsMarked())
557cdf0e10cSrcweir 	{
558cdf0e10cSrcweir 		ScRange aMarkRange;
559cdf0e10cSrcweir 		rMark.GetMarkArea( aMarkRange );
560cdf0e10cSrcweir 		if ( aMarkRange == ScRange( 0,0,nTab, MAXCOL,MAXROW,nTab ) )
561cdf0e10cSrcweir 			return;
562cdf0e10cSrcweir 	}
563cdf0e10cSrcweir 
564cdf0e10cSrcweir 	DoneBlockMode( bContinue );
565cdf0e10cSrcweir 	InitBlockMode( 0,0,nTab );
566cdf0e10cSrcweir 	MarkCursor( MAXCOL,MAXROW,nTab );
567cdf0e10cSrcweir 
568cdf0e10cSrcweir 	SelectionChanged();
569cdf0e10cSrcweir }
570cdf0e10cSrcweir 
571cdf0e10cSrcweir void ScTabView::SelectAllTables()
572cdf0e10cSrcweir {
573cdf0e10cSrcweir 	ScDocument* pDoc = aViewData.GetDocument();
574cdf0e10cSrcweir 	ScMarkData& rMark = aViewData.GetMarkData();
575cdf0e10cSrcweir //    SCTAB nTab = aViewData.GetTabNo();
576cdf0e10cSrcweir 	SCTAB nCount = pDoc->GetTableCount();
577cdf0e10cSrcweir 
578cdf0e10cSrcweir 	if (nCount>1)
579cdf0e10cSrcweir 	{
580cdf0e10cSrcweir 		for (SCTAB i=0; i<nCount; i++)
581cdf0e10cSrcweir 			rMark.SelectTable( i, sal_True );
582cdf0e10cSrcweir 
583cdf0e10cSrcweir 		//		Markierungen werden per Default nicht pro Tabelle gehalten
584cdf0e10cSrcweir //		pDoc->ExtendMarksFromTable( nTab );
585cdf0e10cSrcweir 
586cdf0e10cSrcweir 		aViewData.GetDocShell()->PostPaintExtras();
587cdf0e10cSrcweir         SfxBindings& rBind = aViewData.GetBindings();
588cdf0e10cSrcweir         rBind.Invalidate( FID_FILL_TAB );
589cdf0e10cSrcweir         rBind.Invalidate( FID_TAB_DESELECTALL );
590cdf0e10cSrcweir 	}
591cdf0e10cSrcweir }
592cdf0e10cSrcweir 
593cdf0e10cSrcweir void ScTabView::DeselectAllTables()
594cdf0e10cSrcweir {
595cdf0e10cSrcweir     ScDocument* pDoc = aViewData.GetDocument();
596cdf0e10cSrcweir     ScMarkData& rMark = aViewData.GetMarkData();
597cdf0e10cSrcweir     SCTAB nTab = aViewData.GetTabNo();
598cdf0e10cSrcweir     SCTAB nCount = pDoc->GetTableCount();
599cdf0e10cSrcweir 
600cdf0e10cSrcweir     for (SCTAB i=0; i<nCount; i++)
601cdf0e10cSrcweir         rMark.SelectTable( i, ( i == nTab ) );
602cdf0e10cSrcweir 
603cdf0e10cSrcweir     aViewData.GetDocShell()->PostPaintExtras();
604cdf0e10cSrcweir     SfxBindings& rBind = aViewData.GetBindings();
605cdf0e10cSrcweir     rBind.Invalidate( FID_FILL_TAB );
606cdf0e10cSrcweir     rBind.Invalidate( FID_TAB_DESELECTALL );
607cdf0e10cSrcweir }
608cdf0e10cSrcweir 
609cdf0e10cSrcweir sal_Bool lcl_FitsInWindow( double fScaleX, double fScaleY, sal_uInt16 nZoom,
610cdf0e10cSrcweir 						long nWindowX, long nWindowY, ScDocument* pDoc, SCTAB nTab,
611cdf0e10cSrcweir 						SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
612cdf0e10cSrcweir 						SCCOL nFixPosX, SCROW nFixPosY )
613cdf0e10cSrcweir {
614cdf0e10cSrcweir 	double fZoomFactor = (double)Fraction(nZoom,100);
615cdf0e10cSrcweir 	fScaleX *= fZoomFactor;
616cdf0e10cSrcweir 	fScaleY *= fZoomFactor;
617cdf0e10cSrcweir 
618cdf0e10cSrcweir 	long nBlockX = 0;
619cdf0e10cSrcweir 	SCCOL nCol;
620cdf0e10cSrcweir 	for (nCol=0; nCol<nFixPosX; nCol++)
621cdf0e10cSrcweir 	{
622cdf0e10cSrcweir 		//	for frozen panes, add both parts
623cdf0e10cSrcweir 		sal_uInt16 nColTwips = pDoc->GetColWidth( nCol, nTab );
624cdf0e10cSrcweir 		if (nColTwips)
625cdf0e10cSrcweir 		{
626cdf0e10cSrcweir 			nBlockX += (long)(nColTwips * fScaleX);
627cdf0e10cSrcweir 			if (nBlockX > nWindowX)
628cdf0e10cSrcweir 				return sal_False;
629cdf0e10cSrcweir 		}
630cdf0e10cSrcweir 	}
631cdf0e10cSrcweir 	for (nCol=nStartCol; nCol<=nEndCol; nCol++)
632cdf0e10cSrcweir 	{
633cdf0e10cSrcweir 		sal_uInt16 nColTwips = pDoc->GetColWidth( nCol, nTab );
634cdf0e10cSrcweir 		if (nColTwips)
635cdf0e10cSrcweir 		{
636cdf0e10cSrcweir 			nBlockX += (long)(nColTwips * fScaleX);
637cdf0e10cSrcweir 			if (nBlockX > nWindowX)
638cdf0e10cSrcweir 				return sal_False;
639cdf0e10cSrcweir 		}
640cdf0e10cSrcweir 	}
641cdf0e10cSrcweir 
642cdf0e10cSrcweir 	long nBlockY = 0;
643cdf0e10cSrcweir     for (SCROW nRow = 0; nRow <= nFixPosY-1; ++nRow)
644cdf0e10cSrcweir 	{
645cdf0e10cSrcweir         if (pDoc->RowHidden(nRow, nTab))
646cdf0e10cSrcweir             continue;
647cdf0e10cSrcweir 
648cdf0e10cSrcweir 		//	for frozen panes, add both parts
649cdf0e10cSrcweir         sal_uInt16 nRowTwips = pDoc->GetRowHeight(nRow, nTab);
650cdf0e10cSrcweir 		if (nRowTwips)
651cdf0e10cSrcweir 		{
652cdf0e10cSrcweir 			nBlockY += (long)(nRowTwips * fScaleY);
653cdf0e10cSrcweir 			if (nBlockY > nWindowY)
654cdf0e10cSrcweir 				return sal_False;
655cdf0e10cSrcweir 		}
656cdf0e10cSrcweir 	}
657cdf0e10cSrcweir     for (SCROW nRow = nStartRow; nRow <= nEndRow; ++nRow)
658cdf0e10cSrcweir 	{
659cdf0e10cSrcweir         sal_uInt16 nRowTwips = pDoc->GetRowHeight(nRow, nTab);
660cdf0e10cSrcweir 		if (nRowTwips)
661cdf0e10cSrcweir 		{
662cdf0e10cSrcweir 			nBlockY += (long)(nRowTwips * fScaleY);
663cdf0e10cSrcweir 			if (nBlockY > nWindowY)
664cdf0e10cSrcweir 				return sal_False;
665cdf0e10cSrcweir 		}
666cdf0e10cSrcweir 	}
667cdf0e10cSrcweir 
668cdf0e10cSrcweir 	return sal_True;
669cdf0e10cSrcweir }
670cdf0e10cSrcweir 
671cdf0e10cSrcweir sal_uInt16 ScTabView::CalcZoom( SvxZoomType eType, sal_uInt16 nOldZoom )
672cdf0e10cSrcweir {
673cdf0e10cSrcweir 	sal_uInt16 nZoom = 0; // Ergebnis
674cdf0e10cSrcweir 
675cdf0e10cSrcweir 	switch ( eType )
676cdf0e10cSrcweir 	{
677cdf0e10cSrcweir 		case SVX_ZOOM_PERCENT: // rZoom ist kein besonderer prozentualer Wert
678cdf0e10cSrcweir 			nZoom = nOldZoom;
679cdf0e10cSrcweir 			break;
680cdf0e10cSrcweir 
681cdf0e10cSrcweir 		case SVX_ZOOM_OPTIMAL:	// nZoom entspricht der optimalen Gr"o\se
682cdf0e10cSrcweir 			{
683cdf0e10cSrcweir 				ScMarkData& rMark = aViewData.GetMarkData();
684cdf0e10cSrcweir 				ScDocument* pDoc = aViewData.GetDocument();
685cdf0e10cSrcweir 
686cdf0e10cSrcweir 				if (!rMark.IsMarked() && !rMark.IsMultiMarked())
687cdf0e10cSrcweir 					nZoom = 100;				// nothing selected
688cdf0e10cSrcweir 				else
689cdf0e10cSrcweir 				{
690cdf0e10cSrcweir 					SCTAB	nTab = aViewData.GetTabNo();
691cdf0e10cSrcweir 					ScRange aMarkRange;
692cdf0e10cSrcweir 					if ( aViewData.GetSimpleArea( aMarkRange ) != SC_MARK_SIMPLE )
693cdf0e10cSrcweir 						rMark.GetMultiMarkArea( aMarkRange );
694cdf0e10cSrcweir 
695cdf0e10cSrcweir 					SCCOL	nStartCol = aMarkRange.aStart.Col();
696cdf0e10cSrcweir 					SCROW	nStartRow = aMarkRange.aStart.Row();
697cdf0e10cSrcweir 					SCTAB	nStartTab = aMarkRange.aStart.Tab();
698cdf0e10cSrcweir 					SCCOL	nEndCol = aMarkRange.aEnd.Col();
699cdf0e10cSrcweir 					SCROW	nEndRow = aMarkRange.aEnd.Row();
700cdf0e10cSrcweir 					SCTAB	nEndTab = aMarkRange.aEnd.Tab();
701cdf0e10cSrcweir 
702cdf0e10cSrcweir 					if ( nTab < nStartTab && nTab > nEndTab )
703cdf0e10cSrcweir 						nTab = nStartTab;
704cdf0e10cSrcweir 
705cdf0e10cSrcweir 					ScSplitPos eUsedPart = aViewData.GetActivePart();
706cdf0e10cSrcweir 
707cdf0e10cSrcweir 					SCCOL nFixPosX = 0;
708cdf0e10cSrcweir 					SCROW nFixPosY = 0;
709cdf0e10cSrcweir 					if ( aViewData.GetHSplitMode() == SC_SPLIT_FIX )
710cdf0e10cSrcweir 					{
711cdf0e10cSrcweir 						//	use right part
712cdf0e10cSrcweir 						eUsedPart = (WhichV(eUsedPart)==SC_SPLIT_TOP) ? SC_SPLIT_TOPRIGHT : SC_SPLIT_BOTTOMRIGHT;
713cdf0e10cSrcweir 						nFixPosX = aViewData.GetFixPosX();
714cdf0e10cSrcweir 						if ( nStartCol < nFixPosX )
715cdf0e10cSrcweir 							nStartCol = nFixPosX;
716cdf0e10cSrcweir 					}
717cdf0e10cSrcweir 					if ( aViewData.GetVSplitMode() == SC_SPLIT_FIX )
718cdf0e10cSrcweir 					{
719cdf0e10cSrcweir 						//	use bottom part
720cdf0e10cSrcweir 						eUsedPart = (WhichH(eUsedPart)==SC_SPLIT_LEFT) ? SC_SPLIT_BOTTOMLEFT : SC_SPLIT_BOTTOMRIGHT;
721cdf0e10cSrcweir 						nFixPosY = aViewData.GetFixPosY();
722cdf0e10cSrcweir 						if ( nStartRow < nFixPosY )
723cdf0e10cSrcweir 							nStartRow = nFixPosY;
724cdf0e10cSrcweir 					}
725cdf0e10cSrcweir 
726cdf0e10cSrcweir 					if (pGridWin[eUsedPart])
727cdf0e10cSrcweir 					{
728cdf0e10cSrcweir 						//	Because scale is rounded to pixels, the only reliable way to find
729cdf0e10cSrcweir 						//	the right scale is to check if a zoom fits
730cdf0e10cSrcweir 
731cdf0e10cSrcweir 						Size aWinSize = pGridWin[eUsedPart]->GetOutputSizePixel();
732cdf0e10cSrcweir 
733cdf0e10cSrcweir 						//	for frozen panes, use sum of both parts for calculation
734cdf0e10cSrcweir 
735cdf0e10cSrcweir 						if ( nFixPosX != 0 )
736cdf0e10cSrcweir 							aWinSize.Width() += GetGridWidth( SC_SPLIT_LEFT );
737cdf0e10cSrcweir 						if ( nFixPosY != 0 )
738cdf0e10cSrcweir 							aWinSize.Height() += GetGridHeight( SC_SPLIT_TOP );
739cdf0e10cSrcweir 
740cdf0e10cSrcweir 						ScDocShell* pDocSh = aViewData.GetDocShell();
741cdf0e10cSrcweir 						double nPPTX = ScGlobal::nScreenPPTX / pDocSh->GetOutputFactor();
742cdf0e10cSrcweir 						double nPPTY = ScGlobal::nScreenPPTY;
743cdf0e10cSrcweir 
744cdf0e10cSrcweir 						sal_uInt16 nMin = MINZOOM;
745cdf0e10cSrcweir 						sal_uInt16 nMax = MAXZOOM;
746cdf0e10cSrcweir 						while ( nMax > nMin )
747cdf0e10cSrcweir 						{
748cdf0e10cSrcweir 							sal_uInt16 nTest = (nMin+nMax+1)/2;
749cdf0e10cSrcweir 							if ( lcl_FitsInWindow(
750cdf0e10cSrcweir 										nPPTX, nPPTY, nTest, aWinSize.Width(), aWinSize.Height(),
751cdf0e10cSrcweir 										pDoc, nTab, nStartCol, nStartRow, nEndCol, nEndRow,
752cdf0e10cSrcweir 										nFixPosX, nFixPosY ) )
753cdf0e10cSrcweir 								nMin = nTest;
754cdf0e10cSrcweir 							else
755cdf0e10cSrcweir 								nMax = nTest-1;
756cdf0e10cSrcweir 						}
757cdf0e10cSrcweir 						DBG_ASSERT( nMin == nMax, "Schachtelung ist falsch" );
758cdf0e10cSrcweir 						nZoom = nMin;
759cdf0e10cSrcweir 
760cdf0e10cSrcweir 						if ( nZoom != nOldZoom )
761cdf0e10cSrcweir 						{
762cdf0e10cSrcweir 							// scroll to block only in active split part
763cdf0e10cSrcweir 							// (the part for which the size was calculated)
764cdf0e10cSrcweir 
765cdf0e10cSrcweir 							if ( nStartCol <= nEndCol )
766cdf0e10cSrcweir 								aViewData.SetPosX( WhichH(eUsedPart), nStartCol );
767cdf0e10cSrcweir 							if ( nStartRow <= nEndRow )
768cdf0e10cSrcweir 								aViewData.SetPosY( WhichV(eUsedPart), nStartRow );
769cdf0e10cSrcweir 						}
770cdf0e10cSrcweir 					}
771cdf0e10cSrcweir 				}
772cdf0e10cSrcweir 			}
773cdf0e10cSrcweir 			break;
774cdf0e10cSrcweir 
775cdf0e10cSrcweir 			case SVX_ZOOM_WHOLEPAGE:	// nZoom entspricht der ganzen Seite oder
776cdf0e10cSrcweir 			case SVX_ZOOM_PAGEWIDTH:	// nZoom entspricht der Seitenbreite
777cdf0e10cSrcweir 				{
778cdf0e10cSrcweir 					SCTAB				nCurTab		= aViewData.GetTabNo();
779cdf0e10cSrcweir 					ScDocument*			pDoc		= aViewData.GetDocument();
780cdf0e10cSrcweir 					ScStyleSheetPool*	pStylePool  = pDoc->GetStyleSheetPool();
781cdf0e10cSrcweir 					SfxStyleSheetBase*	pStyleSheet =
782cdf0e10cSrcweir 											pStylePool->Find( pDoc->GetPageStyle( nCurTab ),
783cdf0e10cSrcweir 															  SFX_STYLE_FAMILY_PAGE );
784cdf0e10cSrcweir 
785cdf0e10cSrcweir 					DBG_ASSERT( pStyleSheet, "PageStyle not found :-/" );
786cdf0e10cSrcweir 
787cdf0e10cSrcweir 					if ( pStyleSheet )
788cdf0e10cSrcweir 					{
789cdf0e10cSrcweir 						ScPrintFunc aPrintFunc( aViewData.GetDocShell(),
790cdf0e10cSrcweir 												aViewData.GetViewShell()->GetPrinter(sal_True),
791cdf0e10cSrcweir 												nCurTab );
792cdf0e10cSrcweir 
793cdf0e10cSrcweir 						Size aPageSize = aPrintFunc.GetDataSize();
794cdf0e10cSrcweir 
795cdf0e10cSrcweir 						//	use the size of the largest GridWin for normal split,
796cdf0e10cSrcweir 						//	or both combined for frozen panes, with the (document) size
797cdf0e10cSrcweir 						//	of the frozen part added to the page size
798cdf0e10cSrcweir 						//	(with frozen panes, the size of the individual parts
799cdf0e10cSrcweir 						//	depends on the scale that is to be calculated)
800cdf0e10cSrcweir 
801cdf0e10cSrcweir 						if ( !pGridWin[SC_SPLIT_BOTTOMLEFT] ) return 0;
802cdf0e10cSrcweir 						Size aWinSize = pGridWin[SC_SPLIT_BOTTOMLEFT]->GetOutputSizePixel();
803cdf0e10cSrcweir 						ScSplitMode eHMode = aViewData.GetHSplitMode();
804cdf0e10cSrcweir 						if ( eHMode != SC_SPLIT_NONE && pGridWin[SC_SPLIT_BOTTOMRIGHT] )
805cdf0e10cSrcweir 						{
806cdf0e10cSrcweir 							long nOtherWidth = pGridWin[SC_SPLIT_BOTTOMRIGHT]->
807cdf0e10cSrcweir 														GetOutputSizePixel().Width();
808cdf0e10cSrcweir 							if ( eHMode == SC_SPLIT_FIX )
809cdf0e10cSrcweir 							{
810cdf0e10cSrcweir 								aWinSize.Width() += nOtherWidth;
811cdf0e10cSrcweir 								for ( SCCOL nCol = aViewData.GetPosX(SC_SPLIT_LEFT);
812cdf0e10cSrcweir 										nCol < aViewData.GetFixPosX(); nCol++ )
813cdf0e10cSrcweir 									aPageSize.Width() += pDoc->GetColWidth( nCol, nCurTab );
814cdf0e10cSrcweir 							}
815cdf0e10cSrcweir 							else if ( nOtherWidth > aWinSize.Width() )
816cdf0e10cSrcweir 								aWinSize.Width() = nOtherWidth;
817cdf0e10cSrcweir 						}
818cdf0e10cSrcweir 						ScSplitMode eVMode = aViewData.GetVSplitMode();
819cdf0e10cSrcweir 						if ( eVMode != SC_SPLIT_NONE && pGridWin[SC_SPLIT_TOPLEFT] )
820cdf0e10cSrcweir 						{
821cdf0e10cSrcweir 							long nOtherHeight = pGridWin[SC_SPLIT_TOPLEFT]->
822cdf0e10cSrcweir 														GetOutputSizePixel().Height();
823cdf0e10cSrcweir 							if ( eVMode == SC_SPLIT_FIX )
824cdf0e10cSrcweir 							{
825cdf0e10cSrcweir 								aWinSize.Height() += nOtherHeight;
826cdf0e10cSrcweir                                 aPageSize.Height() += pDoc->GetRowHeight(
827cdf0e10cSrcweir                                         aViewData.GetPosY(SC_SPLIT_TOP),
828cdf0e10cSrcweir                                         aViewData.GetFixPosY()-1, nCurTab);
829cdf0e10cSrcweir 							}
830cdf0e10cSrcweir 							else if ( nOtherHeight > aWinSize.Height() )
831cdf0e10cSrcweir 								aWinSize.Height() = nOtherHeight;
832cdf0e10cSrcweir 						}
833cdf0e10cSrcweir 
834cdf0e10cSrcweir 						double nPPTX = ScGlobal::nScreenPPTX / aViewData.GetDocShell()->GetOutputFactor();
835cdf0e10cSrcweir 						double nPPTY = ScGlobal::nScreenPPTY;
836cdf0e10cSrcweir 
837cdf0e10cSrcweir 						long nZoomX = (long) ( aWinSize.Width() * 100 /
838cdf0e10cSrcweir 											   ( aPageSize.Width() * nPPTX ) );
839cdf0e10cSrcweir 						long nZoomY = (long) ( aWinSize.Height() * 100 /
840cdf0e10cSrcweir 											   ( aPageSize.Height() * nPPTY ) );
841cdf0e10cSrcweir 						long nNew = nZoomX;
842cdf0e10cSrcweir 
843cdf0e10cSrcweir 						if (eType == SVX_ZOOM_WHOLEPAGE && nZoomY < nNew)
844cdf0e10cSrcweir 							nNew = nZoomY;
845cdf0e10cSrcweir 
846cdf0e10cSrcweir 						nZoom = (sal_uInt16) nNew;
847cdf0e10cSrcweir 					}
848cdf0e10cSrcweir 				}
849cdf0e10cSrcweir 				break;
850cdf0e10cSrcweir 
851cdf0e10cSrcweir 		default:
852cdf0e10cSrcweir 			DBG_ERROR("Unknown Zoom-Revision");
853cdf0e10cSrcweir 			nZoom = 0;
854cdf0e10cSrcweir 	}
855cdf0e10cSrcweir 
856cdf0e10cSrcweir 	return nZoom;
857cdf0e10cSrcweir }
858cdf0e10cSrcweir 
859cdf0e10cSrcweir //	wird z.B. gerufen, wenn sich das View-Fenster verschiebt:
860cdf0e10cSrcweir 
861cdf0e10cSrcweir void ScTabView::StopMarking()
862cdf0e10cSrcweir {
863cdf0e10cSrcweir 	ScSplitPos eActive = aViewData.GetActivePart();
864cdf0e10cSrcweir 	if (pGridWin[eActive])
865cdf0e10cSrcweir 		pGridWin[eActive]->StopMarking();
866cdf0e10cSrcweir 
867cdf0e10cSrcweir 	ScHSplitPos eH = WhichH(eActive);
868cdf0e10cSrcweir 	if (pColBar[eH])
869cdf0e10cSrcweir 		pColBar[eH]->StopMarking();
870cdf0e10cSrcweir 
871cdf0e10cSrcweir 	ScVSplitPos eV = WhichV(eActive);
872cdf0e10cSrcweir 	if (pRowBar[eV])
873cdf0e10cSrcweir 		pRowBar[eV]->StopMarking();
874cdf0e10cSrcweir }
875cdf0e10cSrcweir 
876cdf0e10cSrcweir void ScTabView::HideNoteMarker()
877cdf0e10cSrcweir {
878cdf0e10cSrcweir 	for (sal_uInt16 i=0; i<4; i++)
879cdf0e10cSrcweir 		if (pGridWin[i] && pGridWin[i]->IsVisible())
880cdf0e10cSrcweir 			pGridWin[i]->HideNoteMarker();
881cdf0e10cSrcweir }
882cdf0e10cSrcweir 
883cdf0e10cSrcweir void ScTabView::MakeDrawLayer()
884cdf0e10cSrcweir {
885cdf0e10cSrcweir 	if (!pDrawView)
886cdf0e10cSrcweir 	{
887cdf0e10cSrcweir 		aViewData.GetDocShell()->MakeDrawLayer();
888cdf0e10cSrcweir 
889cdf0e10cSrcweir 		//	pDrawView wird per Notify gesetzt
890cdf0e10cSrcweir 		DBG_ASSERT(pDrawView,"ScTabView::MakeDrawLayer funktioniert nicht");
891cdf0e10cSrcweir 
892cdf0e10cSrcweir 		// #114409#
893cdf0e10cSrcweir 		for(sal_uInt16 a(0); a < 4; a++)
894cdf0e10cSrcweir 		{
895cdf0e10cSrcweir 			if(pGridWin[a])
896cdf0e10cSrcweir 			{
897cdf0e10cSrcweir 				pGridWin[a]->DrawLayerCreated();
898cdf0e10cSrcweir 			}
899cdf0e10cSrcweir 		}
900cdf0e10cSrcweir 	}
901cdf0e10cSrcweir }
902cdf0e10cSrcweir 
903cdf0e10cSrcweir void ScTabView::ErrorMessage( sal_uInt16 nGlobStrId )
904cdf0e10cSrcweir {
905cdf0e10cSrcweir     if ( SC_MOD()->IsInExecuteDrop() )
906cdf0e10cSrcweir     {
907cdf0e10cSrcweir         // #i28468# don't show error message when called from Drag&Drop, silently abort instead
908cdf0e10cSrcweir         return;
909cdf0e10cSrcweir     }
910cdf0e10cSrcweir 
911cdf0e10cSrcweir 	StopMarking();		// falls per Focus aus MouseButtonDown aufgerufen
912cdf0e10cSrcweir 
913cdf0e10cSrcweir 	Window* pParent = aViewData.GetDialogParent();
914cdf0e10cSrcweir 	ScWaitCursorOff aWaitOff( pParent );
915cdf0e10cSrcweir 	sal_Bool bFocus = pParent && pParent->HasFocus();
916cdf0e10cSrcweir 
917cdf0e10cSrcweir 	if(nGlobStrId==STR_PROTECTIONERR)
918cdf0e10cSrcweir 	{
919cdf0e10cSrcweir 		if(aViewData.GetDocShell()->IsReadOnly())
920cdf0e10cSrcweir 		{
921cdf0e10cSrcweir 			nGlobStrId=STR_READONLYERR;
922cdf0e10cSrcweir 		}
923cdf0e10cSrcweir 	}
924cdf0e10cSrcweir 
925cdf0e10cSrcweir 	InfoBox aBox( pParent, ScGlobal::GetRscString( nGlobStrId ) );
926cdf0e10cSrcweir 	aBox.Execute();
927cdf0e10cSrcweir 	if (bFocus)
928cdf0e10cSrcweir 		pParent->GrabFocus();
929cdf0e10cSrcweir }
930cdf0e10cSrcweir 
931cdf0e10cSrcweir Window* ScTabView::GetParentOrChild( sal_uInt16 nChildId )
932cdf0e10cSrcweir {
933cdf0e10cSrcweir 	SfxViewFrame* pViewFrm = aViewData.GetViewShell()->GetViewFrame();
934cdf0e10cSrcweir 
935cdf0e10cSrcweir 	if ( pViewFrm->HasChildWindow(nChildId) )
936cdf0e10cSrcweir 	{
937cdf0e10cSrcweir 		SfxChildWindow* pChild = pViewFrm->GetChildWindow(nChildId);
938cdf0e10cSrcweir 		if (pChild)
939cdf0e10cSrcweir 		{
940cdf0e10cSrcweir 			Window* pWin = pChild->GetWindow();
941cdf0e10cSrcweir 			if (pWin && pWin->IsVisible())
942cdf0e10cSrcweir 				return pWin;
943cdf0e10cSrcweir 		}
944cdf0e10cSrcweir 	}
945cdf0e10cSrcweir 
946cdf0e10cSrcweir 	return aViewData.GetDialogParent();
947cdf0e10cSrcweir }
948cdf0e10cSrcweir 
949cdf0e10cSrcweir void ScTabView::UpdatePageBreakData( sal_Bool bForcePaint )
950cdf0e10cSrcweir {
951cdf0e10cSrcweir 	ScPageBreakData* pNewData = NULL;
952cdf0e10cSrcweir 
953cdf0e10cSrcweir 	if (aViewData.IsPagebreakMode())
954cdf0e10cSrcweir 	{
955cdf0e10cSrcweir 		ScDocShell* pDocSh = aViewData.GetDocShell();
956cdf0e10cSrcweir 		ScDocument* pDoc = pDocSh->GetDocument();
957cdf0e10cSrcweir 		SCTAB nTab = aViewData.GetTabNo();
958cdf0e10cSrcweir 
959cdf0e10cSrcweir 		sal_uInt16 nCount = pDoc->GetPrintRangeCount(nTab);
960cdf0e10cSrcweir 		if (!nCount)
961cdf0e10cSrcweir 			nCount = 1;
962cdf0e10cSrcweir 		pNewData = new ScPageBreakData(nCount);
963cdf0e10cSrcweir 
964cdf0e10cSrcweir 		ScPrintFunc aPrintFunc( pDocSh, pDocSh->GetPrinter(), nTab, 0,0,NULL, NULL, pNewData );
965cdf0e10cSrcweir 		//	ScPrintFunc fuellt im ctor die PageBreakData
966cdf0e10cSrcweir 		if ( nCount > 1 )
967cdf0e10cSrcweir 		{
968cdf0e10cSrcweir 			aPrintFunc.ResetBreaks(nTab);
969cdf0e10cSrcweir 			pNewData->AddPages();
970cdf0e10cSrcweir 		}
971cdf0e10cSrcweir 
972cdf0e10cSrcweir 		//	Druckbereiche veraendert?
973cdf0e10cSrcweir 		if ( bForcePaint || ( pPageBreakData && !pPageBreakData->IsEqual( *pNewData ) ) )
974cdf0e10cSrcweir 			PaintGrid();
975cdf0e10cSrcweir 	}
976cdf0e10cSrcweir 
977cdf0e10cSrcweir 	delete pPageBreakData;
978cdf0e10cSrcweir 	pPageBreakData = pNewData;
979cdf0e10cSrcweir }
980cdf0e10cSrcweir 
981cdf0e10cSrcweir 
982cdf0e10cSrcweir 
983