summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEike Rathke <erack@redhat.com>2013-05-17 14:04:34 +0200
committerFridrich Strba <fridrich@documentfoundation.org>2013-05-17 14:28:06 +0000
commit5e159b9834731a0282e45d8e5f5bbaedb624dc6b (patch)
tree6f7d18107596d76e3a7e851fa3df31bb98fea396
parentb4aeed3b8dc402d72ae9a8b928babc228e2ead7a (diff)
resolved fdo#63805 max day of month of the intended month
Since 6619955e72c1c2f29a32e82478d19147c0d7610a Date::GetDaysInMonth() operates on the normalized value that corresponds to the actual values set at the Date instance, obtain and set number of days for the intended month instead of using the rolled-over date. (cherry picked from commit cd9d1bdf5e3351c929d5b651c009ee17b4d962c4) Conflicts: sc/source/core/data/table4.cxx tools/source/datetime/tdate.cxx Change-Id: Ia6b007675104f8e134b278f216c3bb48b72f061c Reviewed-on: https://gerrit.libreoffice.org/3939 Reviewed-by: Fridrich Strba <fridrich@documentfoundation.org> Tested-by: Fridrich Strba <fridrich@documentfoundation.org>
-rw-r--r--sc/source/core/data/table4.cxx3
-rw-r--r--tools/inc/tools/date.hxx7
-rw-r--r--tools/source/datetime/tdate.cxx30
3 files changed, 28 insertions, 12 deletions
diff --git a/sc/source/core/data/table4.cxx b/sc/source/core/data/table4.cxx
index cced07c41b1f..abc885ee471e 100644
--- a/sc/source/core/data/table4.cxx
+++ b/sc/source/core/data/table4.cxx
@@ -1245,8 +1245,7 @@ void ScTable::IncDate(double& rVal, sal_uInt16& nDayOfMonth, double nStep, FillD
{
aDate.SetMonth((sal_uInt16) nMonth);
aDate.SetYear((sal_uInt16) nYear);
- if ( nDayOfMonth > 28 )
- aDate.SetDay( Min( aDate.GetDaysInMonth(), nDayOfMonth ) );
+ aDate.SetDay( std::min( Date::GetDaysInMonth( nMonth, nYear), nDayOfMonth ) );
}
}
break;
diff --git a/tools/inc/tools/date.hxx b/tools/inc/tools/date.hxx
index 71cc65f3b4ad..5d2cb14a3acf 100644
--- a/tools/inc/tools/date.hxx
+++ b/tools/inc/tools/date.hxx
@@ -157,6 +157,13 @@ public:
TOOLS_DLLPUBLIC friend Date operator -( const Date& rDate, long nDays );
TOOLS_DLLPUBLIC friend long operator -( const Date& rDate1, const Date& rDate2 );
+ /** Obtain number of days in a month of a year.
+
+ Internally sanitizes nMonth to values 1 <= nMonth <= 12, does not
+ normalize values.
+ */
+ static sal_uInt16 GetDaysInMonth( sal_uInt16 nMonth, sal_uInt16 nYear );
+
/// Internally normalizes values.
static long DateToDays( sal_uInt16 nDay, sal_uInt16 nMonth, sal_uInt16 nYear );
/// Semantically identical to IsValidDate() member method.
diff --git a/tools/source/datetime/tdate.cxx b/tools/source/datetime/tdate.cxx
index 9d17ec68a3a1..0039d2245081 100644
--- a/tools/source/datetime/tdate.cxx
+++ b/tools/source/datetime/tdate.cxx
@@ -61,8 +61,7 @@ inline sal_Bool ImpIsLeapYear( sal_uInt16 nYear )
// -----------------------------------------------------------------------
// All callers must have sanitized or normalized month and year values!
-
-inline sal_uInt16 DaysInMonth( sal_uInt16 nMonth, sal_uInt16 nYear )
+inline sal_uInt16 ImplDaysInMonth( sal_uInt16 nMonth, sal_uInt16 nYear )
{
if ( nMonth != 2 )
return aDaysInMonth[nMonth-1];
@@ -75,6 +74,17 @@ inline sal_uInt16 DaysInMonth( sal_uInt16 nMonth, sal_uInt16 nYear )
}
}
+// static
+sal_uInt16 Date::GetDaysInMonth( sal_uInt16 nMonth, sal_uInt16 nYear )
+{
+ SAL_WARN_IF( nMonth < 1 || 12 < nMonth, "tools", "Date::GetDaysInMonth - nMonth out of bounds " << nMonth);
+ if (nMonth < 1)
+ nMonth = 1;
+ else if (12 < nMonth)
+ nMonth = 12;
+ return ImplDaysInMonth( nMonth, nYear);
+}
+
// -----------------------------------------------------------------------
long Date::DateToDays( sal_uInt16 nDay, sal_uInt16 nMonth, sal_uInt16 nYear )
@@ -86,7 +96,7 @@ long Date::DateToDays( sal_uInt16 nDay, sal_uInt16 nMonth, sal_uInt16 nYear )
nDays = ((sal_uIntPtr)nYear-1) * 365;
nDays += ((nYear-1) / 4) - ((nYear-1) / 100) + ((nYear-1) / 400);
for( sal_uInt16 i = 1; i < nMonth; i++ )
- nDays += DaysInMonth(i,nYear);
+ nDays += ImplDaysInMonth(i,nYear);
nDays += nDay;
return nDays;
}
@@ -127,9 +137,9 @@ static void DaysToDate( long nDays,
while ( bCalc );
rMonth = 1;
- while ( (sal_uIntPtr)nTempDays > DaysInMonth( rMonth, rYear ) )
+ while ( (sal_uIntPtr)nTempDays > ImplDaysInMonth( rMonth, rYear ) )
{
- nTempDays -= DaysInMonth( rMonth, rYear );
+ nTempDays -= ImplDaysInMonth( rMonth, rYear );
rMonth++;
}
rDay = (sal_uInt16)nTempDays;
@@ -213,7 +223,7 @@ sal_uInt16 Date::GetDayOfYear() const
Normalize( nDay, nMonth, nYear);
for( sal_uInt16 i = 1; i < nMonth; i++ )
- nDay = nDay + ::DaysInMonth( i, nYear ); // += yields a warning on MSVC, so don't use it
+ nDay = nDay + ::ImplDaysInMonth( i, nYear ); // += yields a warning on MSVC, so don't use it
return nDay;
}
@@ -318,7 +328,7 @@ sal_uInt16 Date::GetDaysInMonth() const
sal_uInt16 nYear = GetYear();
Normalize( nDay, nMonth, nYear);
- return DaysInMonth( nMonth, nYear );
+ return ImplDaysInMonth( nMonth, nYear );
}
// -----------------------------------------------------------------------
@@ -339,7 +349,7 @@ sal_Bool Date::IsValidAndGregorian() const
if ( !nMonth || (nMonth > 12) )
return sal_False;
- if ( !nDay || (nDay > DaysInMonth( nMonth, nYear )) )
+ if ( !nDay || (nDay > ImplDaysInMonth( nMonth, nYear )) )
return sal_False;
else if ( nYear <= 1582 )
{
@@ -368,7 +378,7 @@ bool Date::IsValidDate( sal_uInt16 nDay, sal_uInt16 nMonth, sal_uInt16 nYear )
{
if ( !nMonth || (nMonth > 12) )
return false;
- if ( !nDay || (nDay > DaysInMonth( nMonth, nYear )) )
+ if ( !nDay || (nDay > ImplDaysInMonth( nMonth, nYear )) )
return false;
return true;
}
@@ -422,7 +432,7 @@ bool Date::Normalize( sal_uInt16 & rDay, sal_uInt16 & rMonth, sal_uInt16 & rYear
}
}
sal_uInt16 nDays;
- while (rDay > (nDays = DaysInMonth( rMonth, rYear)))
+ while (rDay > (nDays = ImplDaysInMonth( rMonth, rYear)))
{
rDay -= nDays;
if (rMonth < 12)