1 /**************************************************************
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one
4 * or more contributor license agreements. See the NOTICE file
5 * distributed with this work for additional information
6 * regarding copyright ownership. The ASF licenses this file
7 * to you under the Apache License, Version 2.0 (the
8 * "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing,
14 * software distributed under the License is distributed on an
15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 * KIND, either express or implied. See the License for the
17 * specific language governing permissions and limitations
18 * under the License.
19 *
20 *************************************************************/
21
22
23
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_sc.hxx"
26
27 #undef SC_DLLIMPLEMENTATION
28
29 #include "global.hxx"
30 #include "scresid.hxx"
31 #include "impex.hxx"
32 #include "scuiasciiopt.hxx"
33 #include "asciiopt.hrc"
34 #include <tools/debug.hxx>
35 #include <rtl/tencinfo.h>
36 #include <unotools/transliterationwrapper.hxx>
37 // ause
38 #include "editutil.hxx"
39
40 #include <optutil.hxx>
41 #include <com/sun/star/uno/Any.hxx>
42 #include <com/sun/star/uno/Sequence.hxx>
43 #include "miscuno.hxx"
44
45 //! TODO make dynamic
46 const SCSIZE ASCIIDLG_MAXROWS = MAXROWCOUNT;
47
48
49 using namespace rtl;
50 using namespace com::sun::star::uno;
51
52 // Defines - CSV Import Preserve Options
53 #define FIXED_WIDTH "FixedWidth"
54 #define FROM_ROW "FromRow"
55 #define CHAR_SET "CharSet"
56 #define SEPARATORS "Separators"
57 #define TEXT_SEPARATORS "TextSeparators"
58 #define MERGE_DELIMITERS "MergeDelimiters"
59 #define QUOTED_AS_TEXT "QuotedFieldAsText"
60 #define DETECT_SPECIAL_NUM "DetectSpecialNumbers"
61 #define LANGUAGE "Language"
62 #define SEP_PATH "Office.Calc/Dialogs/CSVImport"
63
64 // ============================================================================
65
lcl_FillCombo(ComboBox & rCombo,const String & rList,sal_Unicode cSelect)66 void lcl_FillCombo( ComboBox& rCombo, const String& rList, sal_Unicode cSelect )
67 {
68 xub_StrLen i;
69 xub_StrLen nCount = rList.GetTokenCount('\t');
70 for ( i=0; i<nCount; i+=2 )
71 rCombo.InsertEntry( rList.GetToken(i,'\t') );
72
73 if ( cSelect )
74 {
75 String aStr;
76 for ( i=0; i<nCount; i+=2 )
77 if ( (sal_Unicode)rList.GetToken(i+1,'\t').ToInt32() == cSelect )
78 aStr = rList.GetToken(i,'\t');
79 if (!aStr.Len())
80 aStr = cSelect; // Ascii
81
82 rCombo.SetText(aStr);
83 }
84 }
85
lcl_CharFromCombo(ComboBox & rCombo,const String & rList)86 sal_Unicode lcl_CharFromCombo( ComboBox& rCombo, const String& rList )
87 {
88 sal_Unicode c = 0;
89 String aStr = rCombo.GetText();
90 if ( aStr.Len() )
91 {
92 xub_StrLen nCount = rList.GetTokenCount('\t');
93 for ( xub_StrLen i=0; i<nCount; i+=2 )
94 {
95 if ( ScGlobal::GetpTransliteration()->isEqual( aStr, rList.GetToken(i,'\t') ) )//CHINA001 if ( ScGlobal::GetpTransliteration()->isEqual( aStr, rList.GetToken(i,'\t') ) )
96 c = (sal_Unicode)rList.GetToken(i+1,'\t').ToInt32();
97 }
98 if (!c && aStr.Len())
99 {
100 sal_Unicode cFirst = aStr.GetChar( 0 );
101 // #i24235# first try the first character of the string directly
102 if( (aStr.Len() == 1) || (cFirst < '0') || (cFirst > '9') )
103 c = cFirst;
104 else // keep old behaviour for compatibility (i.e. "39" -> "'")
105 c = (sal_Unicode) aStr.ToInt32(); // Ascii
106 }
107 }
108 return c;
109 }
110
load_Separators(OUString & sFieldSeparators,OUString & sTextSeparators,bool & bMergeDelimiters,bool & bQuotedAsText,bool & bDetectSpecialNum,bool & bFixedWidth,sal_Int32 & nFromRow,sal_Int32 & nCharSet,sal_Int32 & nLanguage)111 static void load_Separators( OUString &sFieldSeparators, OUString &sTextSeparators,
112 bool &bMergeDelimiters, bool& bQuotedAsText, bool& bDetectSpecialNum,
113 bool &bFixedWidth, sal_Int32 &nFromRow, sal_Int32 &nCharSet,
114 sal_Int32& nLanguage )
115 {
116 Sequence<Any>aValues;
117 const Any *pProperties;
118 Sequence<OUString> aNames(9);
119 OUString* pNames = aNames.getArray();
120 ScLinkConfigItem aItem( OUString::createFromAscii( SEP_PATH ) );
121
122 pNames[0] = OUString::createFromAscii( MERGE_DELIMITERS );
123 pNames[1] = OUString::createFromAscii( SEPARATORS );
124 pNames[2] = OUString::createFromAscii( TEXT_SEPARATORS );
125 pNames[3] = OUString::createFromAscii( FIXED_WIDTH );
126 pNames[4] = OUString::createFromAscii( FROM_ROW );
127 pNames[5] = OUString::createFromAscii( CHAR_SET );
128 pNames[6] = OUString::createFromAscii( QUOTED_AS_TEXT );
129 pNames[7] = OUString::createFromAscii( DETECT_SPECIAL_NUM );
130 pNames[8] = OUString::createFromAscii( LANGUAGE );
131 aValues = aItem.GetProperties( aNames );
132 pProperties = aValues.getConstArray();
133 if( pProperties[1].hasValue() )
134 pProperties[1] >>= sFieldSeparators;
135
136 if( pProperties[2].hasValue() )
137 pProperties[2] >>= sTextSeparators;
138
139 if( pProperties[0].hasValue() )
140 bMergeDelimiters = ScUnoHelpFunctions::GetBoolFromAny( pProperties[0] );
141
142 if( pProperties[3].hasValue() )
143 bFixedWidth = ScUnoHelpFunctions::GetBoolFromAny( pProperties[3] );
144
145 if( pProperties[4].hasValue() )
146 pProperties[4] >>= nFromRow;
147
148 if( pProperties[5].hasValue() )
149 pProperties[5] >>= nCharSet;
150
151 if ( pProperties[6].hasValue() )
152 pProperties[6] >>= bQuotedAsText;
153
154 if ( pProperties[7].hasValue() )
155 pProperties[7] >>= bDetectSpecialNum;
156
157 if ( pProperties[8].hasValue() )
158 pProperties[8] >>= nLanguage;
159 }
160
save_Separators(String maSeparators,String maTxtSep,bool bMergeDelimiters,bool bQuotedAsText,bool bDetectSpecialNum,bool bFixedWidth,sal_Int32 nFromRow,sal_Int32 nCharSet,sal_Int32 nLanguage)161 static void save_Separators(
162 String maSeparators, String maTxtSep, bool bMergeDelimiters, bool bQuotedAsText,
163 bool bDetectSpecialNum, bool bFixedWidth, sal_Int32 nFromRow, sal_Int32 nCharSet, sal_Int32 nLanguage )
164 {
165 OUString sFieldSeparators = OUString( maSeparators );
166 OUString sTextSeparators = OUString( maTxtSep );
167 Sequence<Any> aValues;
168 Any *pProperties;
169 Sequence<OUString> aNames(9);
170 OUString* pNames = aNames.getArray();
171 ScLinkConfigItem aItem( OUString::createFromAscii( SEP_PATH ) );
172
173 pNames[0] = OUString::createFromAscii( MERGE_DELIMITERS );
174 pNames[1] = OUString::createFromAscii( SEPARATORS );
175 pNames[2] = OUString::createFromAscii( TEXT_SEPARATORS );
176 pNames[3] = OUString::createFromAscii( FIXED_WIDTH );
177 pNames[4] = OUString::createFromAscii( FROM_ROW );
178 pNames[5] = OUString::createFromAscii( CHAR_SET );
179 pNames[6] = OUString::createFromAscii( QUOTED_AS_TEXT );
180 pNames[7] = OUString::createFromAscii( DETECT_SPECIAL_NUM );
181 pNames[8] = OUString::createFromAscii( LANGUAGE );
182 aValues = aItem.GetProperties( aNames );
183 pProperties = aValues.getArray();
184 pProperties[1] <<= sFieldSeparators;
185 pProperties[2] <<= sTextSeparators;
186 ScUnoHelpFunctions::SetBoolInAny( pProperties[0], bMergeDelimiters );
187 ScUnoHelpFunctions::SetBoolInAny( pProperties[3], bFixedWidth );
188 pProperties[4] <<= nFromRow;
189 pProperties[5] <<= nCharSet;
190 pProperties[6] <<= static_cast<sal_Bool>(bQuotedAsText);
191 pProperties[7] <<= static_cast<sal_Bool>(bDetectSpecialNum);
192 pProperties[8] <<= nLanguage;
193
194 aItem.PutProperties(aNames, aValues);
195 }
196
197 // ----------------------------------------------------------------------------
198
ScImportAsciiDlg(Window * pParent,String aDatName,SvStream * pInStream,sal_Unicode cSep)199 ScImportAsciiDlg::ScImportAsciiDlg( Window* pParent,String aDatName,
200 SvStream* pInStream, sal_Unicode cSep ) :
201 ModalDialog ( pParent, ScResId( RID_SCDLG_ASCII ) ),
202 mpDatStream ( pInStream ),
203 mnStreamPos( pInStream ? pInStream->Tell() : 0 ),
204
205 mpRowPosArray( NULL ),
206 mnRowPosCount(0),
207
208 aFlFieldOpt ( this, ScResId( FL_FIELDOPT ) ),
209 aFtCharSet ( this, ScResId( FT_CHARSET ) ),
210 aLbCharSet ( this, ScResId( LB_CHARSET ) ),
211 aFtCustomLang( this, ScResId( FT_CUSTOMLANG ) ),
212 aLbCustomLang( this, ScResId( LB_CUSTOMLANG ) ),
213
214 aFtRow ( this, ScResId( FT_AT_ROW ) ),
215 aNfRow ( this, ScResId( NF_AT_ROW ) ),
216
217 aFlSepOpt ( this, ScResId( FL_SEPOPT ) ),
218 aRbFixed ( this, ScResId( RB_FIXED ) ),
219 aRbSeparated( this, ScResId( RB_SEPARATED ) ),
220
221 aCkbTab ( this, ScResId( CKB_TAB ) ),
222 aCkbSemicolon(this, ScResId( CKB_SEMICOLON ) ),
223 aCkbComma ( this, ScResId( CKB_COMMA ) ),
224 aCkbSpace ( this, ScResId( CKB_SPACE ) ),
225 aCkbOther ( this, ScResId( CKB_OTHER ) ),
226 aEdOther ( this, ScResId( ED_OTHER ) ),
227 aCkbAsOnce ( this, ScResId( CB_ASONCE) ),
228 aFlOtherOpt ( this, ScResId( FL_OTHER_OPTIONS ) ),
229
230 aFtTextSep ( this, ScResId( FT_TEXTSEP ) ),
231 aCbTextSep ( this, ScResId( CB_TEXTSEP ) ),
232
233 aCkbQuotedAsText( this, ScResId(CB_QUOTED_AS_TEXT) ),
234 aCkbDetectNumber( this, ScResId(CB_DETECT_SPECIAL_NUMBER) ),
235
236 aFlWidth ( this, ScResId( FL_WIDTH ) ),
237 aFtType ( this, ScResId( FT_TYPE ) ),
238 aLbType ( this, ScResId( LB_TYPE1 ) ),
239
240 maTableBox ( this, ScResId( CTR_TABLEBOX ) ),
241
242 aBtnOk ( this, ScResId( BTN_OK ) ),
243 aBtnCancel ( this, ScResId( BTN_CANCEL ) ),
244 aBtnHelp ( this, ScResId( BTN_HELP ) ),
245
246 aCharSetUser( ScResId( SCSTR_CHARSET_USER ) ),
247 aColumnUser ( ScResId( SCSTR_COLUMN_USER ) ),
248 aTextSepList( ScResId( SCSTR_TEXTSEP ) ),
249 mcTextSep ( ScAsciiOptions::cDefaultTextSep ),
250 maStrTextToColumns( ScResId( STR_TEXTTOCOLUMNS ) ),
251 mbFileImport(true)
252 {
253 FreeResource();
254 mbFileImport = aDatName.Len() > 0;
255
256 String aName = GetText();
257 // aDatName is empty if invoked during paste from clipboard.
258 if (mbFileImport)
259 {
260 aName.AppendAscii(RTL_CONSTASCII_STRINGPARAM(" - ["));
261 aName += aDatName;
262 aName += ']';
263 }
264 SetText( aName );
265
266 OUString sFieldSeparators;
267 OUString sTextSeparators;
268 bool bMergeDelimiters = false;
269 bool bFixedWidth = false;
270 bool bQuotedFieldAsText = false;
271 bool bDetectSpecialNum = false;
272 sal_Int32 nFromRow = 1;
273 sal_Int32 nCharSet = -1;
274 sal_Int32 nLanguage = 0;
275 if (mbFileImport)
276 // load separators only when importing csv files.
277 load_Separators (sFieldSeparators, sTextSeparators, bMergeDelimiters,
278 bQuotedFieldAsText, bDetectSpecialNum, bFixedWidth, nFromRow, nCharSet, nLanguage);
279 else
280 {
281 // #i115474# otherwise use sensible defaults
282 sFieldSeparators = OUString( cSep );
283 sTextSeparators = OUString( ScAsciiOptions::cDefaultTextSep );
284 }
285 maFieldSeparators = String(sFieldSeparators);
286
287 if( bMergeDelimiters )
288 aCkbAsOnce.Check();
289 if (bQuotedFieldAsText)
290 aCkbQuotedAsText.Check();
291 if (bDetectSpecialNum)
292 aCkbDetectNumber.Check();
293 if( bFixedWidth )
294 aRbFixed.Check();
295 if( nFromRow != 1 )
296 aNfRow.SetValue( nFromRow );
297
298 ByteString bString(maFieldSeparators,RTL_TEXTENCODING_MS_1252);
299 const sal_Char *aSep = bString.GetBuffer();
300 int len = maFieldSeparators.Len();
301 for (int i = 0; i < len; ++i)
302 {
303 switch( aSep[i] )
304 {
305 case '\t': aCkbTab.Check(); break;
306 case ';': aCkbSemicolon.Check(); break;
307 case ',': aCkbComma.Check(); break;
308 case ' ': aCkbSpace.Check(); break;
309 default:
310 aCkbOther.Check();
311 aEdOther.SetText( aEdOther.GetText() + OUString( aSep[i] ) );
312 }
313 }
314
315 // Get Separators from the dialog
316 maFieldSeparators = GetSeparators();
317
318 // Clipboard is always Unicode, else detect.
319 rtl_TextEncoding ePreselectUnicode = (mbFileImport ?
320 RTL_TEXTENCODING_DONTKNOW : RTL_TEXTENCODING_UNICODE);
321 // Sniff for Unicode / not
322 if( ePreselectUnicode == RTL_TEXTENCODING_DONTKNOW && mpDatStream )
323 {
324 Seek( 0 );
325 mpDatStream->StartReadingUnicodeText( RTL_TEXTENCODING_DONTKNOW );
326 sal_uLong nUniPos = mpDatStream->Tell();
327 switch (nUniPos)
328 {
329 case 2:
330 ePreselectUnicode = RTL_TEXTENCODING_UNICODE; // UTF-16
331 break;
332 case 3:
333 ePreselectUnicode = RTL_TEXTENCODING_UTF8; // UTF-8
334 break;
335 case 0:
336 {
337 sal_uInt16 n;
338 *mpDatStream >> n;
339 // Assume that normal ASCII/ANSI/ISO/etc. text doesn't start with
340 // control characters except CR,LF,TAB
341 if ( (n & 0xff00) < 0x2000 )
342 {
343 switch ( n & 0xff00 )
344 {
345 case 0x0900 :
346 case 0x0a00 :
347 case 0x0d00 :
348 break;
349 default:
350 ePreselectUnicode = RTL_TEXTENCODING_UNICODE; // UTF-16
351 }
352 }
353 mpDatStream->Seek(0);
354 }
355 break;
356 default:
357 ; // nothing
358 }
359 mnStreamPos = mpDatStream->Tell();
360 }
361
362 aNfRow.SetModifyHdl( LINK( this, ScImportAsciiDlg, FirstRowHdl ) );
363
364 // *** Separator characters ***
365 lcl_FillCombo( aCbTextSep, aTextSepList, mcTextSep );
366 aCbTextSep.SetText( sTextSeparators );
367
368 Link aSeparatorHdl =LINK( this, ScImportAsciiDlg, SeparatorHdl );
369 aCbTextSep.SetSelectHdl( aSeparatorHdl );
370 aCbTextSep.SetModifyHdl( aSeparatorHdl );
371 aCkbTab.SetClickHdl( aSeparatorHdl );
372 aCkbSemicolon.SetClickHdl( aSeparatorHdl );
373 aCkbComma.SetClickHdl( aSeparatorHdl );
374 aCkbAsOnce.SetClickHdl( aSeparatorHdl );
375 aCkbQuotedAsText.SetClickHdl( aSeparatorHdl );
376 aCkbDetectNumber.SetClickHdl( aSeparatorHdl );
377 aCkbSpace.SetClickHdl( aSeparatorHdl );
378 aCkbOther.SetClickHdl( aSeparatorHdl );
379 aEdOther.SetModifyHdl( aSeparatorHdl );
380
381 // *** text encoding ListBox ***
382 // all encodings allowed, including Unicode, but subsets are excluded
383 aLbCharSet.FillFromTextEncodingTable( sal_True );
384 // Insert one "SYSTEM" entry for compatibility in AsciiOptions and system
385 // independent document linkage.
386 aLbCharSet.InsertTextEncoding( RTL_TEXTENCODING_DONTKNOW, aCharSetUser );
387 aLbCharSet.SelectTextEncoding( ePreselectUnicode == RTL_TEXTENCODING_DONTKNOW ?
388 gsl_getSystemTextEncoding() : ePreselectUnicode );
389
390 if( nCharSet >= 0 && ePreselectUnicode == RTL_TEXTENCODING_DONTKNOW )
391 aLbCharSet.SelectEntryPos( static_cast<sal_uInt16>(nCharSet) );
392
393 SetSelectedCharSet();
394 aLbCharSet.SetSelectHdl( LINK( this, ScImportAsciiDlg, CharSetHdl ) );
395
396 aLbCustomLang.SetLanguageList(
397 LANG_LIST_ALL | LANG_LIST_ONLY_KNOWN, false, false);
398 aLbCustomLang.InsertLanguage(LANGUAGE_SYSTEM);
399 aLbCustomLang.SelectLanguage(static_cast<LanguageType>(nLanguage), true);
400
401 // *** column type ListBox ***
402 xub_StrLen nCount = aColumnUser.GetTokenCount();
403 for (xub_StrLen i=0; i<nCount; i++)
404 aLbType.InsertEntry( aColumnUser.GetToken( i ) );
405
406 aLbType.SetSelectHdl( LINK( this, ScImportAsciiDlg, LbColTypeHdl ) );
407 aFtType.Disable();
408 aLbType.Disable();
409
410 // *** table box preview ***
411 maTableBox.SetUpdateTextHdl( LINK( this, ScImportAsciiDlg, UpdateTextHdl ) );
412 maTableBox.InitTypes( aLbType );
413 maTableBox.SetColTypeHdl( LINK( this, ScImportAsciiDlg, ColTypeHdl ) );
414
415 aRbSeparated.SetClickHdl( LINK( this, ScImportAsciiDlg, RbSepFixHdl ) );
416 aRbFixed.SetClickHdl( LINK( this, ScImportAsciiDlg, RbSepFixHdl ) );
417
418 SetupSeparatorCtrls();
419 RbSepFixHdl( &aRbFixed );
420
421 UpdateVertical();
422
423 maTableBox.Execute( CSVCMD_NEWCELLTEXTS );
424
425 aEdOther.SetAccessibleName(aCkbOther.GetText());
426 aEdOther.SetAccessibleRelationLabeledBy(&aCkbOther);
427 }
428
429
~ScImportAsciiDlg()430 ScImportAsciiDlg::~ScImportAsciiDlg()
431 {
432 delete[] mpRowPosArray;
433 }
434
435
436 // ----------------------------------------------------------------------------
437
GetLine(sal_uLong nLine,String & rText)438 bool ScImportAsciiDlg::GetLine( sal_uLong nLine, String &rText )
439 {
440 if (nLine >= ASCIIDLG_MAXROWS || !mpDatStream)
441 return false;
442
443 bool bRet = true;
444 bool bFixed = aRbFixed.IsChecked();
445
446 if (!mpRowPosArray)
447 mpRowPosArray = new sal_uLong[ASCIIDLG_MAXROWS + 2];
448
449 if (!mnRowPosCount) // complete re-fresh
450 {
451 memset( mpRowPosArray, 0, sizeof(mpRowPosArray[0]) * (ASCIIDLG_MAXROWS+2));
452
453 Seek(0);
454 mpDatStream->StartReadingUnicodeText( mpDatStream->GetStreamCharSet() );
455
456 mnStreamPos = mpDatStream->Tell();
457 mpRowPosArray[mnRowPosCount] = mnStreamPos;
458 }
459
460 if (nLine >= mnRowPosCount)
461 {
462 // need to work out some more line information
463 do
464 {
465 if (!Seek( mpRowPosArray[mnRowPosCount]) ||
466 mpDatStream->GetError() != ERRCODE_NONE ||
467 mpDatStream->IsEof())
468 {
469 bRet = false;
470 break;
471 }
472 mpDatStream->ReadCsvLine( rText, !bFixed, maFieldSeparators,
473 mcTextSep);
474 mnStreamPos = mpDatStream->Tell();
475 mpRowPosArray[++mnRowPosCount] = mnStreamPos;
476 } while (nLine >= mnRowPosCount &&
477 mpDatStream->GetError() == ERRCODE_NONE &&
478 !mpDatStream->IsEof());
479 if (mpDatStream->IsEof() &&
480 mnStreamPos == mpRowPosArray[mnRowPosCount-1])
481 {
482 // the very end, not even an empty line read
483 bRet = false;
484 --mnRowPosCount;
485 }
486 }
487 else
488 {
489 Seek( mpRowPosArray[nLine]);
490 mpDatStream->ReadCsvLine( rText, !bFixed, maFieldSeparators, mcTextSep);
491 mnStreamPos = mpDatStream->Tell();
492 }
493
494 // #107455# If the file content isn't unicode, ReadUniStringLine
495 // may try to seek beyond the file's end and cause a CANTSEEK error
496 // (depending on the stream type). The error code has to be cleared,
497 // or further read operations (including non-unicode) will fail.
498 if ( mpDatStream->GetError() == ERRCODE_IO_CANTSEEK )
499 mpDatStream->ResetError();
500
501 return bRet;
502 }
503
504
GetOptions(ScAsciiOptions & rOpt)505 void ScImportAsciiDlg::GetOptions( ScAsciiOptions& rOpt )
506 {
507 rOpt.SetCharSet( meCharSet );
508 rOpt.SetCharSetSystem( mbCharSetSystem );
509 rOpt.SetLanguage(aLbCustomLang.GetSelectLanguage());
510 rOpt.SetFixedLen( aRbFixed.IsChecked() );
511 rOpt.SetStartRow( (long)aNfRow.GetValue() );
512 maTableBox.FillColumnData( rOpt );
513 if( aRbSeparated.IsChecked() )
514 {
515 rOpt.SetFieldSeps( GetSeparators() );
516 rOpt.SetMergeSeps( aCkbAsOnce.IsChecked() );
517 rOpt.SetTextSep( lcl_CharFromCombo( aCbTextSep, aTextSepList ) );
518 }
519
520 rOpt.SetQuotedAsText(aCkbQuotedAsText.IsChecked());
521 rOpt.SetDetectSpecialNumber(aCkbDetectNumber.IsChecked());
522 }
523
SetTextToColumnsMode()524 void ScImportAsciiDlg::SetTextToColumnsMode()
525 {
526 SetText( maStrTextToColumns );
527 aFtCharSet.Disable();
528 aLbCharSet.Disable();
529 aFtCustomLang.Disable();
530 aLbCustomLang.SelectLanguage(LANGUAGE_SYSTEM);
531 aLbCustomLang.Disable();
532 aFtRow.Disable();
533 aNfRow.Disable();
534
535 // Quoted field as text option is not used for text-to-columns mode.
536 aCkbQuotedAsText.Check(false);
537 aCkbQuotedAsText.Disable();
538
539 // Always detect special numbers for text-to-columns mode.
540 aCkbDetectNumber.Check();
541 aCkbDetectNumber.Disable();
542 }
543
SaveParameters()544 void ScImportAsciiDlg::SaveParameters()
545 {
546 if (!mbFileImport)
547 // We save parameters only for file import.
548 return;
549
550 save_Separators( maFieldSeparators, aCbTextSep.GetText(), aCkbAsOnce.IsChecked(),
551 aCkbQuotedAsText.IsChecked(), aCkbDetectNumber.IsChecked(),
552 aRbFixed.IsChecked(),
553 static_cast<sal_Int32>(aNfRow.GetValue()),
554 static_cast<sal_Int32>(aLbCharSet.GetSelectEntryPos()),
555 static_cast<sal_Int32>(aLbCustomLang.GetSelectLanguage()) );
556 }
557
SetSelectedCharSet()558 void ScImportAsciiDlg::SetSelectedCharSet()
559 {
560 meCharSet = aLbCharSet.GetSelectTextEncoding();
561 mbCharSetSystem = (meCharSet == RTL_TEXTENCODING_DONTKNOW);
562 if( mbCharSetSystem )
563 meCharSet = gsl_getSystemTextEncoding();
564 }
565
GetSeparators() const566 String ScImportAsciiDlg::GetSeparators() const
567 {
568 String aSepChars;
569 if( aCkbTab.IsChecked() )
570 aSepChars += '\t';
571 if( aCkbSemicolon.IsChecked() )
572 aSepChars += ';';
573 if( aCkbComma.IsChecked() )
574 aSepChars += ',';
575 if( aCkbSpace.IsChecked() )
576 aSepChars += ' ';
577 if( aCkbOther.IsChecked() )
578 aSepChars += aEdOther.GetText();
579 return aSepChars;
580 }
581
SetupSeparatorCtrls()582 void ScImportAsciiDlg::SetupSeparatorCtrls()
583 {
584 sal_Bool bEnable = aRbSeparated.IsChecked();
585 aCkbTab.Enable( bEnable );
586 aCkbSemicolon.Enable( bEnable );
587 aCkbComma.Enable( bEnable );
588 aCkbSpace.Enable( bEnable );
589 aCkbOther.Enable( bEnable );
590 aEdOther.Enable( bEnable );
591 aCkbAsOnce.Enable( bEnable );
592 aFtTextSep.Enable( bEnable );
593 aCbTextSep.Enable( bEnable );
594 }
595
UpdateVertical()596 void ScImportAsciiDlg::UpdateVertical()
597 {
598 mnRowPosCount = 0;
599 if (mpDatStream)
600 mpDatStream->SetStreamCharSet(meCharSet);
601 }
602
603
604 // ----------------------------------------------------------------------------
605
IMPL_LINK(ScImportAsciiDlg,RbSepFixHdl,RadioButton *,pButton)606 IMPL_LINK( ScImportAsciiDlg, RbSepFixHdl, RadioButton*, pButton )
607 {
608 DBG_ASSERT( pButton, "ScImportAsciiDlg::RbSepFixHdl - missing sender" );
609
610 if( (pButton == &aRbFixed) || (pButton == &aRbSeparated) )
611 {
612 SetPointer( Pointer( POINTER_WAIT ) );
613 if( aRbFixed.IsChecked() )
614 maTableBox.SetFixedWidthMode();
615 else
616 maTableBox.SetSeparatorsMode();
617 SetPointer( Pointer( POINTER_ARROW ) );
618
619 SetupSeparatorCtrls();
620 }
621 return 0;
622 }
623
IMPL_LINK(ScImportAsciiDlg,SeparatorHdl,Control *,pCtrl)624 IMPL_LINK( ScImportAsciiDlg, SeparatorHdl, Control*, pCtrl )
625 {
626 DBG_ASSERT( pCtrl, "ScImportAsciiDlg::SeparatorHdl - missing sender" );
627 DBG_ASSERT( !aRbFixed.IsChecked(), "ScImportAsciiDlg::SeparatorHdl - not allowed in fixed width" );
628
629 /* #i41550# First update state of the controls. The GetSeparators()
630 function needs final state of the check boxes. */
631 if( (pCtrl == &aCkbOther) && aCkbOther.IsChecked() )
632 aEdOther.GrabFocus();
633 else if( pCtrl == &aEdOther )
634 aCkbOther.Check( aEdOther.GetText().Len() > 0 );
635
636 String aOldFldSeps( maFieldSeparators);
637 maFieldSeparators = GetSeparators();
638 sal_Unicode cOldSep = mcTextSep;
639 mcTextSep = lcl_CharFromCombo( aCbTextSep, aTextSepList );
640 // Any separator changed may result in completely different lines due to
641 // embedded line breaks.
642 if (cOldSep != mcTextSep || aOldFldSeps != maFieldSeparators)
643 UpdateVertical();
644
645 maTableBox.Execute( CSVCMD_NEWCELLTEXTS );
646 return 0;
647 }
648
IMPL_LINK(ScImportAsciiDlg,CharSetHdl,SvxTextEncodingBox *,pCharSetBox)649 IMPL_LINK( ScImportAsciiDlg, CharSetHdl, SvxTextEncodingBox*, pCharSetBox )
650 {
651 DBG_ASSERT( pCharSetBox, "ScImportAsciiDlg::CharSetHdl - missing sender" );
652
653 if( (pCharSetBox == &aLbCharSet) && (pCharSetBox->GetSelectEntryCount() == 1) )
654 {
655 SetPointer( Pointer( POINTER_WAIT ) );
656 CharSet eOldCharSet = meCharSet;
657 SetSelectedCharSet();
658 // switching char-set invalidates 8bit -> String conversions
659 if (eOldCharSet != meCharSet)
660 UpdateVertical();
661
662 maTableBox.Execute( CSVCMD_NEWCELLTEXTS );
663 SetPointer( Pointer( POINTER_ARROW ) );
664 }
665 return 0;
666 }
667
IMPL_LINK(ScImportAsciiDlg,FirstRowHdl,NumericField *,pNumField)668 IMPL_LINK( ScImportAsciiDlg, FirstRowHdl, NumericField*, pNumField )
669 {
670 DBG_ASSERT( pNumField, "ScImportAsciiDlg::FirstRowHdl - missing sender" );
671 maTableBox.Execute( CSVCMD_SETFIRSTIMPORTLINE, sal::static_int_cast<sal_Int32>( pNumField->GetValue() - 1 ) );
672 return 0;
673 }
674
IMPL_LINK(ScImportAsciiDlg,LbColTypeHdl,ListBox *,pListBox)675 IMPL_LINK( ScImportAsciiDlg, LbColTypeHdl, ListBox*, pListBox )
676 {
677 DBG_ASSERT( pListBox, "ScImportAsciiDlg::LbColTypeHdl - missing sender" );
678 if( pListBox == &aLbType )
679 maTableBox.Execute( CSVCMD_SETCOLUMNTYPE, pListBox->GetSelectEntryPos() );
680 return 0;
681 }
682
IMPL_LINK(ScImportAsciiDlg,UpdateTextHdl,ScCsvTableBox *,EMPTYARG)683 IMPL_LINK( ScImportAsciiDlg, UpdateTextHdl, ScCsvTableBox*, EMPTYARG )
684 {
685 sal_Int32 nBaseLine = maTableBox.GetFirstVisLine();
686 sal_Int32 nRead = maTableBox.GetVisLineCount();
687 // If mnRowPosCount==0, this is an initializing call, read ahead for row
688 // count and resulting scroll bar size and position to be able to scroll at
689 // all. When adding lines, read only the amount of next lines to be
690 // displayed.
691 if (!mnRowPosCount || nRead > CSV_PREVIEW_LINES)
692 nRead = CSV_PREVIEW_LINES;
693
694 sal_Int32 i;
695 for (i = 0; i < nRead; i++)
696 {
697 if (!GetLine( nBaseLine + i, maPreviewLine[i]))
698 break;
699 }
700 for (; i < CSV_PREVIEW_LINES; i++)
701 maPreviewLine[i].Erase();
702
703 maTableBox.Execute( CSVCMD_SETLINECOUNT, mnRowPosCount);
704 bool bMergeSep = (aCkbAsOnce.IsChecked() == sal_True);
705 maTableBox.SetUniStrings( maPreviewLine, maFieldSeparators, mcTextSep, bMergeSep);
706
707 return 0;
708 }
709
IMPL_LINK(ScImportAsciiDlg,ColTypeHdl,ScCsvTableBox *,pTableBox)710 IMPL_LINK( ScImportAsciiDlg, ColTypeHdl, ScCsvTableBox*, pTableBox )
711 {
712 DBG_ASSERT( pTableBox, "ScImportAsciiDlg::ColTypeHdl - missing sender" );
713
714 sal_Int32 nType = pTableBox->GetSelColumnType();
715 sal_Int32 nTypeCount = aLbType.GetEntryCount();
716 bool bEmpty = (nType == CSV_TYPE_MULTI);
717 bool bEnable = ((0 <= nType) && (nType < nTypeCount)) || bEmpty;
718
719 aFtType.Enable( bEnable );
720 aLbType.Enable( bEnable );
721
722 Link aSelHdl = aLbType.GetSelectHdl();
723 aLbType.SetSelectHdl( Link() );
724 if( bEmpty )
725 aLbType.SetNoSelection();
726 else if( bEnable )
727 aLbType.SelectEntryPos( static_cast< sal_uInt16 >( nType ) );
728 aLbType.SetSelectHdl( aSelHdl );
729
730 return 0;
731 }
732