sc/inc/clipcontext.hxx | 37 ++++++++++++++++++-------- sc/inc/column.hxx | 3 +- sc/inc/table.hxx | 9 +++--- sc/source/core/data/clipcontext.cxx | 51 ++++++++++++++++++++---------------- sc/source/core/data/column.cxx | 10 +++++-- sc/source/core/data/document.cxx | 8 ++++- sc/source/core/data/table2.cxx | 14 +++++---- 7 files changed, 84 insertions(+), 48 deletions(-)
New commits: commit 32e561591fb13825c11160a8cb4291f2cebd5741 Author: Kohei Yoshida <kohei.yosh...@gmail.com> Date: Thu May 16 23:59:42 2013 -0400 Do the same optimization for CopyToClip. The basic idea is the same as the one I did for CopyFromClip. This prevents the O(n^2) algorithm from being invoked during undo object creation. Change-Id: Iac46663b0c25db2f00ffa3ab95a4dcf2857252ce diff --git a/sc/inc/clipcontext.hxx b/sc/inc/clipcontext.hxx index 53f2110..e28d265 100644 --- a/sc/inc/clipcontext.hxx +++ b/sc/inc/clipcontext.hxx @@ -20,20 +20,34 @@ class ScDocument; namespace sc { -class CopyFromClipContext +class ClipContextBase { typedef boost::unordered_map<SCCOL, ColumnBlockPosition> ColumnsType; typedef std::vector<ColumnsType> TablesType; + ScDocument& mrDoc; TablesType maTables; + SCTAB mnTabStart; + SCTAB mnTabEnd; - ScDocument& mrDoc; +public: + ClipContextBase(ScDocument& rDoc); + virtual ~ClipContextBase(); + + void setTabRange(SCTAB nStart, SCTAB nEnd); + + SCTAB getTabStart() const; + SCTAB getTabEnd() const; + + ColumnBlockPosition* getBlockPosition(SCTAB nTab, SCCOL nCol); +}; + +class CopyFromClipContext : public ClipContextBase +{ ScDocument* mpRefUndoDoc; ScDocument* mpClipDoc; sal_uInt16 mnInsertFlag; - SCTAB mnTabStart; - SCTAB mnTabEnd; bool mbAsLink:1; bool mbSkipAttrForEmptyCells:1; @@ -44,21 +58,22 @@ public: ScDocument* pRefUndoDoc, ScDocument* pClipDoc, sal_uInt16 nInsertFlag, bool bAsLink, bool bSkipAttrForEmptyCells); - ~CopyFromClipContext(); - - void setTabRange(SCTAB nStart, SCTAB nEnd); - - ColumnBlockPosition* getBlockPosition(SCTAB nTab, SCCOL nCol); + virtual ~CopyFromClipContext(); ScDocument* getUndoDoc(); ScDocument* getClipDoc(); sal_uInt16 getInsertFlag() const; - SCTAB getTabStart() const; - SCTAB getTabEnd() const; bool isAsLink() const; bool isSkipAttrForEmptyCells() const; }; +class CopyToClipContext : public ClipContextBase +{ +public: + CopyToClipContext(ScDocument& rDoc); + virtual ~CopyToClipContext(); +}; + } #endif diff --git a/sc/inc/column.hxx b/sc/inc/column.hxx index f1584b1..0eab575 100644 --- a/sc/inc/column.hxx +++ b/sc/inc/column.hxx @@ -39,6 +39,7 @@ namespace sc { struct FormulaGroupContext; class EndListeningContext; class CopyFromClipContext; + class CopyToClipContext; struct ColumnBlockPosition; } @@ -215,7 +216,7 @@ public: void InsertRow( SCROW nStartRow, SCSIZE nSize ); void DeleteRow( SCROW nStartRow, SCSIZE nSize ); void DeleteArea(SCROW nStartRow, SCROW nEndRow, sal_uInt16 nDelFlag ); - void CopyToClip(SCROW nRow1, SCROW nRow2, ScColumn& rColumn, bool bKeepScenarioFlags) const; + void CopyToClip( sc::CopyToClipContext& rCxt, SCROW nRow1, SCROW nRow2, ScColumn& rColumn, bool bKeepScenarioFlags ) const; void CopyStaticToDocument(SCROW nRow1, SCROW nRow2, ScColumn& rDestCol); void CopyCellToDocument( SCROW nSrcRow, SCROW nDestRow, ScColumn& rDestCol ); bool InitBlockPosition( sc::ColumnBlockPosition& rBlockPos ); diff --git a/sc/inc/table.hxx b/sc/inc/table.hxx index 333eb9a..2538a0b 100644 --- a/sc/inc/table.hxx +++ b/sc/inc/table.hxx @@ -51,6 +51,7 @@ namespace sc { struct FormulaGroupContext; class EndListeningContext; class CopyFromClipContext; + class CopyToClipContext; struct ColumnBlockPosition; } @@ -379,10 +380,10 @@ public: bool* pUndoOutline = NULL ); void DeleteArea(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, sal_uInt16 nDelFlag); - void CopyToClip(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, ScTable* pTable, - bool bKeepScenarioFlags, bool bCloneNoteCaptions); - void CopyToClip(const ScRangeList& rRanges, ScTable* pTable, - bool bKeepScenarioFlags, bool bCloneNoteCaptions); + void CopyToClip( sc::CopyToClipContext& rCxt, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, ScTable* pTable, + bool bKeepScenarioFlags, bool bCloneNoteCaptions ); + void CopyToClip( sc::CopyToClipContext& rCxt, const ScRangeList& rRanges, ScTable* pTable, + bool bKeepScenarioFlags, bool bCloneNoteCaptions ); void CopyStaticToDocument(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, ScTable* pDestTab); void CopyCellToDocument( SCCOL nSrcCol, SCROW nSrcRow, SCCOL nDestCol, SCROW nDestRow, ScTable& rDestTab ); diff --git a/sc/source/core/data/clipcontext.cxx b/sc/source/core/data/clipcontext.cxx index 1d19dd1..e3db67d 100644 --- a/sc/source/core/data/clipcontext.cxx +++ b/sc/source/core/data/clipcontext.cxx @@ -12,25 +12,28 @@ namespace sc { -CopyFromClipContext::CopyFromClipContext(ScDocument& rDoc, - ScDocument* pRefUndoDoc, ScDocument* pClipDoc, sal_uInt16 nInsertFlag, - bool bAsLink, bool bSkipAttrForEmptyCells) : - mrDoc(rDoc), - mpRefUndoDoc(pRefUndoDoc), mpClipDoc(pClipDoc), mnInsertFlag(nInsertFlag), - mnTabStart(-1), mnTabEnd(-1), - mbAsLink(bAsLink), mbSkipAttrForEmptyCells(bSkipAttrForEmptyCells) {} +ClipContextBase::ClipContextBase(ScDocument& rDoc) : + mrDoc(rDoc), mnTabStart(-1), mnTabEnd(-1) {} -CopyFromClipContext::~CopyFromClipContext() -{ -} +ClipContextBase::~ClipContextBase() {} -void CopyFromClipContext::setTabRange(SCTAB nStart, SCTAB nEnd) +void ClipContextBase::setTabRange(SCTAB nStart, SCTAB nEnd) { mnTabStart = nStart; mnTabEnd = nEnd; } -ColumnBlockPosition* CopyFromClipContext::getBlockPosition(SCTAB nTab, SCCOL nCol) +SCTAB ClipContextBase::getTabStart() const +{ + return mnTabStart; +} + +SCTAB ClipContextBase::getTabEnd() const +{ + return mnTabEnd; +} + +ColumnBlockPosition* ClipContextBase::getBlockPosition(SCTAB nTab, SCCOL nCol) { if (mnTabStart < 0 || mnTabEnd < 0 || mnTabStart > mnTabEnd) return NULL; @@ -62,6 +65,17 @@ ColumnBlockPosition* CopyFromClipContext::getBlockPosition(SCTAB nTab, SCCOL nCo return &it->second; } +CopyFromClipContext::CopyFromClipContext(ScDocument& rDoc, + ScDocument* pRefUndoDoc, ScDocument* pClipDoc, sal_uInt16 nInsertFlag, + bool bAsLink, bool bSkipAttrForEmptyCells) : + ClipContextBase(rDoc), + mpRefUndoDoc(pRefUndoDoc), mpClipDoc(pClipDoc), mnInsertFlag(nInsertFlag), + mbAsLink(bAsLink), mbSkipAttrForEmptyCells(bSkipAttrForEmptyCells) {} + +CopyFromClipContext::~CopyFromClipContext() +{ +} + ScDocument* CopyFromClipContext::getUndoDoc() { return mpRefUndoDoc; @@ -77,16 +91,6 @@ sal_uInt16 CopyFromClipContext::getInsertFlag() const return mnInsertFlag; } -SCTAB CopyFromClipContext::getTabStart() const -{ - return mnTabStart; -} - -SCTAB CopyFromClipContext::getTabEnd() const -{ - return mnTabEnd; -} - bool CopyFromClipContext::isAsLink() const { return mbAsLink; @@ -97,6 +101,9 @@ bool CopyFromClipContext::isSkipAttrForEmptyCells() const return mbSkipAttrForEmptyCells; } +CopyToClipContext::CopyToClipContext(ScDocument& rDoc) : ClipContextBase(rDoc) {} +CopyToClipContext::~CopyToClipContext() {} + } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sc/source/core/data/column.cxx b/sc/source/core/data/column.cxx index 77bf89a..655918b 100644 --- a/sc/source/core/data/column.cxx +++ b/sc/source/core/data/column.cxx @@ -34,6 +34,7 @@ #include "cellvalue.hxx" #include "tokenarray.hxx" #include "cellform.hxx" +#include "clipcontext.hxx" #include <svl/poolcach.hxx> #include <svl/zforlist.hxx> @@ -1183,7 +1184,8 @@ void ScColumn::InsertRow( SCROW nStartRow, SCSIZE nSize ) } -void ScColumn::CopyToClip(SCROW nRow1, SCROW nRow2, ScColumn& rColumn, bool bKeepScenarioFlags) const +void ScColumn::CopyToClip( + sc::CopyToClipContext& rCxt, SCROW nRow1, SCROW nRow2, ScColumn& rColumn, bool bKeepScenarioFlags) const { pAttrArray->CopyArea( nRow1, nRow2, 0, *rColumn.pAttrArray, bKeepScenarioFlags ? (SC_MF_ALL & ~SC_MF_SCENARIO) : SC_MF_ALL ); @@ -1219,7 +1221,11 @@ void ScColumn::CopyToClip(SCROW nRow1, SCROW nRow2, ScColumn& rColumn, bool bKee aOwnPos.SetRow( maItems[i].nRow ); aDestPos.SetRow( maItems[i].nRow ); ScBaseCell* pNewCell = maItems[i].pCell->Clone( *rColumn.pDocument, aDestPos, SC_CLONECELL_DEFAULT ); - rColumn.Append( aDestPos.Row(), pNewCell ); + sc::ColumnBlockPosition* p = rCxt.getBlockPosition(rColumn.nTab, rColumn.nCol); + if (p) + rColumn.Append(*p, aDestPos.Row(), pNewCell); + else + rColumn.Append(aDestPos.Row(), pNewCell); } } } diff --git a/sc/source/core/data/document.cxx b/sc/source/core/data/document.cxx index b8d4497..c7bebda 100644 --- a/sc/source/core/data/document.cxx +++ b/sc/source/core/data/document.cxx @@ -1992,6 +1992,8 @@ void ScDocument::CopyToClip(const ScClipParam& rClipParam, else pClipDoc->ResetClip(this, pMarks); + sc::CopyToClipContext aCxt(*pClipDoc); + aCxt.setTabRange(i, nEndTab-1); CopyRangeNamesToClip(pClipDoc, aClipRange, pMarks, bAllTabs); for ( ; i < nEndTab; ++i) @@ -2002,7 +2004,7 @@ void ScDocument::CopyToClip(const ScClipParam& rClipParam, if ( !bUseRangeForVBA && ( pMarks && !pMarks->GetTableSelect(i) ) ) continue; - maTabs[i]->CopyToClip(rClipParam.maRanges, pClipDoc->maTabs[i], bKeepScenarioFlags, bCloneNoteCaptions); + maTabs[i]->CopyToClip(aCxt, rClipParam.maRanges, pClipDoc->maTabs[i], bKeepScenarioFlags, bCloneNoteCaptions); if (pDrawLayer && bIncludeObjects) { @@ -2088,9 +2090,11 @@ void ScDocument::CopyTabToClip(SCCOL nCol1, SCROW nRow1, rClipParam.maRanges.Append(ScRange(nCol1, nRow1, 0, nCol2, nRow2, 0)); pClipDoc->ResetClip( this, nTab ); + sc::CopyToClipContext aCxt(*pClipDoc); + aCxt.setTabRange(nTab, nTab); if (nTab < static_cast<SCTAB>(maTabs.size()) && nTab < static_cast<SCTAB>(pClipDoc->maTabs.size())) if (maTabs[nTab] && pClipDoc->maTabs[nTab]) - maTabs[nTab]->CopyToClip(nCol1, nRow1, nCol2, nRow2, pClipDoc->maTabs[nTab], false, true); + maTabs[nTab]->CopyToClip(aCxt, nCol1, nRow1, nCol2, nRow2, pClipDoc->maTabs[nTab], false, true); pClipDoc->GetClipParam().mbCutMode = false; } diff --git a/sc/source/core/data/table2.cxx b/sc/source/core/data/table2.cxx index 7f620dd..e8d510f 100644 --- a/sc/source/core/data/table2.cxx +++ b/sc/source/core/data/table2.cxx @@ -604,8 +604,9 @@ void ScTable::DeleteSelection( sal_uInt16 nDelFlag, const ScMarkData& rMark ) // pTable = Clipboard -void ScTable::CopyToClip(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, - ScTable* pTable, bool bKeepScenarioFlags, bool bCloneNoteCaptions) +void ScTable::CopyToClip( + sc::CopyToClipContext& rCxt, SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, + ScTable* pTable, bool bKeepScenarioFlags, bool bCloneNoteCaptions ) { if (ValidColRow(nCol1, nRow1) && ValidColRow(nCol2, nRow2)) { @@ -620,7 +621,7 @@ void ScTable::CopyToClip(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, SCCOL i; for ( i = nCol1; i <= nCol2; i++) - aCol[i].CopyToClip(nRow1, nRow2, pTable->aCol[i], bKeepScenarioFlags); + aCol[i].CopyToClip(rCxt, nRow1, nRow2, pTable->aCol[i], bKeepScenarioFlags); // copy widths/heights, and only "hidden", "filtered" and "manual" flags // also for all preceding columns/rows, to have valid positions for drawing objects @@ -654,14 +655,15 @@ void ScTable::CopyToClip(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2, } } -void ScTable::CopyToClip(const ScRangeList& rRanges, ScTable* pTable, - bool bKeepScenarioFlags, bool bCloneNoteCaptions) +void ScTable::CopyToClip( + sc::CopyToClipContext& rCxt, const ScRangeList& rRanges, ScTable* pTable, + bool bKeepScenarioFlags, bool bCloneNoteCaptions ) { ScRangeList aRanges(rRanges); for ( size_t i = 0, nListSize = aRanges.size(); i < nListSize; ++i ) { ScRange* p = aRanges[ i ]; - CopyToClip(p->aStart.Col(), p->aStart.Row(), p->aEnd.Col(), p->aEnd.Row(), + CopyToClip(rCxt, p->aStart.Col(), p->aStart.Row(), p->aEnd.Col(), p->aEnd.Row(), pTable, bKeepScenarioFlags, bCloneNoteCaptions); } } _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits