I'm using the CalendarCtrl and find it to have problems in 2.6.2.1 on Mac OS X.
The EVT_CALENDAR_SEL_CHANGED will be sent with the date set to 2038 (GetTick() == 0xffffffff)
after clicking the up spin arrow on the year. My work around is to ignore this as the correct date arrives
in the next event.
I've been able to get the year to change to 0 and -1 when clicking on the year spinners, not sure of
the exact sequence that did this.
Enable( False ) disabled the year and month controls but the day picker still allows changes.
I work around this by forcing the date back.
It seems that the CalendarCtrl keeps a reference to the DateTime object I pass in.
And that object is returned from GetDate. This was a surprise I would expect the ctrl
to have its own independent DataTime object inside itself.
The code I ended up with is below.
Barry
class HistoryDialog(wx.Dialog):
def __init__( self, parent ):
wx.Dialog.__init__( self, parent, -1, 'Log History' )
self.g_sizer = wx.FlexGridSizer( 0, 2, 0, 0 )
self.g_sizer.AddGrowableCol( 1 )
self.all_radio = wx.RadioButton( self, -1, 'Show all entries' )
self.all_radio.SetValue( True )
self.g_sizer.Add( self.all_radio, 1, wx.EXPAND|wx.ALL|wx.ALIGN_RIGHT, 3 )
self.g_sizer.Add( (0,0), 1, wx.EXPAND|wx.ALL|wx.ALIGN_RIGHT, 3 )
self.limit_radio = wx.RadioButton( self, -1, 'Show only:' )
self.limit_text = wx.TextCtrl( self, -1, '20', style=wx.TE_RIGHT )
self.limit_text.Enable( False )
self.g_sizer.Add( self.limit_radio, 1, wx.EXPAND|wx.ALL|wx.ALIGN_RIGHT, 3 )
self.g_sizer.Add( self.limit_text, 1, wx.EXPAND|wx.ALL|wx.ALIGN_RIGHT, 3 )
self.date = wx.DateTime_Now()
self.date.SubtractDS( wx.DateSpan( weeks=1 ) )
self.since_radio = wx.RadioButton( self, -1, 'Show since:' )
self.since_date = wx.calendar.CalendarCtrl( self, -1,
self.copyDataTime( self.date ),
style=wx.calendar.CAL_MONDAY_FIRST )
self.since_date.Enable( False )
self.g_sizer.Add( self.since_radio, 1, wx.EXPAND|wx.ALL|wx.ALIGN_RIGHT|wx.ALIGN_TOP, 3 )
self.g_sizer.Add( self.since_date, 1, wx.EXPAND|wx.ALL|wx.ALIGN_RIGHT, 3 )
self.button_ok = wx.Button( self, wx.ID_OK, ' OK ' )
self.button_ok.SetDefault()
self.button_cancel = wx.Button( self, wx.ID_CANCEL, ' Cancel ' )
self.h_sizer_buttons = wx.BoxSizer( wx.HORIZONTAL )
self.h_sizer_buttons.Add( (150, 20), 1, wx.EXPAND )
self.h_sizer_buttons.Add( self.button_ok, 0, wx.EXPAND|wx.EAST, 15 )
self.h_sizer_buttons.Add( self.button_cancel, 0, wx.EXPAND|wx.EAST, 2 )
self.v_sizer = wx.BoxSizer( wx.VERTICAL )
self.v_sizer.Add( self.g_sizer, 0, wx.EXPAND|wx.ALL, 5 )
self.v_sizer.Add( self.h_sizer_buttons, 0, wx.EXPAND|wx.ALL, 5 )
self.SetAutoLayout( True )
self.SetSizer( self.v_sizer )
self.v_sizer.Fit( self )
self.Layout()
self.CentreOnParent()
wx.EVT_BUTTON( self, wx.ID_OK, self.OnOk )
wx.EVT_BUTTON( self, wx.ID_CANCEL, self.OnCancel )
wx.EVT_RADIOBUTTON( self, self.all_radio.GetId(), self.OnRadio )
wx.EVT_RADIOBUTTON( self, self.limit_radio.GetId(), self.OnRadio )
wx.EVT_RADIOBUTTON( self, self.since_radio.GetId(), self.OnRadio )
wx.calendar.EVT_CALENDAR_SEL_CHANGED( self, self.since_date.GetId(), self.OnCalendarSelChanged )
# ----------------------------------------
def OnOk( self, event ):
self.EndModal( wx.ID_OK )
def OnCancel( self, event ):
self.EndModal( wx.ID_CANCEL )
# ----------------------------------------
def OnRadio( self, event ):
self.since_date.Enable( self.since_radio.GetValue() )
self.limit_text.Enable( self.limit_radio.GetValue() )
def OnCalendarSelChanged( self, event ):
if self.since_radio.GetValue():
# ensure that the date stays in the past
date = self.since_date.GetDate()
# sometimes the event is sent with a bogus value for the date
# just ignore these events
if date.GetTicks() == ((2**32)-1):
return
if date.IsLaterThan( wx.DateTime_Now() ):
self.since_date.SetDate( self.copyDataTime( self.date ) )
else:
self.date = self.copyDataTime( date )
else:
# CalendarCtrl does not disable day changes
# force date back to self.date
self.since_date.SetDate( self.copyDataTime( self.date ) )
def copyDataTime( self, date ):
t = date.GetTicks()
return wx.DateTimeFromTimeT( t )