(first->wDay == second->wDay);
}
-/* make sure that time is valid */
-static BOOL MONTHCAL_ValidateTime(SYSTEMTIME time)
+/* make sure that date fields are valid */
+static BOOL MONTHCAL_ValidateDate(const SYSTEMTIME *time)
{
- if(time.wMonth < 1 || time.wMonth > 12 ) return FALSE;
- if(time.wDayOfWeek > 6) return FALSE;
- if(time.wDay > MONTHCAL_MonthLength(time.wMonth, time.wYear))
+ if(time->wMonth < 1 || time->wMonth > 12 ) return FALSE;
+ if(time->wDayOfWeek > 6) return FALSE;
+ if(time->wDay > MONTHCAL_MonthLength(time->wMonth, time->wYear))
return FALSE;
return TRUE;
}
+/* Used in MCM_SETRANGE/MCM_SETSELRANGE to determine resulting time part.
+ Milliseconds are intentionaly not validated. */
+static BOOL MONTHCAL_ValidateTime(const SYSTEMTIME *time)
+{
+ if((time->wHour > 24) || (time->wMinute > 59) || (time->wSecond > 59))
+ return FALSE;
+ else
+ return TRUE;
+}
+
+/* Copies timestamp part only. Milliseconds are intentionaly not copied
+ cause it matches required behaviour for current use of this helper */
+static void MONTHCAL_CopyTime(const SYSTEMTIME *from, SYSTEMTIME *to)
+{
+ to->wHour = from->wHour;
+ to->wMinute = from->wMinute;
+ to->wSecond = from->wSecond;
+}
/* Note:Depending on DST, this may be offset by a day.
Need to find out if we're on a DST place & adjust the clock accordingly.
TRACE("%x %p\n", limits, range);
- if ((limits & GDTR_MIN && !MONTHCAL_ValidateTime(range[0])) ||
- (limits & GDTR_MAX && !MONTHCAL_ValidateTime(range[1])))
+ if ((limits & GDTR_MIN && !MONTHCAL_ValidateDate(&range[0])) ||
+ (limits & GDTR_MAX && !MONTHCAL_ValidateDate(&range[1])))
return FALSE;
if (limits & GDTR_MIN)
{
+ if (!MONTHCAL_ValidateTime(&range[0]))
+ MONTHCAL_CopyTime(&infoPtr->todaysDate, &range[0]);
+
infoPtr->minDate = range[0];
infoPtr->rangeValid |= GDTR_MIN;
}
if (limits & GDTR_MAX)
{
+ if (!MONTHCAL_ValidateTime(&range[1]))
+ MONTHCAL_CopyTime(&infoPtr->todaysDate, &range[1]);
+
infoPtr->maxDate = range[1];
infoPtr->rangeValid |= GDTR_MAX;
}
if(!curSel) return FALSE;
if(infoPtr->dwStyle & MCS_MULTISELECT) return FALSE;
- if(!MONTHCAL_ValidateTime(*curSel)) return FALSE;
+ if(!MONTHCAL_ValidateDate(curSel)) return FALSE;
infoPtr->minSel = *curSel;
infoPtr->maxSel = *curSel;
if(infoPtr->dwStyle & MCS_MULTISELECT)
{
- infoPtr->maxSel = range[1];
+ /* adjust timestamps */
+ if(!MONTHCAL_ValidateTime(&range[0]))
+ MONTHCAL_CopyTime(&infoPtr->todaysDate, &range[0]);
+ if(!MONTHCAL_ValidateTime(&range[1]))
+ MONTHCAL_CopyTime(&infoPtr->todaysDate, &range[1]);
+
infoPtr->minSel = range[0];
+ infoPtr->maxSel = range[1];
+
TRACE("[min,max]=[%d %d]\n", infoPtr->minSel.wDay, infoPtr->maxSel.wDay);
return TRUE;
}
static void test_monthcal(void)
{
HWND hwnd;
- SYSTEMTIME st[2], st1[2];
+ SYSTEMTIME st[2], st1[2], today;
int res, month_range;
hwnd = CreateWindowA(MONTHCAL_CLASSA, "MonthCal", WS_POPUP | WS_VISIBLE, CW_USEDEFAULT,
GetSystemTime(&st[0]);
st[1] = st[0];
+ SendMessage(hwnd, MCM_GETTODAY, 0, (LPARAM)&today);
+
/* Invalid date/time */
st[0].wYear = 2000;
/* Time should not matter */
st[1].wHour = st[1].wMinute = st[1].wSecond = 70;
+ st[1].wMilliseconds = 1200;
ok(SendMessage(hwnd, MCM_SETRANGE, GDTR_MAX, (LPARAM)st), "Failed to set MAX limit\n");
+ /* invalid timestamp is written back with today data and msecs untouched */
+ expect(today.wHour, st[1].wHour);
+ expect(today.wMinute, st[1].wMinute);
+ expect(today.wSecond, st[1].wSecond);
+ expect(1200, st[1].wMilliseconds);
+
ok(SendMessage(hwnd, MCM_GETRANGE, 0, (LPARAM)st1) == GDTR_MAX, "No limits should be set\n");
ok(st1[0].wYear != 2000, "Lover limit changed\n");
+ /* invalid timestamp should be replaced with today data, except msecs */
+ expect(today.wHour, st1[1].wHour);
+ expect(today.wMinute, st1[1].wMinute);
+ expect(today.wSecond, st1[1].wSecond);
+ expect(1200, st1[1].wMilliseconds);
+
+ /* Invalid date/time with invalid milliseconds only */
+ GetSystemTime(&st[0]);
+ st[1] = st[0];
+ /* Time should not matter */
+ st[1].wMilliseconds = 1200;
+ ok(SendMessage(hwnd, MCM_SETRANGE, GDTR_MAX, (LPARAM)st), "Failed to set MAX limit\n");
+ /* invalid milliseconds field doesn't lead to invalid timestamp */
+ expect(st[0].wHour, st[1].wHour);
+ expect(st[0].wMinute, st[1].wMinute);
+ expect(st[0].wSecond, st[1].wSecond);
+ expect(1200, st[1].wMilliseconds);
+
+ GetSystemTime(&st[0]);
st[1].wMonth = 0;
ok(!SendMessage(hwnd, MCM_SETRANGE, GDTR_MIN | GDTR_MAX, (LPARAM)st), "Should have failed to set limits\n");