Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*************************************************************************
3 : : *
4 : : * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 : : *
6 : : * Copyright 2000, 2010 Oracle and/or its affiliates.
7 : : *
8 : : * OpenOffice.org - a multi-platform office productivity suite
9 : : *
10 : : * This file is part of OpenOffice.org.
11 : : *
12 : : * OpenOffice.org is free software: you can redistribute it and/or modify
13 : : * it under the terms of the GNU Lesser General Public License version 3
14 : : * only, as published by the Free Software Foundation.
15 : : *
16 : : * OpenOffice.org is distributed in the hope that it will be useful,
17 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 : : * GNU Lesser General Public License version 3 for more details
20 : : * (a copy is included in the LICENSE file that accompanied this code).
21 : : *
22 : : * You should have received a copy of the GNU Lesser General Public License
23 : : * version 3 along with OpenOffice.org. If not, see
24 : : * <http://www.openoffice.org/license.html>
25 : : * for a copy of the LGPLv3 License.
26 : : *
27 : : ************************************************************************/
28 : :
29 : : #ifndef _CALENDAR_HXX
30 : : #define _CALENDAR_HXX
31 : :
32 : : #include "svtools/svtdllapi.h"
33 : : #include <unotools/calendarwrapper.hxx>
34 : : #include <com/sun/star/i18n/Weekdays.hpp>
35 : :
36 : : #include <vcl/ctrl.hxx>
37 : : #include <vcl/timer.hxx>
38 : : #include <vcl/field.hxx>
39 : : #include <set>
40 : :
41 : : class MouseEvent;
42 : : class TrackingEvent;
43 : : class KeyEvent;
44 : : class HelpEvent;
45 : : class DataChangedEvent;
46 : : class FloatingWindow;
47 : : class PushButton;
48 : : class ImplCFieldFloatWin;
49 : :
50 : : /*************************************************************************
51 : :
52 : : Description
53 : : ============
54 : :
55 : : class Calendar
56 : :
57 : : This class allows for the selection of a date. The displayed date range is
58 : : the one specified by the Date class. We display as many months as we have
59 : : space in the control. The user can switch between months using a ContextMenu
60 : : (clicking on the month's name) or via two ScrollButtons in-between the months.
61 : :
62 : : --------------------------------------------------------------------------
63 : :
64 : : WinBits
65 : :
66 : : WB_BORDER We draw a border around the window.
67 : : WB_TABSTOP Keyboard control is possible. We get the focus, when
68 : : the user clicks in the Control.
69 : : WB_QUICKHELPSHOWSDATEINFO Show DateInfo as BallonHelp even if QuickInfo is enabled
70 : : WB_BOLDTEXT We format by bold texts and DIB_BOLD is evaluated by
71 : : AddDateInfo()
72 : : WB_FRAMEINFO We format in a way, so that FrameInfo can be displayed
73 : : and the FrameColor is evaluated by AddDateInfo()
74 : : WB_RANGESELECT The user can select multiple days, which need to be
75 : : consecutive
76 : : WB_MULTISELECT The user can select multiple days
77 : : WB_WEEKNUMBER We also display the weekdays
78 : :
79 : : --------------------------------------------------------------------------
80 : :
81 : : We set and get the selected date by SetCurDate()/GetCurDate().
82 : : If the user selects a date Select() is called. If the user double clicks
83 : : DoubleClick() is called.
84 : :
85 : : --------------------------------------------------------------------------
86 : :
87 : : CalcWindowSizePixel() calculates the window size in pixel that is needed
88 : : to display a certain number of months.
89 : :
90 : : --------------------------------------------------------------------------
91 : :
92 : : SetSaturdayColor() and SetSundayColor() set a special color for Saturdays
93 : : and Sundays.
94 : : AddDateInfo() marks special days. With that we can set e.g. public holidays
95 : : to another color or encircle them (for e.g. appointments).
96 : : If we do not supply a year in the date, the day is used in EVERY year.
97 : :
98 : : AddDateInfo() can also add text for every date, which is displayed if the
99 : : BalloonHelp is enabled.
100 : : In order to not have to supply all years with the relevant data, we call
101 : : the RequestDateInfo() handler if a new year is displayed. We can then query
102 : : the year in the handler with GetRequestYear().
103 : :
104 : : --------------------------------------------------------------------------
105 : :
106 : : In order to display a ContextMenu for a date, we need to override the
107 : : Command handler. GetDate() can infer the date from the mouse's position.
108 : : If we use the keyboard, the current date should be use.
109 : :
110 : : If a ContextMenu is displayed, the baseclass' handler must not be called.
111 : :
112 : : --------------------------------------------------------------------------
113 : :
114 : : For multiple selection (WB_RANGESELECT or WB_MULTISELECT) SelectDate(),
115 : : SelectDateRange() can select date ranges. SelectDateRange() selects
116 : : including the end date.
117 : : SetNoSelection() deselects everything.
118 : : SetCurDate() does not select the current date, but only defines the focus
119 : : rectangle.
120 : : GetSelectDateCount()/GetSelectDate() query the selected range.
121 : : IsDateSelected() queries for the status of a date.
122 : :
123 : : The SelectionChanging() handler is being called while a user selects a
124 : : date. In it, we can change the selected range. E.g. if we want to limit
125 : : or extend the selected range. The selected range is realised via SelectDate()
126 : : and SelectDateRange() and queried with GetSelectDateCount()/GetSelectDate().
127 : :
128 : : IsSelectLeft() returns the direction of the selection:
129 : : sal_True is a selection to the left or up
130 : : sal_False is a selection to the right or down
131 : :
132 : : --------------------------------------------------------------------------
133 : :
134 : : If the DateRange area changes and we want to take over the selection, we
135 : : should only do this is if IsScrollDateRangeChanged() retruns sal_True.
136 : : This method returns sal_True if the area change was triggered by using the
137 : : ScrollButtons and sal_False if it was triggered by Resize(), other method
138 : : calls or by ending a selection.
139 : :
140 : : *************************************************************************/
141 : :
142 : : // ------------------
143 : : // - Calendar types -
144 : : // ------------------
145 : :
146 : : #define WB_QUICKHELPSHOWSDATEINFO ((WinBits)0x00004000)
147 : : #define WB_BOLDTEXT ((WinBits)0x00008000)
148 : : #define WB_FRAMEINFO ((WinBits)0x00010000)
149 : : #define WB_WEEKNUMBER ((WinBits)0x00020000)
150 : : // Needs to in agreement with the WinBits in the TabBar or
151 : : // we move it to \vcl\inc\wintypes.hxx
152 : : #ifndef WB_RANGESELECT
153 : : #define WB_RANGESELECT ((WinBits)0x00200000)
154 : : #endif
155 : : #ifndef WB_MULTISELECT
156 : : #define WB_MULTISELECT ((WinBits)0x00400000)
157 : : #endif
158 : :
159 : : #define DIB_BOLD ((sal_uInt16)0x0001)
160 : :
161 : : // ------------
162 : : // - Calendar -
163 : : // ------------
164 : :
165 : : typedef std::set<sal_uInt32> IntDateSet;
166 : :
167 : :
168 : : class SVT_DLLPUBLIC Calendar : public Control
169 : : {
170 : : private:
171 : : IntDateSet* mpSelectTable;
172 : : IntDateSet* mpOldSelectTable;
173 : : IntDateSet* mpRestoreSelectTable;
174 : : XubString* mpDayText[31];
175 : : XubString maDayText;
176 : : XubString maWeekText;
177 : : CalendarWrapper maCalendarWrapper;
178 : : Rectangle maPrevRect;
179 : : Rectangle maNextRect;
180 : : String maDayOfWeekText;
181 : : sal_Int32 mnDayOfWeekAry[7];
182 : : Date maOldFormatFirstDate;
183 : : Date maOldFormatLastDate;
184 : : Date maFirstDate;
185 : : Date maOldFirstDate;
186 : : Date maCurDate;
187 : : Date maOldCurDate;
188 : : Date maAnchorDate;
189 : : Date maDropDate;
190 : : Color maSelColor;
191 : : Color maOtherColor;
192 : : Color* mpStandardColor;
193 : : Color* mpSaturdayColor;
194 : : Color* mpSundayColor;
195 : : sal_uLong mnDayCount;
196 : : long mnDaysOffX;
197 : : long mnWeekDayOffY;
198 : : long mnDaysOffY;
199 : : long mnMonthHeight;
200 : : long mnMonthWidth;
201 : : long mnMonthPerLine;
202 : : long mnLines;
203 : : long mnDayWidth;
204 : : long mnDayHeight;
205 : : long mnWeekWidth;
206 : : WinBits mnWinStyle;
207 : : sal_uInt16 mnFirstYear;
208 : : sal_uInt16 mnLastYear;
209 : : sal_uInt16 mnRequestYear;
210 : : sal_Bool mbCalc:1,
211 : : mbFormat:1,
212 : : mbDrag:1,
213 : : mbSelection:1,
214 : : mbMultiSelection:1,
215 : : mbWeekSel:1,
216 : : mbUnSel:1,
217 : : mbMenuDown:1,
218 : : mbSpinDown:1,
219 : : mbPrevIn:1,
220 : : mbNextIn:1,
221 : : mbDirect:1,
222 : : mbInSelChange:1,
223 : : mbTravelSelect:1,
224 : : mbScrollDateRange:1,
225 : : mbSelLeft:1,
226 : : mbAllSel:1,
227 : : mbDropPos:1;
228 : : Link maSelectionChangingHdl;
229 : : Link maDateRangeChangedHdl;
230 : : Link maRequestDateInfoHdl;
231 : : Link maDoubleClickHdl;
232 : : Link maSelectHdl;
233 : : Timer maDragScrollTimer;
234 : : sal_uInt16 mnDragScrollHitTest;
235 : :
236 : : #ifdef _SV_CALENDAR_CXX
237 : : using Control::ImplInitSettings;
238 : : using Window::ImplInit;
239 : : SVT_DLLPRIVATE void ImplInit( WinBits nWinStyle );
240 : : SVT_DLLPRIVATE void ImplInitSettings();
241 : : SVT_DLLPRIVATE void ImplGetWeekFont( Font& rFont ) const;
242 : : SVT_DLLPRIVATE void ImplFormat();
243 : : using Window::ImplHitTest;
244 : : SVT_DLLPRIVATE sal_uInt16 ImplHitTest( const Point& rPos, Date& rDate ) const;
245 : : SVT_DLLPRIVATE void ImplDrawSpin( sal_Bool bDrawPrev = sal_True, sal_Bool bDrawNext = sal_True );
246 : : SVT_DLLPRIVATE void ImplDrawDate( long nX, long nY,
247 : : sal_uInt16 nDay, sal_uInt16 nMonth, sal_uInt16 nYear,
248 : : DayOfWeek eDayOfWeek,
249 : : sal_Bool bBack = sal_True, sal_Bool bOther = sal_False,
250 : : sal_uLong nToday = 0 );
251 : : SVT_DLLPRIVATE void ImplDraw( sal_Bool bPaint = sal_False );
252 : : SVT_DLLPRIVATE void ImplUpdateDate( const Date& rDate );
253 : : SVT_DLLPRIVATE void ImplUpdateSelection( IntDateSet* pOld );
254 : : SVT_DLLPRIVATE void ImplMouseSelect( const Date& rDate, sal_uInt16 nHitTest,
255 : : sal_Bool bMove, sal_Bool bExpand, sal_Bool bExtended );
256 : : SVT_DLLPRIVATE void ImplUpdate( sal_Bool bCalcNew = sal_False );
257 : : using Window::ImplScroll;
258 : : SVT_DLLPRIVATE void ImplScroll( sal_Bool bPrev );
259 : : SVT_DLLPRIVATE void ImplInvertDropPos();
260 : : SVT_DLLPRIVATE void ImplShowMenu( const Point& rPos, const Date& rDate );
261 : : SVT_DLLPRIVATE void ImplTracking( const Point& rPos, sal_Bool bRepeat );
262 : : SVT_DLLPRIVATE void ImplEndTracking( sal_Bool bCancel );
263 : : SVT_DLLPRIVATE DayOfWeek ImplGetWeekStart() const;
264 : : #endif
265 : :
266 : : protected:
267 : :
268 : : DECL_STATIC_LINK( Calendar, ScrollHdl, Timer *);
269 : :
270 : : public:
271 : : Calendar( Window* pParent, WinBits nWinStyle = 0 );
272 : : ~Calendar();
273 : :
274 : : virtual void MouseButtonDown( const MouseEvent& rMEvt );
275 : : virtual void MouseButtonUp( const MouseEvent& rMEvt );
276 : : virtual void MouseMove( const MouseEvent& rMEvt );
277 : : virtual void Tracking( const TrackingEvent& rMEvt );
278 : : virtual void KeyInput( const KeyEvent& rKEvt );
279 : : virtual void Paint( const Rectangle& rRect );
280 : : virtual void Resize();
281 : : virtual void GetFocus();
282 : : virtual void LoseFocus();
283 : : virtual void RequestHelp( const HelpEvent& rHEvt );
284 : : virtual void Command( const CommandEvent& rCEvt );
285 : : virtual void StateChanged( StateChangedType nStateChange );
286 : : virtual void DataChanged( const DataChangedEvent& rDCEvt );
287 : :
288 : : virtual void SelectionChanging();
289 : : virtual void DateRangeChanged();
290 : : virtual void RequestDateInfo();
291 : : virtual void DoubleClick();
292 : : virtual void Select();
293 : :
294 : : const CalendarWrapper& GetCalendarWrapper() const { return maCalendarWrapper; }
295 : :
296 : : void SelectDate( const Date& rDate, sal_Bool bSelect = sal_True );
297 : : void SetNoSelection();
298 : : sal_Bool IsDateSelected( const Date& rDate ) const;
299 : : Date GetFirstSelectedDate() const;
300 : 0 : void EnableCallEverySelect( sal_Bool bEvery = sal_True ) { mbAllSel = bEvery; }
301 : : sal_Bool IsCallEverySelectEnabled() const { return mbAllSel; }
302 : :
303 : : sal_uInt16 GetRequestYear() const { return mnRequestYear; }
304 : : void SetCurDate( const Date& rNewDate );
305 : : Date GetCurDate() const { return maCurDate; }
306 : : void SetFirstDate( const Date& rNewFirstDate );
307 : 0 : Date GetFirstDate() const { return maFirstDate; }
308 [ # # ]: 0 : Date GetLastDate() const { return GetFirstDate() + mnDayCount; }
309 : : sal_uLong GetDayCount() const { return mnDayCount; }
310 : : Date GetFirstMonth() const;
311 : : Date GetLastMonth() const;
312 : : sal_uInt16 GetMonthCount() const;
313 : : sal_Bool GetDate( const Point& rPos, Date& rDate ) const;
314 : : Rectangle GetDateRect( const Date& rDate ) const;
315 : :
316 : : long GetCurMonthPerLine() const { return mnMonthPerLine; }
317 : : long GetCurLines() const { return mnLines; }
318 : :
319 : : const Color& GetStandardColor() const;
320 : : const Color& GetSaturdayColor() const;
321 : : const Color& GetSundayColor() const;
322 : :
323 : : void StartSelection();
324 : : void EndSelection();
325 : :
326 : 0 : sal_Bool IsTravelSelect() const { return mbTravelSelect; }
327 : : sal_Bool IsScrollDateRangeChanged() const { return mbScrollDateRange; }
328 : : sal_Bool IsSelectLeft() const { return mbSelLeft; }
329 : :
330 : : Size CalcWindowSizePixel( long nCalcMonthPerLine = 1,
331 : : long nCalcLines = 1 ) const;
332 : :
333 : : void SetSelectionChangingHdl( const Link& rLink ) { maSelectionChangingHdl = rLink; }
334 : : const Link& GetSelectionChangingHdl() const { return maSelectionChangingHdl; }
335 : : void SetDateRangeChangedHdl( const Link& rLink ) { maDateRangeChangedHdl = rLink; }
336 : : const Link& GetDateRangeChangedHdl() const { return maDateRangeChangedHdl; }
337 : : void SetRequestDateInfoHdl( const Link& rLink ) { maRequestDateInfoHdl = rLink; }
338 : : const Link& GetRequestDateInfoHdl() const { return maRequestDateInfoHdl; }
339 : : void SetDoubleClickHdl( const Link& rLink ) { maDoubleClickHdl = rLink; }
340 : : const Link& GetDoubleClickHdl() const { return maDoubleClickHdl; }
341 : 0 : void SetSelectHdl( const Link& rLink ) { maSelectHdl = rLink; }
342 : : const Link& GetSelectHdl() const { return maSelectHdl; }
343 : : };
344 : :
345 : : inline const Color& Calendar::GetStandardColor() const
346 : : {
347 : : if ( mpStandardColor )
348 : : return *mpStandardColor;
349 : : else
350 : : return GetFont().GetColor();
351 : : }
352 : :
353 : : inline const Color& Calendar::GetSaturdayColor() const
354 : : {
355 : : if ( mpSaturdayColor )
356 : : return *mpSaturdayColor;
357 : : else
358 : : return GetFont().GetColor();
359 : : }
360 : :
361 : : inline const Color& Calendar::GetSundayColor() const
362 : : {
363 : : if ( mpSundayColor )
364 : : return *mpSundayColor;
365 : : else
366 : : return GetFont().GetColor();
367 : : }
368 : :
369 : : /*************************************************************************
370 : :
371 : : Description
372 : : ============
373 : :
374 : : class CalendarField
375 : :
376 : : This class is a DateField with which one can select a date via a DropDownButton
377 : : and the CalendarControl.
378 : :
379 : : --------------------------------------------------------------------------
380 : :
381 : : WinBits
382 : :
383 : : See DateField
384 : :
385 : : The preferences for the CalendarControl can be set via SetCalendarStyle().
386 : :
387 : : --------------------------------------------------------------------------
388 : :
389 : : With EnableToday()/EnableNone() we can enable a TodayButton and a NoneButton.
390 : :
391 : : --------------------------------------------------------------------------
392 : :
393 : : If we set WB_RANGESELECT with SetCalendarStyle(), we can select multiple days
394 : : in the Calendar.
395 : :
396 : : Because we only take over the start date into the field, we should query
397 : : with GetCalendar() in the SelectHandler and with GetSelectDateCount()/GetSelectDate()
398 : : the selected range. We then can e.g. take over that value to another field.
399 : :
400 : : --------------------------------------------------------------------------
401 : :
402 : : If a derived Calendar should be used, we can override the CreateCalendar()
403 : : method in CalendarField and create an own calendar there ourselves.
404 : :
405 : : *************************************************************************/
406 : :
407 : : // -----------------
408 : : // - CalendarField -
409 : : // -----------------
410 : :
411 : : class SVT_DLLPUBLIC CalendarField : public DateField
412 : : {
413 : : private:
414 : : ImplCFieldFloatWin* mpFloatWin;
415 : : Calendar* mpCalendar;
416 : : WinBits mnCalendarStyle;
417 : : PushButton* mpTodayBtn;
418 : : PushButton* mpNoneBtn;
419 : : Date maDefaultDate;
420 : : sal_Bool mbToday;
421 : : sal_Bool mbNone;
422 : : Link maSelectHdl;
423 : :
424 : : #ifdef _SV_CALENDAR_CXX
425 : : DECL_DLLPRIVATE_LINK( ImplSelectHdl, Calendar* );
426 : : DECL_DLLPRIVATE_LINK( ImplClickHdl, PushButton* );
427 : : DECL_DLLPRIVATE_LINK( ImplPopupModeEndHdl, void* );
428 : : #endif
429 : :
430 : : public:
431 : : CalendarField( Window* pParent, WinBits nWinStyle );
432 : : ~CalendarField();
433 : :
434 : : virtual void Select();
435 : :
436 : : virtual sal_Bool ShowDropDown( sal_Bool bShow );
437 : : virtual Calendar* CreateCalendar( Window* pParent );
438 : : Calendar* GetCalendar();
439 : :
440 : : void SetDefaultDate( const Date& rDate ) { maDefaultDate = rDate; }
441 : : Date GetDefaultDate() const { return maDefaultDate; }
442 : :
443 : 54 : void EnableToday( sal_Bool bToday = sal_True ) { mbToday = bToday; }
444 : : sal_Bool IsTodayEnabled() const { return mbToday; }
445 : 54 : void EnableNone( sal_Bool bNone = sal_True ) { mbNone = bNone; }
446 : : sal_Bool IsNoneEnabled() const { return mbNone; }
447 : :
448 : : void SetCalendarStyle( WinBits nStyle ) { mnCalendarStyle = nStyle; }
449 : : WinBits GetCalendarStyle() const { return mnCalendarStyle; }
450 : :
451 : : void SetSelectHdl( const Link& rLink ) { maSelectHdl = rLink; }
452 : : const Link& GetSelectHdl() const { return maSelectHdl; }
453 : :
454 : : protected:
455 : : virtual void StateChanged( StateChangedType nStateChange );
456 : : };
457 : :
458 : : #endif // _CALENDAR_HXX
459 : :
460 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|