1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include <comphelper/processfactory.hxx>
21 #include <comphelper/types.hxx>
22 #include <vcl/msgbox.hxx>
23 #include <svx/dataaccessdescriptor.hxx>
24 #include <sfx2/viewfrm.hxx>
26 #include <com/sun/star/sdb/CommandType.hpp>
27 #include <com/sun/star/sdb/XCompletedExecution.hpp>
28 #include <com/sun/star/sdbc/XRow.hpp>
29 #include <com/sun/star/sdbc/XRowSet.hpp>
30 #include <com/sun/star/sdbc/XResultSetMetaDataSupplier.hpp>
31 #include <com/sun/star/sdbcx/XRowLocate.hpp>
32 #include <com/sun/star/task/InteractionHandler.hpp>
33 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
34 #include <com/sun/star/beans/XPropertySet.hpp>
35 #include <com/sun/star/frame/XDispatchProvider.hpp>
36 #include <com/sun/star/frame/FrameSearchFlag.hpp>
37 #include <com/sun/star/view/XSelectionSupplier.hpp>
40 #include "dbdocfun.hxx"
42 #include "globstr.hrc"
43 #include "scerrors.hxx"
45 #include "markdata.hxx"
46 #include "undodat.hxx"
47 #include "progress.hxx"
48 #include "patattr.hxx"
49 #include "docpool.hxx"
51 #include "dbdocutl.hxx"
52 #include "editable.hxx"
54 #include "miscuno.hxx"
55 #include "chgtrack.hxx"
57 using namespace com::sun::star
;
59 #define SC_SERVICE_ROWSET "com.sun.star.sdb.RowSet"
61 //! move to a header file?
62 #define SC_DBPROP_DATASOURCENAME "DataSourceName"
63 #define SC_DBPROP_COMMAND "Command"
64 #define SC_DBPROP_COMMANDTYPE "CommandType"
66 void ScDBDocFunc::ShowInBeamer( const ScImportParam
& rParam
, SfxViewFrame
* pFrame
)
68 // called after opening the database beamer
70 if ( !pFrame
|| !rParam
.bImport
)
73 uno::Reference
<frame::XFrame
> xFrame
= pFrame
->GetFrame().GetFrameInterface();
74 uno::Reference
<frame::XDispatchProvider
> xDP(xFrame
, uno::UNO_QUERY
);
76 uno::Reference
<frame::XFrame
> xBeamerFrame
= xFrame
->findFrame(
78 frame::FrameSearchFlag::CHILDREN
);
79 if (xBeamerFrame
.is())
81 uno::Reference
<frame::XController
> xController
= xBeamerFrame
->getController();
82 uno::Reference
<view::XSelectionSupplier
> xControllerSelection(xController
, uno::UNO_QUERY
);
83 if (xControllerSelection
.is())
85 sal_Int32 nType
= rParam
.bSql
? sdb::CommandType::COMMAND
:
86 ( (rParam
.nType
== ScDbQuery
) ? sdb::CommandType::QUERY
:
87 sdb::CommandType::TABLE
);
89 ::svx::ODataAccessDescriptor aSelection
;
90 aSelection
.setDataSource(rParam
.aDBName
);
91 aSelection
[svx::daCommand
] <<= rParam
.aStatement
;
92 aSelection
[svx::daCommandType
] <<= nType
;
94 xControllerSelection
->select(uno::makeAny(aSelection
.createPropertyValueSequence()));
98 OSL_FAIL("no selection supplier in the beamer!");
103 // -----------------------------------------------------------------
105 bool ScDBDocFunc::DoImportUno( const ScAddress
& rPos
,
106 const uno::Sequence
<beans::PropertyValue
>& aArgs
)
108 svx::ODataAccessDescriptor
aDesc( aArgs
); // includes selection and result set
110 // create database range
111 ScDBData
* pDBData
= rDocShell
.GetDBData( ScRange(rPos
), SC_DB_IMPORT
, SC_DBSEL_KEEP
);
112 DBG_ASSERT(pDBData
, "can't create DB data");
113 OUString sTarget
= pDBData
->GetName();
115 UpdateImport( sTarget
, aDesc
);
120 // -----------------------------------------------------------------
122 bool ScDBDocFunc::DoImport( SCTAB nTab
, const ScImportParam
& rParam
,
123 const svx::ODataAccessDescriptor
* pDescriptor
, bool bRecord
, bool bAddrInsert
)
125 ScDocument
* pDoc
= rDocShell
.GetDocument();
126 ScChangeTrack
*pChangeTrack
= NULL
;
127 ScRange aChangedRange
;
129 if (bRecord
&& !pDoc
->IsUndoEnabled())
132 ScDBData
* pDBData
= NULL
;
135 pDBData
= pDoc
->GetDBAtArea( nTab
, rParam
.nCol1
, rParam
.nRow1
,
136 rParam
.nCol2
, rParam
.nRow2
);
139 OSL_FAIL( "DoImport: no DBData" );
144 Window
* pWaitWin
= rDocShell
.GetActiveDialogParent();
146 pWaitWin
->EnterWait();
147 ScDocShellModificator
aModificator( rDocShell
);
149 sal_Bool bSuccess
= false;
150 sal_Bool bApi
= false; //! pass as argument
151 sal_Bool bTruncated
= false; // for warning
152 sal_uInt16 nErrStringId
= 0;
153 OUString aErrorMessage
;
155 SCCOL nCol
= rParam
.nCol1
;
156 SCROW nRow
= rParam
.nRow1
;
157 SCCOL nEndCol
= nCol
; // end of resulting database area
158 SCROW nEndRow
= nRow
;
161 sal_Bool bDoSelection
= false;
162 sal_Bool bRealSelection
= false; // sal_True if not everything is selected
163 sal_Bool bBookmarkSelection
= sal_False
;
164 sal_Int32 nListPos
= 0;
165 sal_Int32 nRowsRead
= 0;
166 sal_Int32 nListCount
= 0;
168 uno::Sequence
<uno::Any
> aSelection
;
169 if ( pDescriptor
&& pDescriptor
->has(svx::daSelection
) )
171 (*pDescriptor
)[svx::daSelection
] >>= aSelection
;
172 nListCount
= aSelection
.getLength();
173 if ( nListCount
> 0 )
176 if ( pDescriptor
->has(svx::daBookmarkSelection
) )
177 bBookmarkSelection
= ScUnoHelpFunctions::GetBoolFromAny( (*pDescriptor
)[svx::daBookmarkSelection
] );
178 if ( bBookmarkSelection
)
180 // From bookmarks, there's no way to detect if all records are selected.
181 // Rely on base to pass no selection in that case.
182 bRealSelection
= true;
187 uno::Reference
<sdbc::XResultSet
> xResultSet
;
188 if ( pDescriptor
&& pDescriptor
->has(svx::daCursor
) )
189 xResultSet
.set((*pDescriptor
)[svx::daCursor
], uno::UNO_QUERY
);
191 // ImportDoc - also used for Redo
192 ScDocument
* pImportDoc
= new ScDocument( SCDOCMODE_UNDO
);
193 pImportDoc
->InitUndo( pDoc
, nTab
, nTab
);
196 // get data from database into import document
202 // only text (title is still needed, for the cancel button)
203 ScProgress
aProgress( &rDocShell
, ScGlobal::GetRscString(STR_UNDO_IMPORTDATA
), 0 );
205 uno::Reference
<sdbc::XRowSet
> xRowSet
= uno::Reference
<sdbc::XRowSet
>(
206 xResultSet
, uno::UNO_QUERY
);
207 sal_Bool bDispose
= false;
211 xRowSet
= uno::Reference
<sdbc::XRowSet
>(
212 comphelper::getProcessServiceFactory()->createInstance(
213 OUString( SC_SERVICE_ROWSET
) ),
215 uno::Reference
<beans::XPropertySet
> xRowProp( xRowSet
, uno::UNO_QUERY
);
216 OSL_ENSURE( xRowProp
.is(), "can't get RowSet" );
220 // set source parameters
223 sal_Int32 nType
= rParam
.bSql
? sdb::CommandType::COMMAND
:
224 ( (rParam
.nType
== ScDbQuery
) ? sdb::CommandType::QUERY
:
225 sdb::CommandType::TABLE
);
228 aAny
<<= rParam
.aDBName
;
229 xRowProp
->setPropertyValue(
230 OUString(SC_DBPROP_DATASOURCENAME
), aAny
);
232 aAny
<<= rParam
.aStatement
;
233 xRowProp
->setPropertyValue(
234 OUString(SC_DBPROP_COMMAND
), aAny
);
237 xRowProp
->setPropertyValue(
238 OUString(SC_DBPROP_COMMANDTYPE
), aAny
);
240 uno::Reference
<sdb::XCompletedExecution
> xExecute( xRowSet
, uno::UNO_QUERY
);
243 uno::Reference
<task::XInteractionHandler
> xHandler(
244 task::InteractionHandler::createWithParent(comphelper::getProcessComponentContext(), 0),
245 uno::UNO_QUERY_THROW
);
246 xExecute
->executeWithCompletion( xHandler
);
255 // get column descriptions
259 uno::Reference
<sdbc::XResultSetMetaData
> xMeta
;
260 uno::Reference
<sdbc::XResultSetMetaDataSupplier
> xMetaSupp( xRowSet
, uno::UNO_QUERY
);
261 if ( xMetaSupp
.is() )
262 xMeta
= xMetaSupp
->getMetaData();
264 nColCount
= xMeta
->getColumnCount(); // this is the number of real columns
266 if ( rParam
.nCol1
+ nColCount
- 1 > MAXCOL
)
272 uno::Reference
<sdbcx::XRowLocate
> xLocate
;
273 if ( bBookmarkSelection
)
275 xLocate
.set( xRowSet
, uno::UNO_QUERY
);
278 SAL_WARN( "sc.ui","can't get XRowLocate");
279 bDoSelection
= bRealSelection
= bBookmarkSelection
= sal_False
;
283 uno::Reference
<sdbc::XRow
> xRow( xRowSet
, uno::UNO_QUERY
);
284 if ( nColCount
> 0 && xRow
.is() )
286 nEndCol
= (SCCOL
)( rParam
.nCol1
+ nColCount
- 1 );
288 uno::Sequence
<sal_Int32
> aColTypes( nColCount
); // column types
289 uno::Sequence
<sal_Bool
> aColCurr( nColCount
); // currency flag is not in types
290 sal_Int32
* pTypeArr
= aColTypes
.getArray();
291 sal_Bool
* pCurrArr
= aColCurr
.getArray();
292 for (i
=0; i
<nColCount
; i
++)
294 pTypeArr
[i
] = xMeta
->getColumnType( i
+1 );
295 pCurrArr
[i
] = xMeta
->isCurrency( i
+1 );
298 if ( !bAddrInsert
) // read column names
301 for (i
=0; i
<nColCount
; i
++)
303 pImportDoc
->SetString( nCol
, nRow
, nTab
,
304 xMeta
->getColumnLabel( i
+1 ) );
310 sal_Bool bEnd
= false;
312 xRowSet
->beforeFirst();
313 sal_uInt16 nInserted
= 0;
316 // skip rows that are not selected
319 if ( (bEnd
= !xRowSet
->next()) == false )
324 if (nListPos
< nListCount
)
326 if ( bBookmarkSelection
)
328 bEnd
= !xLocate
->moveToBookmark(aSelection
[nListPos
]);
330 else // use record numbers
332 sal_Int32 nNextRow
= 0;
333 aSelection
[nListPos
] >>= nNextRow
;
334 if ( nRowsRead
+1 < nNextRow
)
335 bRealSelection
= true;
336 bEnd
= !xRowSet
->absolute(nRowsRead
= nNextRow
);
342 if ( !bBookmarkSelection
&& xRowSet
->next() )
343 bRealSelection
= true; // more data available but not used
350 if ( ValidRow(nRow
) )
353 for (i
=0; i
<nColCount
; i
++)
355 ScDatabaseDocUtil::PutData( pImportDoc
, nCol
, nRow
, nTab
,
356 xRow
, i
+1, pTypeArr
[i
], pCurrArr
[i
] );
365 if (!(nInserted
& 15))
367 OUString aPict
= ScGlobal::GetRscString( STR_PROGRESS_IMPORT
);
368 OUString aText
= aPict
.getToken(0,'#');
369 aText
+= OUString::number( nInserted
);
370 aText
+= aPict
.getToken(1,'#');
372 if (!aProgress
.SetStateText( 0, aText
)) // stopped by user?
376 nErrStringId
= STR_DATABASE_ABORTED
;
380 else // past the end of the spreadsheet
382 bEnd
= sal_True
; // don't continue
383 bTruncated
= sal_True
; // warning flag
392 ::comphelper::disposeComponent( xRowSet
);
395 catch ( const sdbc::SQLException
& rError
)
397 aErrorMessage
= rError
.Message
;
399 catch ( uno::Exception
& )
401 OSL_FAIL("Unexpected exception in database");
405 // test for cell protection
408 sal_Bool bKeepFormat
= !bAddrInsert
&& pDBData
->IsKeepFmt();
409 sal_Bool bMoveCells
= !bAddrInsert
&& pDBData
->IsDoSize();
410 SCCOL nFormulaCols
= 0; // columns to be filled with formulas
411 if (bMoveCells
&& nEndCol
== rParam
.nCol2
)
413 // if column count changes, formulas would become invalid anyway
414 // -> only set nFormulaCols for unchanged column count
416 SCCOL nTestCol
= rParam
.nCol2
+ 1; // right of the data
417 SCROW nTestRow
= rParam
.nRow1
+ 1; // below the title row
418 while ( nTestCol
<= MAXCOL
&&
419 pDoc
->GetCellType(ScAddress( nTestCol
, nTestRow
, nTab
)) == CELLTYPE_FORMULA
)
420 ++nTestCol
, ++nFormulaCols
;
425 // old and new range editable?
426 ScEditableTester aTester
;
427 aTester
.TestBlock( pDoc
, nTab
, rParam
.nCol1
,rParam
.nRow1
,rParam
.nCol2
,rParam
.nRow2
);
428 aTester
.TestBlock( pDoc
, nTab
, rParam
.nCol1
,rParam
.nRow1
,nEndCol
,nEndRow
);
429 if ( !aTester
.IsEditable() )
431 nErrStringId
= aTester
.GetMessageId();
434 else if ( (pChangeTrack
= pDoc
->GetChangeTrack()) != NULL
)
435 aChangedRange
= ScRange(rParam
.nCol1
, rParam
.nRow1
, nTab
,
436 nEndCol
+nFormulaCols
, nEndRow
, nTab
);
439 if ( bSuccess
&& bMoveCells
)
441 ScRange
aOld( rParam
.nCol1
, rParam
.nRow1
, nTab
,
442 rParam
.nCol2
+nFormulaCols
, rParam
.nRow2
, nTab
);
443 ScRange
aNew( rParam
.nCol1
, rParam
.nRow1
, nTab
,
444 nEndCol
+nFormulaCols
, nEndRow
, nTab
);
445 if (!pDoc
->CanFitBlock( aOld
, aNew
))
447 nErrStringId
= STR_MSSG_DOSUBTOTALS_2
; // can't insert cells
453 // copy data from import doc into real document
460 // keep formatting of title and first data row from the document
461 // CopyToDocument also copies styles, Apply... needs separate calls
463 SCCOL nMinEndCol
= std::min( rParam
.nCol2
, nEndCol
); // not too much
464 nMinEndCol
= sal::static_int_cast
<SCCOL
>( nMinEndCol
+ nFormulaCols
); // only if column count unchanged
465 pImportDoc
->DeleteAreaTab( 0,0, MAXCOL
,MAXROW
, nTab
, IDF_ATTRIB
);
466 pDoc
->CopyToDocument( rParam
.nCol1
, rParam
.nRow1
, nTab
,
467 nMinEndCol
, rParam
.nRow1
, nTab
,
468 IDF_ATTRIB
, false, pImportDoc
);
470 SCROW nDataStartRow
= rParam
.nRow1
+1;
471 for (SCCOL nCopyCol
=rParam
.nCol1
; nCopyCol
<=nMinEndCol
; nCopyCol
++)
473 const ScPatternAttr
* pSrcPattern
= pDoc
->GetPattern(
474 nCopyCol
, nDataStartRow
, nTab
);
475 pImportDoc
->ApplyPatternAreaTab( nCopyCol
, nDataStartRow
, nCopyCol
, nEndRow
,
476 nTab
, *pSrcPattern
);
477 const ScStyleSheet
* pStyle
= pSrcPattern
->GetStyleSheet();
479 pImportDoc
->ApplyStyleAreaTab( nCopyCol
, nDataStartRow
, nCopyCol
, nEndRow
,
484 // don't set cell protection attribute if table is protected
485 if (pDoc
->IsTabProtected(nTab
))
487 ScPatternAttr
aPattern(pImportDoc
->GetPool());
488 aPattern
.GetItemSet().Put( ScProtectionAttr( false,false,false,false ) );
489 pImportDoc
->ApplyPatternAreaTab( 0,0,MAXCOL
,MAXROW
, nTab
, aPattern
);
493 // copy old data for undo
496 SCCOL nUndoEndCol
= std::max( nEndCol
, rParam
.nCol2
); // rParam = old end
497 SCROW nUndoEndRow
= std::max( nEndRow
, rParam
.nRow2
);
499 ScDocument
* pUndoDoc
= NULL
;
500 ScDBData
* pUndoDBData
= NULL
;
503 pUndoDoc
= new ScDocument( SCDOCMODE_UNDO
);
504 pUndoDoc
->InitUndo( pDoc
, nTab
, nTab
);
507 pUndoDBData
= new ScDBData( *pDBData
);
511 aNewMark
.SelectOneTable( nTab
);
515 // do not touch notes (ScUndoImportData does not support drawing undo)
516 sal_uInt16 nCopyFlags
= IDF_ALL
& ~IDF_NOTE
;
518 // nFormulaCols is set only if column count is unchanged
519 pDoc
->CopyToDocument( rParam
.nCol1
, rParam
.nRow1
, nTab
,
520 nEndCol
+nFormulaCols
, nEndRow
, nTab
,
521 nCopyFlags
, false, pUndoDoc
);
522 if ( rParam
.nCol2
> nEndCol
)
523 pDoc
->CopyToDocument( nEndCol
+1, rParam
.nRow1
, nTab
,
524 nUndoEndCol
, nUndoEndRow
, nTab
,
525 nCopyFlags
, false, pUndoDoc
);
526 if ( rParam
.nRow2
> nEndRow
)
527 pDoc
->CopyToDocument( rParam
.nCol1
, nEndRow
+1, nTab
,
528 nUndoEndCol
+nFormulaCols
, nUndoEndRow
, nTab
,
529 nCopyFlags
, false, pUndoDoc
);
538 // clear only the range without the formulas,
539 // so the formula title and first row are preserved
541 ScRange
aDelRange( rParam
.nCol1
, rParam
.nRow1
, nTab
,
542 rParam
.nCol2
, rParam
.nRow2
, nTab
);
543 pDoc
->DeleteAreaTab( aDelRange
, IDF_ALL
& ~IDF_NOTE
); // ohne die Formeln
545 ScRange
aOld( rParam
.nCol1
, rParam
.nRow1
, nTab
,
546 rParam
.nCol2
+nFormulaCols
, rParam
.nRow2
, nTab
);
547 ScRange
aNew( rParam
.nCol1
, rParam
.nRow1
, nTab
,
548 nEndCol
+nFormulaCols
, nEndRow
, nTab
);
549 pDoc
->FitBlock( aOld
, aNew
, false ); // Formeln nicht loeschen
551 else if ( nEndCol
< rParam
.nCol2
) // DeleteArea calls PutInOrder
552 pDoc
->DeleteArea( nEndCol
+1, rParam
.nRow1
, rParam
.nCol2
, rParam
.nRow2
,
553 aNewMark
, IDF_CONTENTS
& ~IDF_NOTE
);
555 // CopyToDocument doesn't remove contents
556 pDoc
->DeleteAreaTab( rParam
.nCol1
, rParam
.nRow1
, nEndCol
, nEndRow
, nTab
, IDF_CONTENTS
& ~IDF_NOTE
);
558 // remove each column from ImportDoc after copying to reduce memory usage
559 sal_Bool bOldAutoCalc
= pDoc
->GetAutoCalc();
560 pDoc
->SetAutoCalc( false ); // outside of the loop
561 for (SCCOL nCopyCol
= rParam
.nCol1
; nCopyCol
<= nEndCol
; nCopyCol
++)
563 pImportDoc
->CopyToDocument( nCopyCol
, rParam
.nRow1
, nTab
, nCopyCol
, nEndRow
, nTab
,
564 IDF_ALL
, false, pDoc
);
565 pImportDoc
->DeleteAreaTab( nCopyCol
, rParam
.nRow1
, nCopyCol
, nEndRow
, nTab
, IDF_CONTENTS
);
567 pDoc
->SetAutoCalc( bOldAutoCalc
);
569 if (nFormulaCols
> 0) // copy formulas
571 if (bKeepFormat
) // formats for formulas
572 pImportDoc
->CopyToDocument( nEndCol
+1, rParam
.nRow1
, nTab
,
573 nEndCol
+nFormulaCols
, nEndRow
, nTab
,
574 IDF_ATTRIB
, false, pDoc
);
577 aMark
.SelectOneTable(nTab
);
579 sal_uLong nProgCount
= nFormulaCols
;
580 nProgCount
*= nEndRow
-rParam
.nRow1
-1;
581 ScProgress
aProgress( pDoc
->GetDocumentShell(),
582 ScGlobal::GetRscString(STR_FILL_SERIES_PROGRESS
), nProgCount
);
584 pDoc
->Fill( nEndCol
+1, rParam
.nRow1
+1, nEndCol
+nFormulaCols
, rParam
.nRow1
+1,
585 &aProgress
, aMark
, nEndRow
-rParam
.nRow1
-1, FILL_TO_BOTTOM
, FILL_SIMPLE
);
588 // if new range is smaller, clear old contents
590 if (!bMoveCells
) // move has happened above
592 if ( rParam
.nCol2
> nEndCol
)
593 pDoc
->DeleteArea( nEndCol
+1, rParam
.nRow1
, rParam
.nCol2
, rParam
.nRow2
,
594 aNewMark
, IDF_CONTENTS
);
595 if ( rParam
.nRow2
> nEndRow
)
596 pDoc
->DeleteArea( rParam
.nCol1
, nEndRow
+1, rParam
.nCol2
, rParam
.nRow2
,
597 aNewMark
, IDF_CONTENTS
);
600 if( !bAddrInsert
) // update database range
602 pDBData
->SetImportParam( rParam
);
603 pDBData
->SetHeader( sal_True
);
604 pDBData
->SetByRow( sal_True
);
605 pDBData
->SetArea( nTab
, rParam
.nCol1
,rParam
.nRow1
, nEndCol
,nEndRow
);
606 pDBData
->SetImportSelection( bRealSelection
);
607 pDoc
->CompileDBFormula();
612 ScDocument
* pRedoDoc
= pImportDoc
;
615 if (nFormulaCols
> 0) // include filled formulas for redo
616 pDoc
->CopyToDocument( rParam
.nCol1
, rParam
.nRow1
, nTab
,
617 nEndCol
+nFormulaCols
, nEndRow
, nTab
,
618 IDF_ALL
& ~IDF_NOTE
, false, pRedoDoc
);
620 ScDBData
* pRedoDBData
= pDBData
? new ScDBData( *pDBData
) : NULL
;
622 rDocShell
.GetUndoManager()->AddUndoAction(
623 new ScUndoImportData( &rDocShell
, nTab
,
624 rParam
, nUndoEndCol
, nUndoEndRow
,
626 pUndoDoc
, pRedoDoc
, pUndoDBData
, pRedoDBData
) );
630 rDocShell
.PostPaint(ScRange(0, 0, nTab
, MAXCOL
, MAXROW
, nTab
), PAINT_GRID
);
631 aModificator
.SetDocumentModified();
633 ScDBRangeRefreshedHint
aHint( rParam
);
634 pDoc
->BroadcastUno( aHint
);
637 pWaitWin
->LeaveWait();
639 if ( bTruncated
&& !bApi
) // show warning
640 ErrorHandler::HandleError(SCWARN_IMPORT_RANGE_OVERFLOW
);
645 pWaitWin
->LeaveWait();
647 if (aErrorMessage
.isEmpty())
650 nErrStringId
= STR_MSSG_IMPORTDATA_0
;
651 aErrorMessage
= ScGlobal::GetRscString( nErrStringId
);
653 InfoBox
aInfoBox( rDocShell
.GetActiveDialogParent(), aErrorMessage
);
659 if (bSuccess
&& pChangeTrack
)
660 pChangeTrack
->AppendInsert ( aChangedRange
);
668 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */