#pragma once #include "ListTypes.h" #define DATE_STRING 32 class CListDate : public CWindowImpl< CListDate, CDateTimePickerCtrl > { public: CListDate() { m_nItem = NULL_ITEM; m_nSubItem = NULL_SUBITEM; m_nFlags = ITEM_FLAGS_NONE; m_nExitChar = 0; } ~CListDate() { } protected: int m_nItem; int m_nSubItem; UINT m_nFlags; TCHAR m_nExitChar; CFont m_fntDateFont; public: BOOL Create( HWND hWndParent, int nItem, int nSubItem, CRect& rcRect, UINT nFlags, SYSTEMTIME& stItemDate ) { m_nItem = nItem; m_nSubItem = nSubItem; m_nFlags = nFlags; m_nExitChar = 0; // destroy old date control... if ( IsWindow() ) DestroyWindow(); DWORD dwStyle = WS_CHILD | WS_CLIPCHILDREN; if ( nFlags & ITEM_FLAGS_DATETIME_NONE ) dwStyle |= DTS_SHOWNONE; if ( nFlags & ITEM_FLAGS_TIME_ONLY ) dwStyle |= DTS_UPDOWN; // create date-time control CRect Area( rcRect.left + 3, rcRect.top + 2, rcRect.right - 3, rcRect.bottom - 2 ); if ( CWindowImpl< CListDate, CDateTimePickerCtrl >::Create( hWndParent, Area, NULL, dwStyle ) == NULL ) return FALSE; // remove border ModifyStyleEx( WS_EX_CLIENTEDGE, 0, SWP_FRAMECHANGED ); // get system message font CLogFont logFont; logFont.SetMessageBoxFont(); if ( !m_fntDateFont.IsNull() ) m_fntDateFont.DeleteObject(); if ( m_fntDateFont.CreateFontIndirect( &logFont ) == NULL ) return FALSE; SetMonthCalFont( m_fntDateFont ); SetFont( m_fntDateFont ); TCHAR szDateFormat[ DATE_STRING ]; GetLocaleInfo( LOCALE_USER_DEFAULT, LOCALE_SSHORTDATE, szDateFormat, DATE_STRING ); TCHAR szTimeFormat[ DATE_STRING ]; GetLocaleInfo( LOCALE_USER_DEFAULT, LOCALE_STIMEFORMAT, szTimeFormat, DATE_STRING ); if ( nFlags & ITEM_FLAGS_DATE_ONLY ) SetFormat( szDateFormat ); else if ( nFlags & ITEM_FLAGS_TIME_ONLY ) SetFormat( szTimeFormat ); else SetFormat( stdstr_f("%s %s",szDateFormat,szTimeFormat ).c_str() ); // get current date if setting time-only if ( nFlags & ITEM_FLAGS_TIME_ONLY ) { SYSTEMTIME stCurrentDate; if ( GetSystemTime( &stCurrentDate ) == GDT_VALID ) { stItemDate.wYear = stCurrentDate.wYear; stItemDate.wMonth = stCurrentDate.wMonth; stItemDate.wDay = stCurrentDate.wDay; } } SetSystemTime( ( !( nFlags & ITEM_FLAGS_TIME_ONLY ) && stItemDate.wYear == 0 ) ? GDT_NONE : GDT_VALID, &stItemDate ); // show date-time control ShowWindow( SW_SHOW ); SetFocus(); return TRUE; } BEGIN_MSG_MAP_EX(CListDate) MSG_WM_KILLFOCUS(OnKillFocus) REFLECTED_NOTIFY_CODE_HANDLER_EX(DTN_CLOSEUP, OnCloseUp) MSG_WM_GETDLGCODE(OnGetDlgCode) MSG_WM_CHAR(OnChar) DEFAULT_REFLECTION_HANDLER() END_MSG_MAP() void OnKillFocus( HWND hNewWnd ) { // have we dropped down the calendar control? if ( hNewWnd != NULL && GetMonthCal() == hNewWnd ) return; // have we selected a new date from the calendar control? if ( GetFocus() == m_hWnd ) return; // hide calendar control in case it's not closed by losing focus if ( GetMonthCal().IsWindow() ) GetMonthCal().ShowWindow( SW_HIDE ); CWindow wndParent( GetParent() ); if ( wndParent.IsWindow() ) { SYSTEMTIME stItemDate; BOOL bValidDate = ( GetSystemTime( &stItemDate ) == GDT_VALID ); if ( !bValidDate ) ZeroMemory( &stItemDate, sizeof( SYSTEMTIME ) ); if ( m_nFlags & ITEM_FLAGS_DATE_ONLY ) { stItemDate.wHour = 0; stItemDate.wMinute = 0; stItemDate.wSecond = 0; stItemDate.wMilliseconds = 0; } if ( m_nFlags & ITEM_FLAGS_TIME_ONLY ) { stItemDate.wYear = 0; stItemDate.wMonth = 0; stItemDate.wDay = 0; stItemDate.wDayOfWeek = 0; } CListNotify listNotify; listNotify.m_hdrNotify.hwndFrom = m_hWnd; listNotify.m_hdrNotify.idFrom = GetDlgCtrlID(); listNotify.m_hdrNotify.code = LCN_ENDEDIT; listNotify.m_nItem = m_nItem; listNotify.m_nSubItem = m_nSubItem; listNotify.m_nExitChar = m_nExitChar; listNotify.m_lpszItemText = bValidDate ? _T( "1" ) : _T( "0" ); listNotify.m_lpItemDate = &stItemDate; // forward notification to parent FORWARD_WM_NOTIFY( wndParent, listNotify.m_hdrNotify.idFrom, &listNotify.m_hdrNotify, ::SendMessage ); } ShowWindow( SW_HIDE ); } LRESULT OnCloseUp( LPNMHDR /*lpNMHDR*/ ) { SetMsgHandled( FALSE ); SetFocus(); return TRUE; } UINT OnGetDlgCode( LPMSG /*lpMessage*/ ) { return DLGC_WANTALLKEYS; } void OnChar( TCHAR nChar, UINT /*nRepCnt*/, UINT /*nFlags*/ ) { switch ( nChar ) { case VK_TAB: case VK_RETURN: case VK_ESCAPE: { m_nExitChar = nChar; CWindow wndParent( GetParent() ); if ( wndParent.IsWindow() ) wndParent.SetFocus(); } break; default: SetMsgHandled( FALSE ); break; } } };