diff options
author | Eike Rathke <erack@redhat.com> | 2014-03-31 19:28:31 +0200 |
---|---|---|
committer | Eike Rathke <erack@redhat.com> | 2014-03-31 22:31:23 +0200 |
commit | e65141e93a540fc9fb4343ee65a5a7da7e3b1769 (patch) | |
tree | aab49525e80c516f8e7261a873e4ad2d3ca13af2 /sc/source/ui/docshell | |
parent | 94a10aa1d6af3520f4c4f31337a040eb42e8c39e (diff) |
re-enabled user-defined numeric fields for dBase export
Since commit f59e350d1733125055f1144f8b3b1b0a46f6d1ca it was impossible
to define a numeric field with a precision of less than 2 decimals, even
if all values were integers. It was also impossible to define a field
width larger than needed for any values in that column. Furthermore, the
integer part was shortened if the overall column's values resulted in
more precision than defined, but the overall length did not reach the
predefined length.
This does not change the behavior of the original intention of
f59e350d1733125055f1144f8b3b1b0a46f6d1ca to give the precision of number
formats precedence over precision defined in the column header, which is
debatable though because conflicts may silently change the field
definition.
Change-Id: I234c4bceaa1a6aadbd259cb8d9b6cb6f16bf91c2
Diffstat (limited to 'sc/source/ui/docshell')
-rw-r--r-- | sc/source/ui/docshell/docsh8.cxx | 53 |
1 files changed, 47 insertions, 6 deletions
diff --git a/sc/source/ui/docshell/docsh8.cxx b/sc/source/ui/docshell/docsh8.cxx index b7d049a9b52d..e35989354207 100644 --- a/sc/source/ui/docshell/docsh8.cxx +++ b/sc/source/ui/docshell/docsh8.cxx @@ -551,6 +551,7 @@ void lcl_GetColumnTypes( break; case 'N' : nDbType = sdbc::DataType::DECIMAL; + bTypeDefined = true; break; } if ( bTypeDefined && !nFieldLen && nToken > 2 ) @@ -562,6 +563,8 @@ void lcl_GetColumnTypes( if ( CharClass::isAsciiNumeric(aTmp) ) { nPrecision = aTmp.toInt32(); + if (nPrecision && nFieldLen < nPrecision+1) + nFieldLen = nPrecision + 1; // include decimal separator bPrecDefined = true; } } @@ -662,14 +665,52 @@ void lcl_GetColumnTypes( if ( nPrec > 15 ) nPrec = 15; if ( bPrecDefined && nPrecision != nPrec ) - { // Adjust length to predefined precision. - if ( nPrecision ) - nLen = nLen + ( nPrecision - nPrec ); + { + if (nPrecision < nPrec) + { + // This is a hairy case. User defined nPrecision but a + // number format has more precision. Modifying a dBase + // field may as well render the resulting file useless for + // an application that relies on its defined structure, + // especially if we are resaving an already existing file. + // So who's right, the user who (or the loaded file that) + // defined the field, or the user who applied the format? + // Commit f59e350d1733125055f1144f8b3b1b0a46f6d1ca gave the + // format a higher priority, which is debatable. + SAL_WARN( "sc", "lcl_GetColumnTypes: conflicting dBase field precision for " + << aFieldName << " (" << nPrecision << "<" << nPrec << ")"); + + // Adjust length to larger predefined integer part. There + // may be a reason that the field was prepared for larger + // numbers. + if (nFieldLen - nPrecision > nLen - nPrec) + nLen = nFieldLen - (nPrecision ? nPrecision+1 : 0) + 1 + nPrec; + // And override precision. + nPrecision = nPrec; + } + else + { + // Adjust length to predefined precision. + if ( nPrecision ) + nLen = nLen + ( nPrecision - nPrec ); + else + nLen -= nPrec+1; // also remove the decimal separator + } + } + if (nFieldLen < nLen) + { + if (!bTypeDefined) + nFieldLen = nLen; else - nLen -= nPrec+1; // also remove the decimal separator + { + // Again a hairy case and conflict. Furthermore, the + // larger overall length may be a result of only a higher + // precision obtained from formats. + SAL_WARN( "sc", "lcl_GetColumnTypes: conflicting dBase field length for " + << aFieldName << " (" << nFieldLen << "<" << nLen << ")"); + nFieldLen = nLen; + } } - if ( nLen > nFieldLen && !bTypeDefined ) - nFieldLen = nLen; if ( !bPrecDefined ) nPrecision = nPrec; if ( nFieldLen == 0 ) |