diff options
author | Eike Rathke <erack@redhat.com> | 2012-01-10 16:42:01 +0100 |
---|---|---|
committer | Eike Rathke <erack@redhat.com> | 2012-01-11 13:18:45 +0100 |
commit | 958cdbdcf5e35c04e259a69e972684060f1b3d12 (patch) | |
tree | 3ef304d9abb0c5efac583bcadc33f8bad49caea8 /svl | |
parent | 8ca1557b85188b7708930468d77412f51356e34c (diff) |
accept and display years < 100
+ Years < 100 without being hit by the 2 digits year magic can be entered by
preceding them with a leading 0 if at least 3 digits are present, e.g.
099-1-1 is year 99, not 1999.
+ Years < 100 in an yyyy format are always displayed as 0099.
Diffstat (limited to 'svl')
-rw-r--r-- | svl/source/numbers/zforfind.cxx | 29 | ||||
-rw-r--r-- | svl/source/numbers/zforfind.hxx | 19 | ||||
-rw-r--r-- | svl/source/numbers/zformat.cxx | 26 |
3 files changed, 61 insertions, 13 deletions
diff --git a/svl/source/numbers/zforfind.cxx b/svl/source/numbers/zforfind.cxx index ef76faca7763..3df9232c3b56 100644 --- a/svl/source/numbers/zforfind.cxx +++ b/svl/source/numbers/zforfind.cxx @@ -957,10 +957,14 @@ sal_uInt16 ImpSvNumberInputScan::ImplGetYear( sal_uInt16 nIndex ) { sal_uInt16 nYear = 0; - if (sStrArray[nNums[nIndex]].Len() <= 4) + xub_StrLen nLen = sStrArray[nNums[nIndex]].Len(); + if (nLen <= 4) { nYear = (sal_uInt16) sStrArray[nNums[nIndex]].ToInt32(); - nYear = SvNumberFormatter::ExpandTwoDigitYear( nYear, nYear2000 ); + // A year < 100 entered with at least 3 digits with leading 0 is taken + // as is without expansion. + if (nYear < 100 && nLen < 3) + nYear = SvNumberFormatter::ExpandTwoDigitYear( nYear, nYear2000 ); } return nYear; @@ -972,13 +976,22 @@ bool ImpSvNumberInputScan::MayBeIso8601() { if (nMayBeIso8601 == 0) { - if (nAnzNums >= 3 && nNums[0] < nAnzStrings && - sStrArray[nNums[0]].ToInt32() > 31) - nMayBeIso8601 = 1; - else - nMayBeIso8601 = 2; + nMayBeIso8601 = 1; + xub_StrLen nLen = ((nAnzNums >= 1 && nNums[0] < nAnzStrings) ? sStrArray[nNums[0]].Len() : 0); + if (nLen) + { + sal_Int32 n; + if (nAnzNums >= 3 && nNums[2] < nAnzStrings && + sStrArray[nNums[0]+1] == '-' && // separator year-month + (n = sStrArray[nNums[1]].ToInt32()) >= 1 && n <= 12 && // month + sStrArray[nNums[1]+1] == '-' && // separator month-day + (n = sStrArray[nNums[2]].ToInt32()) >= 1 && n <= 31) // day + // Year (nNums[0]) value not checked, may be anything, but + // length (number of digits) is checked. + nMayBeIso8601 = (nLen >= 4 ? 4 : (nLen == 3 ? 3 : (nLen > 0 ? 2 : 0))); + } } - return nMayBeIso8601 == 1; + return nMayBeIso8601 > 1; } //--------------------------------------------------------------------------- diff --git a/svl/source/numbers/zforfind.hxx b/svl/source/numbers/zforfind.hxx index 9c557b7e8303..02e08d4b31a3 100644 --- a/svl/source/numbers/zforfind.hxx +++ b/svl/source/numbers/zforfind.hxx @@ -69,8 +69,13 @@ public: /// get threshold of two-digit year input sal_uInt16 GetYear2000() const { return nYear2000; } - // Whether input may be a ISO 8601 date format, yyyy-mm-dd... - // checks if at least 3 numbers and first number>31 + /** Whether input may be an ISO 8601 date format, yyyy-mm-dd... + + Checks if input has at least 3 numbers for yyyy-mm-dd and the separator + is '-', and 1<=mm<=12 and 1<=dd<=31. + + @see nMayBeIso8601 + */ bool MayBeIso8601(); private: @@ -129,7 +134,15 @@ private: // number <= nYear2000 => 20xx // number > nYear2000 => 19xx sal_uInt16 nTimezonePos; // Index of timezone separator (+1) - sal_uInt8 nMayBeIso8601; // 0:=dontknowyet, 1:=yes, 2:=no + + /** State of ISO 8601 detection. + 0:= don't know yet + 1:= no + 2:= yes, <=2 digits in year + 3:= yes, 3 digits in year + 4:= yes, >=4 digits in year + */ + sal_uInt8 nMayBeIso8601; #ifdef _ZFORFIND_CXX // methods private to implementation void Reset(); // Reset all variables before start of analysis diff --git a/svl/source/numbers/zformat.cxx b/svl/source/numbers/zformat.cxx index d7969803459d..1976ec90afca 100644 --- a/svl/source/numbers/zformat.cxx +++ b/svl/source/numbers/zformat.cxx @@ -3387,8 +3387,19 @@ bool SvNumberformat::ImpGetDateOutput(double fNumber, { if ( bOtherCalendar ) SwitchToGregorianCalendar( aOrgCalendar, fOrgDateTime ); - OutString += rCal.getDisplayString( + String aYear = rCal.getDisplayString( CalendarDisplayCode::LONG_YEAR, nNatNum ); + if (aYear.Len() < 4) + { + // Ensure that year consists of at least 4 digits, so it + // can be distinguished from 2 digits display and edited + // without suddenly being hit by the 2-digit year magic. + String aZero; + aZero.Fill( 4 - aYear.Len(), sal_Unicode('0')); + ImpTransliterate( aZero, NumFor[nIx].GetNatNum()); + aYear.Insert( aZero, 0); + } + OutString += aYear; if ( bOtherCalendar ) SwitchToOtherCalendar( aOrgCalendar, fOrgDateTime ); } @@ -3710,8 +3721,19 @@ bool SvNumberformat::ImpGetDateTimeOutput(double fNumber, { if ( bOtherCalendar ) SwitchToGregorianCalendar( aOrgCalendar, fOrgDateTime ); - OutString += rCal.getDisplayString( + String aYear = rCal.getDisplayString( CalendarDisplayCode::LONG_YEAR, nNatNum ); + if (aYear.Len() < 4) + { + // Ensure that year consists of at least 4 digits, so it + // can be distinguished from 2 digits display and edited + // without suddenly being hit by the 2-digit year magic. + String aZero; + aZero.Fill( 4 - aYear.Len(), sal_Unicode('0')); + ImpTransliterate( aZero, NumFor[nIx].GetNatNum()); + aYear.Insert( aZero, 0); + } + OutString += aYear; if ( bOtherCalendar ) SwitchToOtherCalendar( aOrgCalendar, fOrgDateTime ); } |