1*b3f79822SAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
3*b3f79822SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
4*b3f79822SAndrew Rist * or more contributor license agreements. See the NOTICE file
5*b3f79822SAndrew Rist * distributed with this work for additional information
6*b3f79822SAndrew Rist * regarding copyright ownership. The ASF licenses this file
7*b3f79822SAndrew Rist * to you under the Apache License, Version 2.0 (the
8*b3f79822SAndrew Rist * "License"); you may not use this file except in compliance
9*b3f79822SAndrew Rist * with the License. You may obtain a copy of the License at
10*b3f79822SAndrew Rist *
11*b3f79822SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
12*b3f79822SAndrew Rist *
13*b3f79822SAndrew Rist * Unless required by applicable law or agreed to in writing,
14*b3f79822SAndrew Rist * software distributed under the License is distributed on an
15*b3f79822SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*b3f79822SAndrew Rist * KIND, either express or implied. See the License for the
17*b3f79822SAndrew Rist * specific language governing permissions and limitations
18*b3f79822SAndrew Rist * under the License.
19*b3f79822SAndrew Rist *
20*b3f79822SAndrew Rist *************************************************************/
21*b3f79822SAndrew Rist
22*b3f79822SAndrew 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 <sfx2/dispatch.hxx>
32cdf0e10cSrcweir #include <vcl/help.hxx>
33cdf0e10cSrcweir #include <tools/poly.hxx>
34cdf0e10cSrcweir #include <svtools/colorcfg.hxx>
35cdf0e10cSrcweir
36cdf0e10cSrcweir #include "scresid.hxx"
37cdf0e10cSrcweir #include "sc.hrc"
38cdf0e10cSrcweir #include "tabvwsh.hxx"
39cdf0e10cSrcweir #include "hdrcont.hxx"
40cdf0e10cSrcweir #include "scmod.hxx" // Optionen
41cdf0e10cSrcweir #include "inputopt.hxx" // Optionen
42cdf0e10cSrcweir #include "gridmerg.hxx"
43cdf0e10cSrcweir #include "document.hxx"
44cdf0e10cSrcweir
45cdf0e10cSrcweir // -----------------------------------------------------------------------
46cdf0e10cSrcweir
47cdf0e10cSrcweir #define SC_DRAG_MIN 2
48cdf0e10cSrcweir
49cdf0e10cSrcweir // passes in paint
50cdf0e10cSrcweir // (selection left/right must be first because the continuous lines
51cdf0e10cSrcweir // are partly overwritten later)
52cdf0e10cSrcweir
53cdf0e10cSrcweir #define SC_HDRPAINT_SEL_RIGHT 0
54cdf0e10cSrcweir #define SC_HDRPAINT_SEL_LEFT 1
55cdf0e10cSrcweir #define SC_HDRPAINT_TOP 2
56cdf0e10cSrcweir #define SC_HDRPAINT_SEL_TOP 3
57cdf0e10cSrcweir #define SC_HDRPAINT_SEL_BOTTOM 4
58cdf0e10cSrcweir #define SC_HDRPAINT_BOTTOM 5
59cdf0e10cSrcweir #define SC_HDRPAINT_TEXT 6
60cdf0e10cSrcweir #define SC_HDRPAINT_COUNT 7
61cdf0e10cSrcweir
62cdf0e10cSrcweir //==================================================================
63cdf0e10cSrcweir
ScHeaderControl(Window * pParent,SelectionEngine * pSelectionEngine,SCCOLROW nNewSize,sal_uInt16 nNewFlags)64cdf0e10cSrcweir ScHeaderControl::ScHeaderControl( Window* pParent, SelectionEngine* pSelectionEngine,
65cdf0e10cSrcweir SCCOLROW nNewSize, sal_uInt16 nNewFlags ) :
66cdf0e10cSrcweir Window ( pParent ),
67cdf0e10cSrcweir pSelEngine ( pSelectionEngine ),
68cdf0e10cSrcweir nFlags ( nNewFlags ),
69cdf0e10cSrcweir bVertical ( (nNewFlags & HDR_VERTICAL) != 0 ),
70cdf0e10cSrcweir nSize ( nNewSize ),
71cdf0e10cSrcweir nMarkStart ( 0 ),
72cdf0e10cSrcweir nMarkEnd ( 0 ),
73cdf0e10cSrcweir bMarkRange ( sal_False ),
74cdf0e10cSrcweir bDragging ( sal_False ),
75cdf0e10cSrcweir bIgnoreMove ( sal_False )
76cdf0e10cSrcweir {
77cdf0e10cSrcweir // --- RTL --- no default mirroring for this window, the spreadsheet itself
78cdf0e10cSrcweir // is also not mirrored
79cdf0e10cSrcweir // #107811# mirror the vertical window for correct border drawing
80cdf0e10cSrcweir // #106948# table layout depends on sheet format, not UI setting, so the
81cdf0e10cSrcweir // borders of the vertical window have to be handled manually, too.
82cdf0e10cSrcweir EnableRTL( sal_False );
83cdf0e10cSrcweir
84cdf0e10cSrcweir aNormFont = GetFont();
85cdf0e10cSrcweir aNormFont.SetTransparent( sal_True ); //! WEIGHT_NORMAL hart setzen ???
86cdf0e10cSrcweir aBoldFont = aNormFont;
87cdf0e10cSrcweir aBoldFont.SetWeight( WEIGHT_BOLD );
88cdf0e10cSrcweir
89cdf0e10cSrcweir SetFont(aBoldFont);
90cdf0e10cSrcweir bBoldSet = sal_True;
91cdf0e10cSrcweir
92cdf0e10cSrcweir Size aSize = LogicToPixel( Size(
93cdf0e10cSrcweir GetTextWidth( String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM("8888")) ),
94cdf0e10cSrcweir GetTextHeight() ) );
95cdf0e10cSrcweir aSize.Width() += 4; // Platz fuer hervorgehobene Umrandung
96cdf0e10cSrcweir aSize.Height() += 3;
97cdf0e10cSrcweir SetSizePixel( aSize );
98cdf0e10cSrcweir
99cdf0e10cSrcweir nWidth = nSmallWidth = aSize.Width();
100cdf0e10cSrcweir nBigWidth = LogicToPixel( Size( GetTextWidth(
101cdf0e10cSrcweir String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM("8888888")) ), 0 ) ).Width() + 5;
102cdf0e10cSrcweir
103cdf0e10cSrcweir SetBackground(); // sonst Probleme auf OS/2 !?!?!
104cdf0e10cSrcweir }
105cdf0e10cSrcweir
SetWidth(long nNew)106cdf0e10cSrcweir void ScHeaderControl::SetWidth( long nNew )
107cdf0e10cSrcweir {
108cdf0e10cSrcweir DBG_ASSERT( bVertical, "SetDigits nur fuer Zeilenkoepfe erlaubt" );
109cdf0e10cSrcweir if ( nNew != nWidth )
110cdf0e10cSrcweir {
111cdf0e10cSrcweir Size aSize( nNew, GetSizePixel().Height() ); // Hoehe nicht aendern
112cdf0e10cSrcweir SetSizePixel( aSize );
113cdf0e10cSrcweir
114cdf0e10cSrcweir nWidth = nNew;
115cdf0e10cSrcweir
116cdf0e10cSrcweir Invalidate(); // neu zentrieren
117cdf0e10cSrcweir }
118cdf0e10cSrcweir }
119cdf0e10cSrcweir
~ScHeaderControl()120cdf0e10cSrcweir ScHeaderControl::~ScHeaderControl()
121cdf0e10cSrcweir {
122cdf0e10cSrcweir }
123cdf0e10cSrcweir
DoPaint(SCCOLROW nStart,SCCOLROW nEnd)124cdf0e10cSrcweir void ScHeaderControl::DoPaint( SCCOLROW nStart, SCCOLROW nEnd )
125cdf0e10cSrcweir {
126cdf0e10cSrcweir sal_Bool bLayoutRTL = IsLayoutRTL();
127cdf0e10cSrcweir long nLayoutSign = bLayoutRTL ? -1 : 1;
128cdf0e10cSrcweir
129cdf0e10cSrcweir Rectangle aRect( Point(0,0), GetOutputSizePixel() );
130cdf0e10cSrcweir if ( bVertical )
131cdf0e10cSrcweir {
132cdf0e10cSrcweir aRect.Top() = GetScrPos( nStart )-nLayoutSign; // extra pixel for line at top of selection
133cdf0e10cSrcweir aRect.Bottom() = GetScrPos( nEnd+1 )-nLayoutSign;
134cdf0e10cSrcweir }
135cdf0e10cSrcweir else
136cdf0e10cSrcweir {
137cdf0e10cSrcweir aRect.Left() = GetScrPos( nStart )-nLayoutSign; // extra pixel for line left of selection
138cdf0e10cSrcweir aRect.Right() = GetScrPos( nEnd+1 )-nLayoutSign;
139cdf0e10cSrcweir }
140cdf0e10cSrcweir Invalidate(aRect);
141cdf0e10cSrcweir }
142cdf0e10cSrcweir
SetMark(sal_Bool bNewSet,SCCOLROW nNewStart,SCCOLROW nNewEnd)143cdf0e10cSrcweir void ScHeaderControl::SetMark( sal_Bool bNewSet, SCCOLROW nNewStart, SCCOLROW nNewEnd )
144cdf0e10cSrcweir {
145cdf0e10cSrcweir sal_Bool bEnabled = SC_MOD()->GetInputOptions().GetMarkHeader(); //! cachen?
146cdf0e10cSrcweir if (!bEnabled)
147cdf0e10cSrcweir bNewSet = sal_False;
148cdf0e10cSrcweir
149cdf0e10cSrcweir // Variablen setzen
150cdf0e10cSrcweir
151cdf0e10cSrcweir sal_Bool bOldSet = bMarkRange;
152cdf0e10cSrcweir SCCOLROW nOldStart = nMarkStart;
153cdf0e10cSrcweir SCCOLROW nOldEnd = nMarkEnd;
154cdf0e10cSrcweir PutInOrder( nNewStart, nNewEnd );
155cdf0e10cSrcweir bMarkRange = bNewSet;
156cdf0e10cSrcweir nMarkStart = nNewStart;
157cdf0e10cSrcweir nMarkEnd = nNewEnd;
158cdf0e10cSrcweir
159cdf0e10cSrcweir // Paint
160cdf0e10cSrcweir
161cdf0e10cSrcweir if ( bNewSet )
162cdf0e10cSrcweir {
163cdf0e10cSrcweir if ( bOldSet )
164cdf0e10cSrcweir {
165cdf0e10cSrcweir if ( nNewStart == nOldStart )
166cdf0e10cSrcweir {
167cdf0e10cSrcweir if ( nNewEnd != nOldEnd )
168cdf0e10cSrcweir DoPaint( Min( nNewEnd, nOldEnd ) + 1, Max( nNewEnd, nOldEnd ) );
169cdf0e10cSrcweir // sonst nix
170cdf0e10cSrcweir }
171cdf0e10cSrcweir else if ( nNewEnd == nOldEnd )
172cdf0e10cSrcweir DoPaint( Min( nNewStart, nOldStart ), Max( nNewStart, nOldStart ) - 1 );
173cdf0e10cSrcweir else if ( nNewStart > nOldEnd || nNewEnd < nOldStart )
174cdf0e10cSrcweir {
175cdf0e10cSrcweir // zwei Bereiche...
176cdf0e10cSrcweir DoPaint( nOldStart, nOldEnd );
177cdf0e10cSrcweir DoPaint( nNewStart, nNewEnd );
178cdf0e10cSrcweir }
179cdf0e10cSrcweir else // irgendwie ueberlappend... (kommt eh nicht oft vor)
180cdf0e10cSrcweir DoPaint( Min( nNewStart, nOldStart ), Max( nNewEnd, nOldEnd ) );
181cdf0e10cSrcweir }
182cdf0e10cSrcweir else
183cdf0e10cSrcweir DoPaint( nNewStart, nNewEnd ); // komplett neu
184cdf0e10cSrcweir }
185cdf0e10cSrcweir else if ( bOldSet )
186cdf0e10cSrcweir DoPaint( nOldStart, nOldEnd ); // komplett aufheben
187cdf0e10cSrcweir
188cdf0e10cSrcweir // sonst war nix, is nix
189cdf0e10cSrcweir }
190cdf0e10cSrcweir
GetScrPos(SCCOLROW nEntryNo)191cdf0e10cSrcweir long ScHeaderControl::GetScrPos( SCCOLROW nEntryNo )
192cdf0e10cSrcweir {
193cdf0e10cSrcweir long nScrPos;
194cdf0e10cSrcweir
195cdf0e10cSrcweir long nMax = ( bVertical ? GetOutputSizePixel().Height() : GetOutputSizePixel().Width() ) + 1;
196cdf0e10cSrcweir if (nEntryNo >= nSize)
197cdf0e10cSrcweir nScrPos = nMax;
198cdf0e10cSrcweir else
199cdf0e10cSrcweir {
200cdf0e10cSrcweir nScrPos = 0;
201cdf0e10cSrcweir for (SCCOLROW i=GetPos(); i<nEntryNo && nScrPos<nMax; i++)
202cdf0e10cSrcweir {
203cdf0e10cSrcweir sal_uInt16 nAdd = GetEntrySize(i);
204cdf0e10cSrcweir if (nAdd)
205cdf0e10cSrcweir nScrPos += nAdd;
206cdf0e10cSrcweir else
207cdf0e10cSrcweir {
208cdf0e10cSrcweir SCCOLROW nHidden = GetHiddenCount(i);
209cdf0e10cSrcweir if (nHidden > 0)
210cdf0e10cSrcweir i += nHidden - 1;
211cdf0e10cSrcweir }
212cdf0e10cSrcweir }
213cdf0e10cSrcweir }
214cdf0e10cSrcweir
215cdf0e10cSrcweir if ( IsLayoutRTL() )
216cdf0e10cSrcweir nScrPos = nMax - nScrPos - 2;
217cdf0e10cSrcweir
218cdf0e10cSrcweir return nScrPos;
219cdf0e10cSrcweir }
220cdf0e10cSrcweir
221cdf0e10cSrcweir // draw a rectangle across the window's width/height, with the outer part in a lighter color
222cdf0e10cSrcweir
DrawShadedRect(long nStart,long nEnd,const Color & rBaseColor)223cdf0e10cSrcweir void ScHeaderControl::DrawShadedRect( long nStart, long nEnd, const Color& rBaseColor )
224cdf0e10cSrcweir {
225cdf0e10cSrcweir Color aWhite( COL_WHITE );
226cdf0e10cSrcweir
227cdf0e10cSrcweir Color aInner( rBaseColor ); // highlight color, unchanged
228cdf0e10cSrcweir Color aCenter( rBaseColor );
229cdf0e10cSrcweir aCenter.Merge( aWhite, 0xd0 ); // lighten up a bit
230cdf0e10cSrcweir Color aOuter( rBaseColor );
231cdf0e10cSrcweir aOuter.Merge( aWhite, 0xa0 ); // lighten up more
232cdf0e10cSrcweir
233cdf0e10cSrcweir if ( IsMirrored() )
234cdf0e10cSrcweir std::swap( aInner, aOuter ); // just swap colors instead of positions
235cdf0e10cSrcweir
236cdf0e10cSrcweir Size aWinSize = GetSizePixel();
237cdf0e10cSrcweir long nBarSize = bVertical ? aWinSize.Width() : aWinSize.Height();
238cdf0e10cSrcweir long nCenterPos = (nBarSize / 2) - 1;
239cdf0e10cSrcweir
240cdf0e10cSrcweir SetLineColor();
241cdf0e10cSrcweir SetFillColor( aOuter );
242cdf0e10cSrcweir if (bVertical)
243cdf0e10cSrcweir DrawRect( Rectangle( 0, nStart, nCenterPos-1, nEnd ) );
244cdf0e10cSrcweir else
245cdf0e10cSrcweir DrawRect( Rectangle( nStart, 0, nEnd, nCenterPos-1 ) );
246cdf0e10cSrcweir SetFillColor( aCenter );
247cdf0e10cSrcweir if (bVertical)
248cdf0e10cSrcweir DrawRect( Rectangle( nCenterPos, nStart, nCenterPos, nEnd ) );
249cdf0e10cSrcweir else
250cdf0e10cSrcweir DrawRect( Rectangle( nStart, nCenterPos, nEnd, nCenterPos ) );
251cdf0e10cSrcweir SetFillColor( aInner );
252cdf0e10cSrcweir if (bVertical)
253cdf0e10cSrcweir DrawRect( Rectangle( nCenterPos+1, nStart, nBarSize-1, nEnd ) );
254cdf0e10cSrcweir else
255cdf0e10cSrcweir DrawRect( Rectangle( nStart, nCenterPos+1, nEnd, nBarSize-1 ) );
256cdf0e10cSrcweir }
257cdf0e10cSrcweir
258cdf0e10cSrcweir //
259cdf0e10cSrcweir // Paint
260cdf0e10cSrcweir //
261cdf0e10cSrcweir
Paint(const Rectangle & rRect)262cdf0e10cSrcweir void ScHeaderControl::Paint( const Rectangle& rRect )
263cdf0e10cSrcweir {
264cdf0e10cSrcweir // fuer VCL ist es wichtig, wenig Aufrufe zu haben, darum werden die aeusseren
265cdf0e10cSrcweir // Linien zusammengefasst
266cdf0e10cSrcweir
267cdf0e10cSrcweir const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings();
268cdf0e10cSrcweir sal_Bool bHighContrast = rStyleSettings.GetHighContrastMode();
269cdf0e10cSrcweir sal_Bool bDark = rStyleSettings.GetFaceColor().IsDark();
270cdf0e10cSrcweir // Use the same distinction for bDark as in Window::DrawSelectionBackground
271cdf0e10cSrcweir
272cdf0e10cSrcweir Color aTextColor = rStyleSettings.GetButtonTextColor();
273cdf0e10cSrcweir Color aSelTextColor = rStyleSettings.GetHighlightTextColor();
274cdf0e10cSrcweir aNormFont.SetColor( aTextColor );
275cdf0e10cSrcweir if ( bHighContrast )
276cdf0e10cSrcweir aBoldFont.SetColor( aTextColor );
277cdf0e10cSrcweir else
278cdf0e10cSrcweir aBoldFont.SetColor( aSelTextColor );
279cdf0e10cSrcweir SetTextColor( ( bBoldSet && !bHighContrast ) ? aSelTextColor : aTextColor );
280cdf0e10cSrcweir
281cdf0e10cSrcweir Color aBlack( COL_BLACK );
282cdf0e10cSrcweir Color aSelLineColor = rStyleSettings.GetHighlightColor();
283cdf0e10cSrcweir aSelLineColor.Merge( aBlack, 0xe0 ); // darken just a little bit
284cdf0e10cSrcweir
285cdf0e10cSrcweir sal_Bool bLayoutRTL = IsLayoutRTL();
286cdf0e10cSrcweir long nLayoutSign = bLayoutRTL ? -1 : 1;
287cdf0e10cSrcweir sal_Bool bMirrored = IsMirrored();
288cdf0e10cSrcweir
289cdf0e10cSrcweir // const FunctionSet* pFuncSet = pSelEngine->GetFunctionSet();
290cdf0e10cSrcweir String aString;
291cdf0e10cSrcweir sal_uInt16 nBarSize;
292cdf0e10cSrcweir Point aScrPos;
293cdf0e10cSrcweir Size aTextSize;
294cdf0e10cSrcweir // Size aSize = GetOutputSizePixel();
295cdf0e10cSrcweir
296cdf0e10cSrcweir if (bVertical)
297cdf0e10cSrcweir nBarSize = (sal_uInt16) GetSizePixel().Width();
298cdf0e10cSrcweir else
299cdf0e10cSrcweir nBarSize = (sal_uInt16) GetSizePixel().Height();
300cdf0e10cSrcweir
301cdf0e10cSrcweir SCCOLROW nPos = GetPos();
302cdf0e10cSrcweir
303cdf0e10cSrcweir long nPStart = bVertical ? rRect.Top() : rRect.Left();
304cdf0e10cSrcweir long nPEnd = bVertical ? rRect.Bottom() : rRect.Right();
305cdf0e10cSrcweir
306cdf0e10cSrcweir long nTransStart = nPEnd + 1;
307cdf0e10cSrcweir long nTransEnd = 0;
308cdf0e10cSrcweir
309cdf0e10cSrcweir long nInitScrPos = 0;
310cdf0e10cSrcweir if ( bLayoutRTL )
311cdf0e10cSrcweir {
312cdf0e10cSrcweir long nTemp = nPStart; // swap nPStart / nPEnd
313cdf0e10cSrcweir nPStart = nPEnd;
314cdf0e10cSrcweir nPEnd = nTemp;
315cdf0e10cSrcweir nTemp = nTransStart; // swap nTransStart / nTransEnd
316cdf0e10cSrcweir nTransStart = nTransEnd;
317cdf0e10cSrcweir nTransEnd = nTemp;
318cdf0e10cSrcweir if ( bVertical ) // start loops from the end
319cdf0e10cSrcweir nInitScrPos = GetSizePixel().Height() - 1;
320cdf0e10cSrcweir else
321cdf0e10cSrcweir nInitScrPos = GetSizePixel().Width() - 1;
322cdf0e10cSrcweir }
323cdf0e10cSrcweir
324cdf0e10cSrcweir // aeussere Linien komplett durchzeichnen
325cdf0e10cSrcweir // Zuerst Ende der letzten Zelle finden
326cdf0e10cSrcweir
327cdf0e10cSrcweir // long nLineEnd = -1;
328cdf0e10cSrcweir long nLineEnd = nInitScrPos - nLayoutSign;
329cdf0e10cSrcweir
330cdf0e10cSrcweir for (SCCOLROW i=nPos; i<nSize; i++)
331cdf0e10cSrcweir {
332cdf0e10cSrcweir sal_uInt16 nSizePix = GetEntrySize( i );
333cdf0e10cSrcweir if (nSizePix)
334cdf0e10cSrcweir {
335cdf0e10cSrcweir nLineEnd += nSizePix * nLayoutSign;
336cdf0e10cSrcweir
337cdf0e10cSrcweir if ( bMarkRange && i >= nMarkStart && i <= nMarkEnd )
338cdf0e10cSrcweir {
339cdf0e10cSrcweir long nLineStart = nLineEnd - ( nSizePix - 1 ) * nLayoutSign;
340cdf0e10cSrcweir if ( nLineStart * nLayoutSign < nTransStart * nLayoutSign )
341cdf0e10cSrcweir nTransStart = nLineStart;
342cdf0e10cSrcweir if ( nLineEnd * nLayoutSign > nTransEnd * nLayoutSign )
343cdf0e10cSrcweir nTransEnd = nLineEnd;
344cdf0e10cSrcweir }
345cdf0e10cSrcweir
346cdf0e10cSrcweir if ( nLineEnd * nLayoutSign > nPEnd * nLayoutSign )
347cdf0e10cSrcweir {
348cdf0e10cSrcweir nLineEnd = nPEnd;
349cdf0e10cSrcweir break;
350cdf0e10cSrcweir }
351cdf0e10cSrcweir }
352cdf0e10cSrcweir else
353cdf0e10cSrcweir {
354cdf0e10cSrcweir SCCOLROW nHidden = GetHiddenCount(i);
355cdf0e10cSrcweir if (nHidden > 0)
356cdf0e10cSrcweir i += nHidden - 1;
357cdf0e10cSrcweir }
358cdf0e10cSrcweir }
359cdf0e10cSrcweir
360cdf0e10cSrcweir // background is different for entry area and behind the entries
361cdf0e10cSrcweir
362cdf0e10cSrcweir Rectangle aFillRect;
363cdf0e10cSrcweir SetLineColor();
364cdf0e10cSrcweir
365cdf0e10cSrcweir if ( nLineEnd * nLayoutSign >= nInitScrPos * nLayoutSign )
366cdf0e10cSrcweir {
367cdf0e10cSrcweir if ( bHighContrast )
368cdf0e10cSrcweir {
369cdf0e10cSrcweir // high contrast: single-color background
370cdf0e10cSrcweir SetFillColor( rStyleSettings.GetFaceColor() );
371cdf0e10cSrcweir if ( bVertical )
372cdf0e10cSrcweir aFillRect = Rectangle( 0, nInitScrPos, nBarSize-1, nLineEnd );
373cdf0e10cSrcweir else
374cdf0e10cSrcweir aFillRect = Rectangle( nInitScrPos, 0, nLineEnd, nBarSize-1 );
375cdf0e10cSrcweir DrawRect( aFillRect );
376cdf0e10cSrcweir }
377cdf0e10cSrcweir else
378cdf0e10cSrcweir {
379cdf0e10cSrcweir // normal: 3-part background
380cdf0e10cSrcweir DrawShadedRect( nInitScrPos, nLineEnd, rStyleSettings.GetFaceColor() );
381cdf0e10cSrcweir }
382cdf0e10cSrcweir }
383cdf0e10cSrcweir
384cdf0e10cSrcweir if ( nLineEnd * nLayoutSign < nPEnd * nLayoutSign )
385cdf0e10cSrcweir {
386cdf0e10cSrcweir SetFillColor( SC_MOD()->GetColorConfig().GetColorValue(svtools::APPBACKGROUND).nColor );
387cdf0e10cSrcweir if ( bVertical )
388cdf0e10cSrcweir aFillRect = Rectangle( 0, nLineEnd+nLayoutSign, nBarSize-1, nPEnd );
389cdf0e10cSrcweir else
390cdf0e10cSrcweir aFillRect = Rectangle( nLineEnd+nLayoutSign, 0, nPEnd, nBarSize-1 );
391cdf0e10cSrcweir DrawRect( aFillRect );
392cdf0e10cSrcweir }
393cdf0e10cSrcweir
394cdf0e10cSrcweir if ( nLineEnd * nLayoutSign >= nPStart * nLayoutSign )
395cdf0e10cSrcweir {
396cdf0e10cSrcweir if ( nTransEnd * nLayoutSign >= nTransStart * nLayoutSign )
397cdf0e10cSrcweir {
398cdf0e10cSrcweir if ( bHighContrast )
399cdf0e10cSrcweir {
400cdf0e10cSrcweir if ( bDark )
401cdf0e10cSrcweir {
402cdf0e10cSrcweir // solid grey background for dark face color is drawn before lines
403cdf0e10cSrcweir
404cdf0e10cSrcweir SetLineColor();
405cdf0e10cSrcweir SetFillColor( COL_LIGHTGRAY );
406cdf0e10cSrcweir if (bVertical)
407cdf0e10cSrcweir DrawRect( Rectangle( 0, nTransStart, nBarSize-1, nTransEnd ) );
408cdf0e10cSrcweir else
409cdf0e10cSrcweir DrawRect( Rectangle( nTransStart, 0, nTransEnd, nBarSize-1 ) );
410cdf0e10cSrcweir }
411cdf0e10cSrcweir }
412cdf0e10cSrcweir else
413cdf0e10cSrcweir {
414cdf0e10cSrcweir // background for selection
415cdf0e10cSrcweir
416cdf0e10cSrcweir DrawShadedRect( nTransStart, nTransEnd, rStyleSettings.GetHighlightColor() );
417cdf0e10cSrcweir }
418cdf0e10cSrcweir }
419cdf0e10cSrcweir
420cdf0e10cSrcweir #if 0
421cdf0e10cSrcweir // 3D border is no longer used
422cdf0e10cSrcweir SetLineColor( rStyleSettings.GetLightColor() );
423cdf0e10cSrcweir if (bVertical)
424cdf0e10cSrcweir DrawLine( Point( 0, nPStart ), Point( 0, nLineEnd ) );
425cdf0e10cSrcweir else
426cdf0e10cSrcweir DrawLine( Point( nPStart, 0 ), Point( nLineEnd, 0 ) );
427cdf0e10cSrcweir #endif
428cdf0e10cSrcweir
429cdf0e10cSrcweir SetLineColor( rStyleSettings.GetDarkShadowColor() );
430cdf0e10cSrcweir if (bVertical)
431cdf0e10cSrcweir {
432cdf0e10cSrcweir long nDarkPos = bMirrored ? 0 : nBarSize-1;
433cdf0e10cSrcweir DrawLine( Point( nDarkPos, nPStart ), Point( nDarkPos, nLineEnd ) );
434cdf0e10cSrcweir }
435cdf0e10cSrcweir else
436cdf0e10cSrcweir DrawLine( Point( nPStart, nBarSize-1 ), Point( nLineEnd, nBarSize-1 ) );
437cdf0e10cSrcweir
438cdf0e10cSrcweir // line in different color for selection
439cdf0e10cSrcweir if ( nTransEnd * nLayoutSign >= nTransStart * nLayoutSign && !bHighContrast )
440cdf0e10cSrcweir {
441cdf0e10cSrcweir SetLineColor( aSelLineColor );
442cdf0e10cSrcweir if (bVertical)
443cdf0e10cSrcweir {
444cdf0e10cSrcweir long nDarkPos = bMirrored ? 0 : nBarSize-1;
445cdf0e10cSrcweir DrawLine( Point( nDarkPos, nTransStart ), Point( nDarkPos, nTransEnd ) );
446cdf0e10cSrcweir }
447cdf0e10cSrcweir else
448cdf0e10cSrcweir DrawLine( Point( nTransStart, nBarSize-1 ), Point( nTransEnd, nBarSize-1 ) );
449cdf0e10cSrcweir }
450cdf0e10cSrcweir }
451cdf0e10cSrcweir
452cdf0e10cSrcweir //
453cdf0e10cSrcweir // loop through entries several times to avoid changing the line color too often
454cdf0e10cSrcweir // and to allow merging of lines
455cdf0e10cSrcweir //
456cdf0e10cSrcweir
457cdf0e10cSrcweir ScGridMerger aGrid( this, 1, 1 );
458cdf0e10cSrcweir
459cdf0e10cSrcweir // start at SC_HDRPAINT_BOTTOM instead of 0 - selection doesn't get different
460cdf0e10cSrcweir // borders, light border at top isn't used anymore
461cdf0e10cSrcweir // use SC_HDRPAINT_SEL_BOTTOM for different color
462cdf0e10cSrcweir
463cdf0e10cSrcweir for (sal_uInt16 nPass = SC_HDRPAINT_SEL_BOTTOM; nPass < SC_HDRPAINT_COUNT; nPass++)
464cdf0e10cSrcweir {
465cdf0e10cSrcweir // set line color etc. before entry loop
466cdf0e10cSrcweir switch ( nPass )
467cdf0e10cSrcweir {
468cdf0e10cSrcweir case SC_HDRPAINT_SEL_BOTTOM:
469cdf0e10cSrcweir // same as non-selected for high contrast
470cdf0e10cSrcweir SetLineColor( bHighContrast ? rStyleSettings.GetDarkShadowColor() : aSelLineColor );
471cdf0e10cSrcweir break;
472cdf0e10cSrcweir case SC_HDRPAINT_BOTTOM:
473cdf0e10cSrcweir SetLineColor( rStyleSettings.GetDarkShadowColor() );
474cdf0e10cSrcweir break;
475cdf0e10cSrcweir case SC_HDRPAINT_TEXT:
476cdf0e10cSrcweir // DrawSelectionBackground is used only for high contrast on light background
477cdf0e10cSrcweir if ( nTransEnd * nLayoutSign >= nTransStart * nLayoutSign && bHighContrast && !bDark )
478cdf0e10cSrcweir {
479cdf0e10cSrcweir // Transparent selection background is drawn after lines, before text.
480cdf0e10cSrcweir // #109814# Use DrawSelectionBackground to make sure there is a visible
481cdf0e10cSrcweir // difference. The case of a dark face color, where DrawSelectionBackground
482cdf0e10cSrcweir // would just paint over the lines, is handled separately (bDark).
483cdf0e10cSrcweir // Otherwise, GetHighlightColor is used with 80% transparency.
484cdf0e10cSrcweir // The window's background color (SetBackground) has to be the background
485cdf0e10cSrcweir // of the cell area, for the contrast comparison in DrawSelectionBackground.
486cdf0e10cSrcweir
487cdf0e10cSrcweir Rectangle aTransRect;
488cdf0e10cSrcweir if (bVertical)
489cdf0e10cSrcweir aTransRect = Rectangle( 0, nTransStart, nBarSize-1, nTransEnd );
490cdf0e10cSrcweir else
491cdf0e10cSrcweir aTransRect = Rectangle( nTransStart, 0, nTransEnd, nBarSize-1 );
492cdf0e10cSrcweir SetBackground( Color( rStyleSettings.GetFaceColor() ) );
493cdf0e10cSrcweir DrawSelectionBackground( aTransRect, 0, sal_True, sal_False, sal_False );
494cdf0e10cSrcweir SetBackground();
495cdf0e10cSrcweir }
496cdf0e10cSrcweir break;
497cdf0e10cSrcweir }
498cdf0e10cSrcweir
499cdf0e10cSrcweir SCCOLROW nCount=0;
500cdf0e10cSrcweir long nScrPos=nInitScrPos;
501cdf0e10cSrcweir do
502cdf0e10cSrcweir {
503cdf0e10cSrcweir if (bVertical)
504cdf0e10cSrcweir aScrPos = Point( 0, nScrPos );
505cdf0e10cSrcweir else
506cdf0e10cSrcweir aScrPos = Point( nScrPos, 0 );
507cdf0e10cSrcweir
508cdf0e10cSrcweir SCCOLROW nEntryNo = nCount + nPos;
509cdf0e10cSrcweir if ( nEntryNo >= nSize ) // MAXCOL/MAXROW
510cdf0e10cSrcweir nScrPos = nPEnd + nLayoutSign; // beyond nPEnd -> stop
511cdf0e10cSrcweir else
512cdf0e10cSrcweir {
513cdf0e10cSrcweir sal_uInt16 nSizePix = GetEntrySize( nEntryNo );
514cdf0e10cSrcweir
515cdf0e10cSrcweir if (nSizePix == 0)
516cdf0e10cSrcweir {
517cdf0e10cSrcweir SCCOLROW nHidden = GetHiddenCount(nEntryNo);
518cdf0e10cSrcweir if (nHidden > 0)
519cdf0e10cSrcweir nCount += nHidden - 1;
520cdf0e10cSrcweir }
521cdf0e10cSrcweir else if ((nScrPos+nSizePix*nLayoutSign)*nLayoutSign >= nPStart*nLayoutSign)
522cdf0e10cSrcweir {
523cdf0e10cSrcweir Point aEndPos(aScrPos);
524cdf0e10cSrcweir if (bVertical)
525cdf0e10cSrcweir aEndPos = Point( aScrPos.X()+nBarSize-1, aScrPos.Y()+(nSizePix-1)*nLayoutSign );
526cdf0e10cSrcweir else
527cdf0e10cSrcweir aEndPos = Point( aScrPos.X()+(nSizePix-1)*nLayoutSign, aScrPos.Y()+nBarSize-1 );
528cdf0e10cSrcweir
529cdf0e10cSrcweir sal_Bool bMark = bMarkRange && nEntryNo >= nMarkStart && nEntryNo <= nMarkEnd;
530cdf0e10cSrcweir sal_Bool bNextToMark = bMarkRange && nEntryNo + 1 >= nMarkStart && nEntryNo <= nMarkEnd;
531cdf0e10cSrcweir
532cdf0e10cSrcweir switch ( nPass )
533cdf0e10cSrcweir {
534cdf0e10cSrcweir case SC_HDRPAINT_SEL_BOTTOM:
535cdf0e10cSrcweir case SC_HDRPAINT_BOTTOM:
536cdf0e10cSrcweir if ( nPass == ( bNextToMark ? SC_HDRPAINT_SEL_BOTTOM : SC_HDRPAINT_BOTTOM ) )
537cdf0e10cSrcweir {
538cdf0e10cSrcweir if (bVertical)
539cdf0e10cSrcweir aGrid.AddHorLine( aScrPos.X(), aEndPos.X(), aEndPos.Y() );
540cdf0e10cSrcweir else
541cdf0e10cSrcweir aGrid.AddVerLine( aEndPos.X(), aScrPos.Y(), aEndPos.Y() );
542cdf0e10cSrcweir
543cdf0e10cSrcweir // thick bottom for hidden rows
544cdf0e10cSrcweir // (drawn directly, without aGrid)
545cdf0e10cSrcweir if ( nEntryNo+1 < nSize )
546cdf0e10cSrcweir if ( GetEntrySize(nEntryNo+1)==0 )
547cdf0e10cSrcweir {
548cdf0e10cSrcweir if (bVertical)
549cdf0e10cSrcweir DrawLine( Point(aScrPos.X(),aEndPos.Y()-nLayoutSign),
550cdf0e10cSrcweir Point(aEndPos.X(),aEndPos.Y()-nLayoutSign) );
551cdf0e10cSrcweir else
552cdf0e10cSrcweir DrawLine( Point(aEndPos.X()-nLayoutSign,aScrPos.Y()),
553cdf0e10cSrcweir Point(aEndPos.X()-nLayoutSign,aEndPos.Y()) );
554cdf0e10cSrcweir }
555cdf0e10cSrcweir }
556cdf0e10cSrcweir break;
557cdf0e10cSrcweir
558cdf0e10cSrcweir case SC_HDRPAINT_TEXT:
559cdf0e10cSrcweir if ( nSizePix > 1 ) // minimal check for small columns/rows
560cdf0e10cSrcweir {
561cdf0e10cSrcweir if ( bMark != bBoldSet )
562cdf0e10cSrcweir {
563cdf0e10cSrcweir if (bMark)
564cdf0e10cSrcweir SetFont(aBoldFont);
565cdf0e10cSrcweir else
566cdf0e10cSrcweir SetFont(aNormFont);
567cdf0e10cSrcweir bBoldSet = bMark;
568cdf0e10cSrcweir }
569cdf0e10cSrcweir aString = GetEntryText( nEntryNo );
570cdf0e10cSrcweir aTextSize.Width() = GetTextWidth( aString );
571cdf0e10cSrcweir aTextSize.Height() = GetTextHeight();
572cdf0e10cSrcweir
573cdf0e10cSrcweir Point aTxtPos(aScrPos);
574cdf0e10cSrcweir if (bVertical)
575cdf0e10cSrcweir {
576cdf0e10cSrcweir aTxtPos.X() += (nBarSize-aTextSize.Width())/2;
577cdf0e10cSrcweir aTxtPos.Y() += (nSizePix*nLayoutSign-aTextSize.Height())/2;
578cdf0e10cSrcweir if ( bMirrored )
579cdf0e10cSrcweir aTxtPos.X() += 1; // dark border is left instead of right
580cdf0e10cSrcweir }
581cdf0e10cSrcweir else
582cdf0e10cSrcweir {
583cdf0e10cSrcweir aTxtPos.X() += (nSizePix*nLayoutSign-aTextSize.Width()+1)/2;
584cdf0e10cSrcweir aTxtPos.Y() += (nBarSize-aTextSize.Height())/2;
585cdf0e10cSrcweir }
586cdf0e10cSrcweir DrawText( aTxtPos, aString );
587cdf0e10cSrcweir }
588cdf0e10cSrcweir break;
589cdf0e10cSrcweir }
590cdf0e10cSrcweir
591cdf0e10cSrcweir // bei Selektion der ganzen Zeile/Spalte:
592cdf0e10cSrcweir // InvertRect( Rectangle( aScrPos, aEndPos ) );
593cdf0e10cSrcweir }
594cdf0e10cSrcweir nScrPos += nSizePix * nLayoutSign; // also if before the visible area
595cdf0e10cSrcweir }
596cdf0e10cSrcweir ++nCount;
597cdf0e10cSrcweir }
598cdf0e10cSrcweir while ( nScrPos * nLayoutSign <= nPEnd * nLayoutSign );
599cdf0e10cSrcweir
600cdf0e10cSrcweir aGrid.Flush();
601cdf0e10cSrcweir }
602cdf0e10cSrcweir }
603cdf0e10cSrcweir
604cdf0e10cSrcweir //
605cdf0e10cSrcweir // Maus - Handling
606cdf0e10cSrcweir //
607cdf0e10cSrcweir
GetMousePos(const MouseEvent & rMEvt,sal_Bool & rBorder)608cdf0e10cSrcweir SCCOLROW ScHeaderControl::GetMousePos( const MouseEvent& rMEvt, sal_Bool& rBorder )
609cdf0e10cSrcweir {
610cdf0e10cSrcweir sal_Bool bFound=sal_False;
611cdf0e10cSrcweir SCCOLROW nCount = 1;
612cdf0e10cSrcweir SCCOLROW nPos = GetPos();
613cdf0e10cSrcweir SCCOLROW nHitNo = nPos;
614cdf0e10cSrcweir long nScrPos;
615cdf0e10cSrcweir long nMousePos = bVertical ? rMEvt.GetPosPixel().Y() : rMEvt.GetPosPixel().X();
616cdf0e10cSrcweir long nDif;
617cdf0e10cSrcweir Size aSize = GetOutputSizePixel();
618cdf0e10cSrcweir long nWinSize = bVertical ? aSize.Height() : aSize.Width();
619cdf0e10cSrcweir
620cdf0e10cSrcweir sal_Bool bLayoutRTL = IsLayoutRTL();
621cdf0e10cSrcweir long nLayoutSign = bLayoutRTL ? -1 : 1;
622cdf0e10cSrcweir long nEndPos = bLayoutRTL ? -1 : nWinSize;
623cdf0e10cSrcweir
624cdf0e10cSrcweir nScrPos = GetScrPos( nPos ) - nLayoutSign;
625cdf0e10cSrcweir do
626cdf0e10cSrcweir {
627cdf0e10cSrcweir SCCOLROW nEntryNo = nCount + nPos;
628cdf0e10cSrcweir
629cdf0e10cSrcweir // nScrPos = GetScrPos( nEntryNo ) - 1;
630cdf0e10cSrcweir
631cdf0e10cSrcweir if (nEntryNo > nSize)
632cdf0e10cSrcweir nScrPos = nEndPos + nLayoutSign;
633cdf0e10cSrcweir else
634cdf0e10cSrcweir nScrPos += GetEntrySize( nEntryNo - 1 ) * nLayoutSign; //! GetHiddenCount() ??
635cdf0e10cSrcweir
636cdf0e10cSrcweir nDif = nMousePos - nScrPos;
637cdf0e10cSrcweir if (nDif >= -2 && nDif <= 2 && nCount > 0)
638cdf0e10cSrcweir {
639cdf0e10cSrcweir bFound=sal_True;
640cdf0e10cSrcweir nHitNo=nEntryNo-1;
641cdf0e10cSrcweir }
642cdf0e10cSrcweir else if (nDif * nLayoutSign >= 0 && nEntryNo < nSize)
643cdf0e10cSrcweir nHitNo = nEntryNo;
644cdf0e10cSrcweir ++nCount;
645cdf0e10cSrcweir }
646cdf0e10cSrcweir while ( nScrPos * nLayoutSign < nEndPos * nLayoutSign && nDif * nLayoutSign > 0 );
647cdf0e10cSrcweir
648cdf0e10cSrcweir rBorder = bFound;
649cdf0e10cSrcweir return nHitNo;
650cdf0e10cSrcweir }
651cdf0e10cSrcweir
IsSelectionAllowed(SCCOLROW nPos) const652cdf0e10cSrcweir bool ScHeaderControl::IsSelectionAllowed(SCCOLROW nPos) const
653cdf0e10cSrcweir {
654cdf0e10cSrcweir ScTabViewShell* pViewSh = dynamic_cast<ScTabViewShell*>(SfxViewShell::Current());
655cdf0e10cSrcweir if (!pViewSh)
656cdf0e10cSrcweir return false;
657cdf0e10cSrcweir
658cdf0e10cSrcweir ScViewData* pViewData = pViewSh->GetViewData();
659cdf0e10cSrcweir sal_uInt16 nTab = pViewData->GetTabNo();
660cdf0e10cSrcweir ScDocument* pDoc = pViewData->GetDocument();
661cdf0e10cSrcweir const ScTableProtection* pProtect = pDoc->GetTabProtection(nTab);
662cdf0e10cSrcweir bool bSelectAllowed = true;
663cdf0e10cSrcweir if ( pProtect && pProtect->isProtected() )
664cdf0e10cSrcweir {
665cdf0e10cSrcweir // This sheet is protected. Check if a context menu is allowed on this cell.
666cdf0e10cSrcweir bool bCellsProtected = false;
667cdf0e10cSrcweir if (bVertical)
668cdf0e10cSrcweir {
669cdf0e10cSrcweir // row header
670cdf0e10cSrcweir SCROW nRPos = static_cast<SCROW>(nPos);
671cdf0e10cSrcweir bCellsProtected = pDoc->HasAttrib(0, nRPos, nTab, MAXCOL, nRPos, nTab, HASATTR_PROTECTED);
672cdf0e10cSrcweir }
673cdf0e10cSrcweir else
674cdf0e10cSrcweir {
675cdf0e10cSrcweir // column header
676cdf0e10cSrcweir SCCOL nCPos = static_cast<SCCOL>(nPos);
677cdf0e10cSrcweir bCellsProtected = pDoc->HasAttrib(nCPos, 0, nTab, nCPos, MAXROW, nTab, HASATTR_PROTECTED);
678cdf0e10cSrcweir }
679cdf0e10cSrcweir
680cdf0e10cSrcweir bool bSelProtected = pProtect->isOptionEnabled(ScTableProtection::SELECT_LOCKED_CELLS);
681cdf0e10cSrcweir bool bSelUnprotected = pProtect->isOptionEnabled(ScTableProtection::SELECT_UNLOCKED_CELLS);
682cdf0e10cSrcweir
683cdf0e10cSrcweir if (bCellsProtected)
684cdf0e10cSrcweir bSelectAllowed = bSelProtected;
685cdf0e10cSrcweir else
686cdf0e10cSrcweir bSelectAllowed = bSelUnprotected;
687cdf0e10cSrcweir }
688cdf0e10cSrcweir return bSelectAllowed;
689cdf0e10cSrcweir }
690cdf0e10cSrcweir
MouseButtonDown(const MouseEvent & rMEvt)691cdf0e10cSrcweir void ScHeaderControl::MouseButtonDown( const MouseEvent& rMEvt )
692cdf0e10cSrcweir {
693cdf0e10cSrcweir if (IsDisabled())
694cdf0e10cSrcweir return;
695cdf0e10cSrcweir
696cdf0e10cSrcweir bIgnoreMove = sal_False;
697cdf0e10cSrcweir SelectWindow();
698cdf0e10cSrcweir
699cdf0e10cSrcweir sal_Bool bFound;
700cdf0e10cSrcweir SCCOLROW nHitNo = GetMousePos( rMEvt, bFound );
701cdf0e10cSrcweir if (!IsSelectionAllowed(nHitNo))
702cdf0e10cSrcweir return;
703cdf0e10cSrcweir
704cdf0e10cSrcweir if ( bFound && rMEvt.IsLeft() && ResizeAllowed() )
705cdf0e10cSrcweir {
706cdf0e10cSrcweir nDragNo = nHitNo;
707cdf0e10cSrcweir sal_uInt16 nClicks = rMEvt.GetClicks();
708cdf0e10cSrcweir if ( nClicks && nClicks%2==0 )
709cdf0e10cSrcweir {
710cdf0e10cSrcweir SetEntrySize( nDragNo, HDR_SIZE_OPTIMUM );
711cdf0e10cSrcweir SetPointer( Pointer( POINTER_ARROW ) );
712cdf0e10cSrcweir }
713cdf0e10cSrcweir else
714cdf0e10cSrcweir {
715cdf0e10cSrcweir if (bVertical)
716cdf0e10cSrcweir nDragStart = rMEvt.GetPosPixel().Y();
717cdf0e10cSrcweir else
718cdf0e10cSrcweir nDragStart = rMEvt.GetPosPixel().X();
719cdf0e10cSrcweir nDragPos = nDragStart;
720cdf0e10cSrcweir ShowDragHelp();
721cdf0e10cSrcweir DrawInvert( nDragPos );
722cdf0e10cSrcweir
723cdf0e10cSrcweir // CaptureMouse();
724cdf0e10cSrcweir StartTracking();
725cdf0e10cSrcweir bDragging = sal_True;
726cdf0e10cSrcweir bDragMoved = sal_False;
727cdf0e10cSrcweir }
728cdf0e10cSrcweir }
729cdf0e10cSrcweir else if (rMEvt.IsLeft())
730cdf0e10cSrcweir {
731cdf0e10cSrcweir pSelEngine->SetWindow( this );
732cdf0e10cSrcweir Point aPoint;
733cdf0e10cSrcweir Rectangle aVis( aPoint,GetOutputSizePixel() );
734cdf0e10cSrcweir if (bVertical)
735cdf0e10cSrcweir aVis.Left() = LONG_MIN, aVis.Right() = LONG_MAX;
736cdf0e10cSrcweir else
737cdf0e10cSrcweir aVis.Top() = LONG_MIN, aVis.Bottom() = LONG_MAX;
738cdf0e10cSrcweir pSelEngine->SetVisibleArea( aVis );
739cdf0e10cSrcweir
740cdf0e10cSrcweir SetMarking( sal_True ); // muss vor SelMouseButtonDown sein
741cdf0e10cSrcweir pSelEngine->SelMouseButtonDown( rMEvt );
742cdf0e10cSrcweir
743cdf0e10cSrcweir // #74215# In column/row headers a simple click already is a selection.
744cdf0e10cSrcweir // -> Call SelMouseMove to ensure CreateAnchor is called (and DestroyAnchor
745cdf0e10cSrcweir // if the next click is somewhere else with Control key).
746cdf0e10cSrcweir pSelEngine->SelMouseMove( rMEvt );
747cdf0e10cSrcweir
748cdf0e10cSrcweir if (IsMouseCaptured())
749cdf0e10cSrcweir {
750cdf0e10cSrcweir // Tracking statt CaptureMouse, damit sauber abgebrochen werden kann
751cdf0e10cSrcweir //! Irgendwann sollte die SelectionEngine selber StartTracking rufen!?!
752cdf0e10cSrcweir ReleaseMouse();
753cdf0e10cSrcweir StartTracking();
754cdf0e10cSrcweir }
755cdf0e10cSrcweir }
756cdf0e10cSrcweir }
757cdf0e10cSrcweir
MouseButtonUp(const MouseEvent & rMEvt)758cdf0e10cSrcweir void ScHeaderControl::MouseButtonUp( const MouseEvent& rMEvt )
759cdf0e10cSrcweir {
760cdf0e10cSrcweir if ( IsDisabled() )
761cdf0e10cSrcweir return;
762cdf0e10cSrcweir
763cdf0e10cSrcweir SetMarking( sal_False );
764cdf0e10cSrcweir bIgnoreMove = sal_False;
765cdf0e10cSrcweir // sal_Bool bFound;
766cdf0e10cSrcweir // SCCOLROW nHitNo = GetMousePos( rMEvt, bFound );
767cdf0e10cSrcweir
768cdf0e10cSrcweir if ( bDragging )
769cdf0e10cSrcweir {
770cdf0e10cSrcweir DrawInvert( nDragPos );
771cdf0e10cSrcweir ReleaseMouse();
772cdf0e10cSrcweir bDragging = sal_False;
773cdf0e10cSrcweir
774cdf0e10cSrcweir long nScrPos = GetScrPos( nDragNo );
775cdf0e10cSrcweir long nMousePos = bVertical ? rMEvt.GetPosPixel().Y() : rMEvt.GetPosPixel().X();
776cdf0e10cSrcweir sal_Bool bLayoutRTL = IsLayoutRTL();
777cdf0e10cSrcweir long nNewWidth = bLayoutRTL ? ( nScrPos - nMousePos + 1 )
778cdf0e10cSrcweir : ( nMousePos + 2 - nScrPos );
779cdf0e10cSrcweir
780cdf0e10cSrcweir if ( nNewWidth < 0 /* && !IsSelected(nDragNo) */ )
781cdf0e10cSrcweir {
782cdf0e10cSrcweir SCCOLROW nStart = 0;
783cdf0e10cSrcweir SCCOLROW nEnd = nDragNo;
784cdf0e10cSrcweir while (nNewWidth < 0)
785cdf0e10cSrcweir {
786cdf0e10cSrcweir nStart = nDragNo;
787cdf0e10cSrcweir if (nDragNo>0)
788cdf0e10cSrcweir {
789cdf0e10cSrcweir --nDragNo;
790cdf0e10cSrcweir nNewWidth += GetEntrySize( nDragNo ); //! GetHiddenCount() ???
791cdf0e10cSrcweir }
792cdf0e10cSrcweir else
793cdf0e10cSrcweir nNewWidth = 0;
794cdf0e10cSrcweir }
795cdf0e10cSrcweir HideEntries( nStart, nEnd );
796cdf0e10cSrcweir }
797cdf0e10cSrcweir else
798cdf0e10cSrcweir {
799cdf0e10cSrcweir if (nNewWidth<0) nNewWidth=0;
800cdf0e10cSrcweir if (bDragMoved)
801cdf0e10cSrcweir SetEntrySize( nDragNo, (sal_uInt16) nNewWidth );
802cdf0e10cSrcweir }
803cdf0e10cSrcweir }
804cdf0e10cSrcweir else
805cdf0e10cSrcweir {
806cdf0e10cSrcweir pSelEngine->SelMouseButtonUp( rMEvt );
807cdf0e10cSrcweir ReleaseMouse();
808cdf0e10cSrcweir }
809cdf0e10cSrcweir }
810cdf0e10cSrcweir
MouseMove(const MouseEvent & rMEvt)811cdf0e10cSrcweir void ScHeaderControl::MouseMove( const MouseEvent& rMEvt )
812cdf0e10cSrcweir {
813cdf0e10cSrcweir if ( IsDisabled() )
814cdf0e10cSrcweir {
815cdf0e10cSrcweir SetPointer( Pointer( POINTER_ARROW ) );
816cdf0e10cSrcweir return;
817cdf0e10cSrcweir }
818cdf0e10cSrcweir
819cdf0e10cSrcweir sal_Bool bFound;
820cdf0e10cSrcweir (void)GetMousePos( rMEvt, bFound );
821cdf0e10cSrcweir
822cdf0e10cSrcweir if ( bDragging )
823cdf0e10cSrcweir {
824cdf0e10cSrcweir long nNewPos = bVertical ? rMEvt.GetPosPixel().Y() : rMEvt.GetPosPixel().X();
825cdf0e10cSrcweir if ( nNewPos != nDragPos )
826cdf0e10cSrcweir {
827cdf0e10cSrcweir DrawInvert( nDragPos );
828cdf0e10cSrcweir nDragPos = nNewPos;
829cdf0e10cSrcweir ShowDragHelp();
830cdf0e10cSrcweir DrawInvert( nDragPos );
831cdf0e10cSrcweir
832cdf0e10cSrcweir if (nDragPos <= nDragStart-SC_DRAG_MIN || nDragPos >= nDragStart+SC_DRAG_MIN)
833cdf0e10cSrcweir bDragMoved = sal_True;
834cdf0e10cSrcweir }
835cdf0e10cSrcweir }
836cdf0e10cSrcweir else
837cdf0e10cSrcweir {
838cdf0e10cSrcweir if ( bFound && rMEvt.GetButtons()==0 && ResizeAllowed() )
839cdf0e10cSrcweir SetPointer( Pointer( bVertical ? POINTER_VSIZEBAR : POINTER_HSIZEBAR ) );
840cdf0e10cSrcweir else
841cdf0e10cSrcweir SetPointer( Pointer( POINTER_ARROW ) );
842cdf0e10cSrcweir
843cdf0e10cSrcweir if (!bIgnoreMove)
844cdf0e10cSrcweir pSelEngine->SelMouseMove( rMEvt );
845cdf0e10cSrcweir }
846cdf0e10cSrcweir }
847cdf0e10cSrcweir
Tracking(const TrackingEvent & rTEvt)848cdf0e10cSrcweir void ScHeaderControl::Tracking( const TrackingEvent& rTEvt )
849cdf0e10cSrcweir {
850cdf0e10cSrcweir // Weil die SelectionEngine kein Tracking kennt, die Events nur auf
851cdf0e10cSrcweir // die verschiedenen MouseHandler verteilen...
852cdf0e10cSrcweir
853cdf0e10cSrcweir if ( rTEvt.IsTrackingCanceled() )
854cdf0e10cSrcweir StopMarking();
855cdf0e10cSrcweir else if ( rTEvt.IsTrackingEnded() )
856cdf0e10cSrcweir MouseButtonUp( rTEvt.GetMouseEvent() );
857cdf0e10cSrcweir else
858cdf0e10cSrcweir MouseMove( rTEvt.GetMouseEvent() );
859cdf0e10cSrcweir }
860cdf0e10cSrcweir
Command(const CommandEvent & rCEvt)861cdf0e10cSrcweir void ScHeaderControl::Command( const CommandEvent& rCEvt )
862cdf0e10cSrcweir {
863cdf0e10cSrcweir sal_uInt16 nCmd = rCEvt.GetCommand();
864cdf0e10cSrcweir if ( nCmd == COMMAND_CONTEXTMENU )
865cdf0e10cSrcweir {
866cdf0e10cSrcweir StopMarking(); // Selektion / Dragging beenden
867cdf0e10cSrcweir
868cdf0e10cSrcweir // Popup ausfuehren
869cdf0e10cSrcweir
870cdf0e10cSrcweir ScTabViewShell* pViewSh = PTR_CAST( ScTabViewShell,
871cdf0e10cSrcweir SfxViewShell::Current() );
872cdf0e10cSrcweir if ( pViewSh )
873cdf0e10cSrcweir {
874cdf0e10cSrcweir if ( rCEvt.IsMouseEvent() )
875cdf0e10cSrcweir {
876cdf0e10cSrcweir // #i18735# select the column/row under the mouse pointer
877cdf0e10cSrcweir ScViewData* pViewData = pViewSh->GetViewData();
878cdf0e10cSrcweir
879cdf0e10cSrcweir SelectWindow(); // also deselects drawing objects, stops draw text edit
880cdf0e10cSrcweir if ( pViewData->HasEditView( pViewData->GetActivePart() ) )
881cdf0e10cSrcweir SC_MOD()->InputEnterHandler(); // always end edit mode
882cdf0e10cSrcweir
883cdf0e10cSrcweir MouseEvent aMEvt( rCEvt.GetMousePosPixel() );
884cdf0e10cSrcweir sal_Bool bBorder;
885cdf0e10cSrcweir SCCOLROW nPos = GetMousePos( aMEvt, bBorder );
886cdf0e10cSrcweir if (!IsSelectionAllowed(nPos))
887cdf0e10cSrcweir // Selecting this cell is not allowed, neither is context menu.
888cdf0e10cSrcweir return;
889cdf0e10cSrcweir
890cdf0e10cSrcweir SCTAB nTab = pViewData->GetTabNo();
891cdf0e10cSrcweir ScRange aNewRange;
892cdf0e10cSrcweir if ( bVertical )
893cdf0e10cSrcweir aNewRange = ScRange( 0, sal::static_int_cast<SCROW>(nPos), nTab,
894cdf0e10cSrcweir MAXCOL, sal::static_int_cast<SCROW>(nPos), nTab );
895cdf0e10cSrcweir else
896cdf0e10cSrcweir aNewRange = ScRange( sal::static_int_cast<SCCOL>(nPos), 0, nTab,
897cdf0e10cSrcweir sal::static_int_cast<SCCOL>(nPos), MAXROW, nTab );
898cdf0e10cSrcweir
899cdf0e10cSrcweir // see if any part of the range is already selected
900cdf0e10cSrcweir sal_Bool bSelected = sal_False;
901cdf0e10cSrcweir ScRangeList aRanges;
902cdf0e10cSrcweir pViewData->GetMarkData().FillRangeListWithMarks( &aRanges, sal_False );
903cdf0e10cSrcweir sal_uLong nRangeCount = aRanges.Count();
904cdf0e10cSrcweir for (sal_uLong i=0; i<nRangeCount && !bSelected; i++)
905cdf0e10cSrcweir if ( aRanges.GetObject(i)->Intersects( aNewRange ) )
906cdf0e10cSrcweir bSelected = sal_True;
907cdf0e10cSrcweir
908cdf0e10cSrcweir // select the range if no part of it was selected
909cdf0e10cSrcweir if ( !bSelected )
910cdf0e10cSrcweir pViewSh->MarkRange( aNewRange );
911cdf0e10cSrcweir }
912cdf0e10cSrcweir
913cdf0e10cSrcweir ScResId aResId( bVertical ? RID_POPUP_ROWHEADER : RID_POPUP_COLHEADER );
914cdf0e10cSrcweir pViewSh->GetDispatcher()->ExecutePopup( aResId );
915cdf0e10cSrcweir }
916cdf0e10cSrcweir }
917cdf0e10cSrcweir else if ( nCmd == COMMAND_STARTDRAG )
918cdf0e10cSrcweir {
919cdf0e10cSrcweir pSelEngine->Command( rCEvt );
920cdf0e10cSrcweir }
921cdf0e10cSrcweir }
922cdf0e10cSrcweir
StopMarking()923cdf0e10cSrcweir void ScHeaderControl::StopMarking()
924cdf0e10cSrcweir {
925cdf0e10cSrcweir if ( bDragging )
926cdf0e10cSrcweir {
927cdf0e10cSrcweir DrawInvert( nDragPos );
928cdf0e10cSrcweir bDragging = sal_False;
929cdf0e10cSrcweir }
930cdf0e10cSrcweir
931cdf0e10cSrcweir SetMarking( sal_False );
932cdf0e10cSrcweir bIgnoreMove = sal_True;
933cdf0e10cSrcweir
934cdf0e10cSrcweir // #86260# don't call pSelEngine->Reset, so selection across the parts of
935cdf0e10cSrcweir // a split/frozen view is possible
936cdf0e10cSrcweir
937cdf0e10cSrcweir ReleaseMouse();
938cdf0e10cSrcweir }
939cdf0e10cSrcweir
ShowDragHelp()940cdf0e10cSrcweir void ScHeaderControl::ShowDragHelp()
941cdf0e10cSrcweir {
942cdf0e10cSrcweir if (Help::IsQuickHelpEnabled())
943cdf0e10cSrcweir {
944cdf0e10cSrcweir long nScrPos = GetScrPos( nDragNo );
945cdf0e10cSrcweir sal_Bool bLayoutRTL = IsLayoutRTL();
946cdf0e10cSrcweir long nVal = bLayoutRTL ? ( nScrPos - nDragPos + 1 )
947cdf0e10cSrcweir : ( nDragPos + 2 - nScrPos );
948cdf0e10cSrcweir
949cdf0e10cSrcweir String aHelpStr = GetDragHelp( nVal );
950cdf0e10cSrcweir Point aPos = OutputToScreenPixel( Point(0,0) );
951cdf0e10cSrcweir Size aSize = GetSizePixel();
952cdf0e10cSrcweir
953cdf0e10cSrcweir Point aMousePos = OutputToScreenPixel(GetPointerPosPixel());
954cdf0e10cSrcweir
955cdf0e10cSrcweir Rectangle aRect;
956cdf0e10cSrcweir sal_uInt16 nAlign;
957cdf0e10cSrcweir if (!bVertical)
958cdf0e10cSrcweir {
959cdf0e10cSrcweir // oberhalb
960cdf0e10cSrcweir aRect.Left() = aMousePos.X();
961cdf0e10cSrcweir aRect.Top() = aPos.Y() - 4;
962cdf0e10cSrcweir nAlign = QUICKHELP_BOTTOM|QUICKHELP_CENTER;
963cdf0e10cSrcweir }
964cdf0e10cSrcweir else
965cdf0e10cSrcweir {
966cdf0e10cSrcweir // rechts oben
967cdf0e10cSrcweir aRect.Left() = aPos.X() + aSize.Width() + 8;
968cdf0e10cSrcweir aRect.Top() = aMousePos.Y() - 2;
969cdf0e10cSrcweir nAlign = QUICKHELP_LEFT|QUICKHELP_BOTTOM;
970cdf0e10cSrcweir }
971cdf0e10cSrcweir
972cdf0e10cSrcweir aRect.Right() = aRect.Left();
973cdf0e10cSrcweir aRect.Bottom() = aRect.Top();
974cdf0e10cSrcweir
975cdf0e10cSrcweir Help::ShowQuickHelp(this, aRect, aHelpStr, nAlign);
976cdf0e10cSrcweir }
977cdf0e10cSrcweir }
978cdf0e10cSrcweir
RequestHelp(const HelpEvent & rHEvt)979cdf0e10cSrcweir void ScHeaderControl::RequestHelp( const HelpEvent& rHEvt )
980cdf0e10cSrcweir {
981cdf0e10cSrcweir // Wenn eigene QuickHelp angezeigt wird, nicht durch RequestHelp
982cdf0e10cSrcweir // wieder wegnehmen lassen
983cdf0e10cSrcweir
984cdf0e10cSrcweir sal_Bool bOwn = bDragging && Help::IsQuickHelpEnabled();
985cdf0e10cSrcweir if (!bOwn)
986cdf0e10cSrcweir Window::RequestHelp(rHEvt);
987cdf0e10cSrcweir }
988cdf0e10cSrcweir
989cdf0e10cSrcweir // -----------------------------------------------------------------------
990cdf0e10cSrcweir // Dummys fuer virtuelle Methoden
991cdf0e10cSrcweir // -----------------------------------------------------------------------
992cdf0e10cSrcweir
GetHiddenCount(SCCOLROW nEntryNo)993cdf0e10cSrcweir SCCOLROW ScHeaderControl::GetHiddenCount( SCCOLROW nEntryNo )
994cdf0e10cSrcweir {
995cdf0e10cSrcweir SCCOLROW nHidden = 0;
996cdf0e10cSrcweir while ( nEntryNo < nSize && GetEntrySize( nEntryNo ) == 0 )
997cdf0e10cSrcweir {
998cdf0e10cSrcweir ++nEntryNo;
999cdf0e10cSrcweir ++nHidden;
1000cdf0e10cSrcweir }
1001cdf0e10cSrcweir return nHidden;
1002cdf0e10cSrcweir }
1003cdf0e10cSrcweir
IsLayoutRTL()1004cdf0e10cSrcweir sal_Bool ScHeaderControl::IsLayoutRTL()
1005cdf0e10cSrcweir {
1006cdf0e10cSrcweir return sal_False;
1007cdf0e10cSrcweir }
1008cdf0e10cSrcweir
IsMirrored()1009cdf0e10cSrcweir sal_Bool ScHeaderControl::IsMirrored()
1010cdf0e10cSrcweir {
1011cdf0e10cSrcweir return sal_False;
1012cdf0e10cSrcweir }
1013cdf0e10cSrcweir
IsDisabled()1014cdf0e10cSrcweir sal_Bool ScHeaderControl::IsDisabled()
1015cdf0e10cSrcweir {
1016cdf0e10cSrcweir return sal_False;
1017cdf0e10cSrcweir }
1018cdf0e10cSrcweir
ResizeAllowed()1019cdf0e10cSrcweir sal_Bool ScHeaderControl::ResizeAllowed()
1020cdf0e10cSrcweir {
1021cdf0e10cSrcweir return sal_True;
1022cdf0e10cSrcweir }
1023cdf0e10cSrcweir
SelectWindow()1024cdf0e10cSrcweir void ScHeaderControl::SelectWindow()
1025cdf0e10cSrcweir {
1026cdf0e10cSrcweir }
1027cdf0e10cSrcweir
DrawInvert(long)1028cdf0e10cSrcweir void ScHeaderControl::DrawInvert( long /* nDragPos */ )
1029cdf0e10cSrcweir {
1030cdf0e10cSrcweir }
1031cdf0e10cSrcweir
GetDragHelp(long)1032cdf0e10cSrcweir String ScHeaderControl::GetDragHelp( long /* nVal */ )
1033cdf0e10cSrcweir {
1034cdf0e10cSrcweir return EMPTY_STRING;
1035cdf0e10cSrcweir }
1036cdf0e10cSrcweir
SetMarking(sal_Bool)1037cdf0e10cSrcweir void ScHeaderControl::SetMarking( sal_Bool /* bSet */ )
1038cdf0e10cSrcweir {
1039cdf0e10cSrcweir }
1040cdf0e10cSrcweir
1041cdf0e10cSrcweir
1042cdf0e10cSrcweir
1043