]> git.saurik.com Git - wxWidgets.git/blob - utils/wxPython/lib/calendar.py
Fixed remaining int vs. long warnings.
[wxWidgets.git] / utils / wxPython / lib / calendar.py
1 #----------------------------------------------------------------------------
2 # Name: calendar.py
3 # Purpose: Calendar display control
4 #
5 # Author: Lorne White (email: lwhite1@planet.eon.net)
6 #
7 # Created:
8 # Version 0.5 1999/11/03
9 # Licence: wxWindows license
10 #----------------------------------------------------------------------------
11
12 from wxPython.wx import *
13
14 from CDate import *
15 import string, time
16
17
18 CalDays = [6, 0, 1, 2, 3, 4, 5]
19 AbrWeekday = {6:"Sun", 0:"Mon", 1:"Tue", 2:"Wed", 3:"Thu", 4:"Fri", 5:"Sat"}
20 _MIDSIZE = 100
21
22
23 # calendar drawing routing
24
25 class CalDraw:
26 def __init__(self):
27 self.rg = {}
28 self.y_st = 15 # start of vertical draw default
29
30 def SetSize(self, size):
31 self.sizew = size.width
32 self.sizeh = size.height
33
34 # draw the various elements of the calendar
35
36 def DrawCal(self, DC, sel_lst):
37 self.DC = DC
38
39 self.DrawBorder()
40
41 if self.hide_title is FALSE:
42 self.DrawMonth()
43
44 self.Center()
45
46 self.DrawGrid()
47 self.GetRect()
48
49 self.DrawSel(sel_lst) # highlighted days
50 self.DrawWeek()
51 self.DrawNum()
52
53 # draw border around the outside of the main display rectangle
54
55 def DrawBorder(self):
56 rect = wxRect(0, 0, self.sizew, self.sizeh) # full display window area
57 self.DC.DrawRectangle(rect.x, rect.y, rect.width, rect.height)
58
59 def DrawNumVal(self):
60 self.DrawNum()
61
62 # calculate the calendar days and offset position
63
64 def SetCal(self, year, month):
65 self.year = year
66 self.month = month
67
68 day = 1
69 t = Date(year, month, day)
70 dow = t.day_of_week # start day in month
71 dim = t.days_in_month # number of days in month
72 start_pos = dow+1
73 self.st_pos = start_pos
74
75 self.cal = []
76 for i in range(start_pos):
77 self.cal.append('')
78 i = 1
79 while i <= dim:
80 self.cal.append(str(i))
81 i = i + 1
82 return start_pos
83
84 # get the display rectange list of the day grid
85
86 def GetRect(self):
87 cnt = 0
88 for y in self.gridy[1:-1]:
89 for x in self.gridx[:-1]:
90 rect = wxRect(x, y, self.dl_w, self.dl_h) # create rect region
91 self.rg[cnt] = rect
92 cnt = cnt + 1
93 return self.rg
94
95 def GetCal(self):
96 return self.cal
97
98 def GetOffset(self):
99 return self.st_pos
100
101 # month and year title
102
103 def DrawMonth(self):
104 month = Month[self.month]
105
106 sizef = 12
107 if self.sizeh < _MIDSIZE:
108 sizef = 10
109
110 f = wxFont(sizef, self.font, wxNORMAL, self.bold)
111 self.DC.SetFont(f)
112
113 tw,th = self.DC.GetTextExtent(month)
114 adjust = (self.sizew-tw)/2
115 self.DC.DrawText(month, adjust, 10)
116
117 year = str(self.year)
118 tw,th = self.DC.GetTextExtent(year)
119 adjust = self.sizew-tw-20
120
121 self.y_st = th * 3
122
123 f = wxFont(sizef, self.font, wxNORMAL, self.bold)
124 self.DC.SetFont(f)
125 self.DC.DrawText(year, adjust, 10)
126
127 # draw the week days
128
129 def DrawWeek(self):
130 sizef = 10
131 if self.sizeh < _MIDSIZE:
132 sizef = 8
133
134 f = wxFont(sizef, self.font, wxNORMAL, self.bold)
135 self.DC.SetFont(f)
136
137 cnt_x = 0
138 cnt_y = 0
139 width = self.gridx[1]-self.gridx[0]
140 height = self.gridy[1] - self.gridy[0]
141
142 for val in CalDays:
143 day = AbrWeekday[val]
144 if self.sizew < 200:
145 day = day[0]
146 dw,dh = self.DC.GetTextExtent(day)
147 diffx = (width-dw)/2
148 diffy = (height-dh)/2
149
150 x = self.gridx[cnt_x]
151 y = self.gridy[cnt_y]
152 self.DC.DrawText(day, x+diffx, y+diffy)
153 cnt_x = cnt_x + 1
154
155 # draw the day numbers
156
157 def DrawNum(self):
158 sizef = 10
159 if self.sizeh < _MIDSIZE:
160 sizef = 8
161 f = wxFont(sizef, self.font, wxNORMAL, self.bold)
162 self.DC.SetFont(f)
163
164 cnt_x = 0
165 cnt_y = 1
166 for val in self.cal:
167 x = self.gridx[cnt_x]
168 y = self.gridy[cnt_y]
169 self.DC.DrawText(val, x+5, y+5)
170 if cnt_x < 6:
171 cnt_x = cnt_x + 1
172 else:
173 cnt_x = 0
174 cnt_y = cnt_y + 1
175
176 # calculate the dimensions in the center of the drawing area
177
178 def Center(self):
179 self.x_st = 10
180 self.y_end = 10
181
182 bdw = self.x_st * 2
183 bdh = self.y_st + self.y_end
184
185 self.dl_w = (self.sizew-bdw)/7
186 self.dl_h = (self.sizeh-bdh)/7
187
188 self.cwidth = self.dl_w * 7
189 self.cheight = self.dl_h * 6 + self.dl_h/2
190
191 # highlighted selectioned days
192
193 def DrawSel(self, sel_lst):
194 for key in sel_lst:
195 brush = wxBrush(wxNamedColour(self.high_color), wxSOLID)
196 self.DC.SetBrush(brush)
197 if self.hide_grid is FALSE:
198 self.DC.SetPen(wxPen(wxNamedColour(self.grid_color), 0))
199 else:
200 self.DC.SetPen(wxPen(wxNamedColour(self.back_color), 0))
201 nkey = key + self.st_pos -1
202 rect = self.rg[nkey]
203 self.DC.DrawRectangle(rect.x, rect.y, rect.width+1, rect.height+1)
204
205 # calculate and draw the grid lines
206
207 def DrawGrid(self):
208 self.DC.SetPen(wxPen(wxNamedColour(self.grid_color), 0))
209
210 self.gridx = []
211 self.gridy = []
212
213 x1 = self.x_st
214 y1 = self.y_st
215 y1 = self.y_st
216 y2 = self.y_st + self.cheight
217 for i in range(8):
218 if self.hide_grid is FALSE:
219 self.DC.DrawLine(x1, y1, x1, y2)
220 self.gridx.append(x1)
221 x1 = x1 + self.dl_w
222
223 x1 = self.x_st
224 y1 = self.y_st
225 x2 = self.x_st + self.cwidth
226 for i in range(8):
227 if self.hide_grid is FALSE:
228 self.DC.DrawLine(x1, y1, x2, y1)
229 self.gridy.append(y1)
230 if i == 0:
231 y1 = y1 + self.dl_h/2
232 else:
233 y1 = y1 + self.dl_h
234
235
236 class wxCalendar(wxWindow):
237 def __init__(self, parent, id, pos=wxDefaultPosition, size=wxDefaultSize):
238 wxWindow.__init__(self, parent, id, pos, size)
239
240 # set the calendar control attributes
241
242 self.grid_color = 'BLACK'
243 self.back_color = 'WHITE'
244 self.sel_color = 'RED'
245 self.high_color = 'LIGHT BLUE'
246 self.font = wxSWISS
247 self.bold = wxNORMAL
248
249 self.SetBackgroundColour(wxNamedColor(self.back_color))
250 self.Connect(-1, -1, wxEVT_LEFT_DOWN, self.OnLeftEvent)
251 self.Connect(-1, -1, wxEVT_LEFT_DCLICK, self.OnLeftDEvent)
252 self.Connect(-1, -1, wxEVT_RIGHT_DOWN, self.OnRightEvent)
253 self.Connect(-1, -1, wxEVT_RIGHT_DCLICK, self.OnRightDEvent)
254
255 self.sel_key = None # last used by
256 self.sel_lst = [] # highlighted selected days
257
258 self.SetNow() # default calendar for current month
259
260 self.size = None
261 self.hide_title = FALSE
262 self.hide_grid = FALSE
263 self.set_day = None
264
265 # control some of the main calendar attributes
266
267 def HideTitle(self):
268 self.hide_title = TRUE
269
270 def HideGrid(self):
271 self.hide_grid = TRUE
272
273 # determine the calendar rectangle click area and draw a selection
274
275 def ProcessClick(self, event):
276 self.x, self.y = event.GetX(), event.GetY()
277 key = self.GetDayHit(self.x, self.y)
278 self.SelectDay(key)
279
280 # tab mouse click events and process
281
282 def OnLeftEvent(self, event):
283 self.click = 'LEFT'
284 self.ProcessClick(event)
285
286 def OnLeftDEvent(self, event):
287 self.click = 'DLEFT'
288 self.ProcessClick(event)
289
290 def OnRightEvent(self, event):
291 self.click = 'RIGHT'
292 self.ProcessClick(event)
293
294 def OnRightDEvent(self, event):
295 self.click = 'DRIGHT'
296 self.ProcessClick(event)
297
298 def SetSize(self, set_size):
299 self.size = set_size
300
301 def SetSelDay(self, sel):
302 self.sel_lst = sel # list of highlighted days
303
304 # get the current date
305
306 def SetNow(self):
307 dt = now()
308 self.month = dt.month
309 self.year = dt.year
310 self.day = dt.day
311
312 # set the current day
313
314 def SetCurrentDay(self):
315 self.SetNow()
316 self.set_day = self.day
317
318 # get the date, day, month, year set in calendar
319
320 def GetDate(self):
321 return self.day, self.month, self.year
322
323 def GetDay(self):
324 return self.day
325
326 def GetMonth(self):
327 return self.month
328
329 def GetYear(self):
330 return self.year
331
332 # set the day, month, and year
333
334 def SetDayValue(self, day):
335 self.set_day = day
336
337 def SetMonth(self, month):
338 if month >= 1 and month <= 12:
339 self.month = month
340 else:
341 self.month = 1
342 self.set_day = None
343
344 def SetYear(self, year):
345 self.year = year
346
347 # increment year and month
348
349 def IncYear(self):
350 self.year = self.year + 1
351 self.set_day = None
352
353 def DecYear(self):
354 self.year = self.year - 1
355 self.set_day = None
356
357 def IncMonth(self):
358 self.month = self.month + 1
359 if self.month > 12:
360 self.month = 1
361 self.year = self.year + 1
362 self.set_day = None
363
364 def DecMonth(self):
365 self.month = self.month - 1
366 if self.month < 1:
367 self.month = 12
368 self.year = self.year - 1
369 self.set_day = None
370
371 # test to see if the selection has a date and create event
372
373 def TestDay(self, key):
374 try:
375 self.day = int(self.cal[key])
376 except:
377 return None
378 if self.day == "":
379 return None
380 else:
381 evt = wxPyCommandEvent(2100, self.GetId())
382 evt.click, evt.day, evt.month, evt.year = self.click, self.day, self.month, self.year
383 self.GetEventHandler().ProcessEvent(evt)
384
385 self.set_day = self.day
386 return key
387
388 # find the clicked area rectangle
389
390 def GetDayHit(self, mx, my):
391 for key in self.rg.keys():
392 val = self.rg[key]
393 rt = wxRegion()
394 rt.UnionRect(val)
395 if rt.Contains(mx, my) != 0:
396 result = self.TestDay(key)
397 return result
398 return None
399
400 # calendar drawing
401
402 def OnPaint(self, event):
403 DC = wxPaintDC(self)
404 self.DoDrawing(DC)
405
406 def DoDrawing(self, DC):
407 DC = wxPaintDC(self)
408 DC.BeginDrawing()
409
410 self.cal = cal = CalDraw()
411 if self.size is None:
412 size = self.GetClientSize()
413 else:
414 size = self.size
415
416 # drawing attributes
417
418 cal.hide_title = self.hide_title
419 cal.hide_grid = self.hide_grid
420
421 cal.grid_color = self.grid_color
422 cal.high_color = self.high_color
423 cal.back_color = self.back_color
424 cal.font = self.font
425 cal.bold = self.bold
426
427 cal.SetSize(size)
428 cal.SetCal(self.year, self.month)
429 cal.DrawCal(DC, self.sel_lst)
430
431 self.rg = cal.GetRect()
432 self.cal = cal.GetCal()
433 self.st_pos = cal.GetOffset()
434 self.ymax = DC.MaxY()
435
436 if self.set_day != None:
437 self.SetDay(self.set_day)
438 DC.EndDrawing()
439
440 # draw the selection rectangle
441
442 def DrawRect(self, key, color = 'BLACK', width = 0):
443 if key == None:
444 return
445 DC = wxClientDC(self)
446 DC.BeginDrawing()
447
448 brush = wxBrush(wxColour(0, 0xFF, 0x80), wxTRANSPARENT)
449 DC.SetBrush(brush)
450 DC.SetPen(wxPen(wxNamedColour(color), width))
451
452 rect = self.rg[key]
453 DC.DrawRectangle(rect.x, rect.y, rect.width+1, rect.height+1)
454
455 DC.EndDrawing()
456
457 # set the day selection
458
459 def SetDay(self, day):
460 day = day + self.st_pos - 1
461 self.SelectDay(day)
462
463 def SelectDay(self, key):
464 sel_size = 1
465 self.DrawRect(self.sel_key, self.back_color, sel_size) # clear large selection
466 if self.hide_grid is FALSE:
467 self.DrawRect(self.sel_key, self.grid_color)
468
469 self.DrawRect(key, self.sel_color, sel_size)
470 self.sel_key = key # store last used by
471 self.select_day = None
472
473 def ClearDsp(self):
474 self.Clear()
475
476