ooo-build r15230 - in branches/ooo-build-3-0-1: . patches/dev300
- From: kyoshida svn gnome org
- To: svn-commits-list gnome org
- Subject: ooo-build r15230 - in branches/ooo-build-3-0-1: . patches/dev300
- Date: Wed, 28 Jan 2009 22:34:16 +0000 (UTC)
Author: kyoshida
Date: Wed Jan 28 22:34:15 2009
New Revision: 15230
URL: http://svn.gnome.org/viewvc/ooo-build?rev=15230&view=rev
Log:
2009-01-28 Kohei Yoshida <kyoshida novell com>
* patches/dev300/calc-external-defined-names-empty-cells.diff: put the
right fix to deal with out-of-bound external references on a cached
sheet.
Modified:
branches/ooo-build-3-0-1/ChangeLog
branches/ooo-build-3-0-1/patches/dev300/calc-external-defined-names-empty-cells.diff
Modified: branches/ooo-build-3-0-1/patches/dev300/calc-external-defined-names-empty-cells.diff
==============================================================================
--- branches/ooo-build-3-0-1/patches/dev300/calc-external-defined-names-empty-cells.diff (original)
+++ branches/ooo-build-3-0-1/patches/dev300/calc-external-defined-names-empty-cells.diff Wed Jan 28 22:34:15 2009
@@ -1,24 +1,288 @@
+diff --git sc/inc/externalrefmgr.hxx sc/inc/externalrefmgr.hxx
+index fa2bd9e..e16d192 100644
+--- sc/inc/externalrefmgr.hxx
++++ sc/inc/externalrefmgr.hxx
+@@ -72,7 +72,7 @@ private:
+ ScExternalRefLink(); // disabled
+ ScExternalRefLink(const ScExternalRefLink&); // disabled
+
+- DECL_LINK(EndEditHdl, void*);
++ DECL_LINK( ExternalRefEndEditHdl, ::sfx2::SvBaseLink* );
+
+ sal_uInt16 mnFileId;
+ String maFilterName;
+@@ -149,16 +149,14 @@ public:
+ *
+ * @param nFileId file ID of an external document
+ * @param rTabName sheet name
+- * @param nRow
+ * @param nCol
++ * @param nRow
+ *
+- * @return pointer to the token instance in the cache. <i>The caller does
+- * not need to delete this instance since its life cycle is
+- * managed by this class.</i>
++ * @return pointer to the token instance in the cache.
+ */
+ ScExternalRefCache::TokenRef getCellData(
+- sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol,
+- sal_uInt32* pnFmtIndex = NULL);
++ sal_uInt16 nFileId, const String& rTabName, SCCOL nCol, SCROW nRow,
++ bool bEmptyCellOnNull, sal_uInt32* pnFmtIndex = NULL);
+
+ /**
+ * Get a cached cell range data.
+@@ -167,7 +165,8 @@ public:
+ * manage the life cycle of the returned instance</i>, which is
+ * guaranteed if the TokenArrayRef is properly used..
+ */
+- ScExternalRefCache::TokenArrayRef getCellRangeData(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange);
++ ScExternalRefCache::TokenArrayRef getCellRangeData(
++ sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange, bool bEmptyCellOnNull);
+
+ ScExternalRefCache::TokenArrayRef getRangeNameTokens(sal_uInt16 nFileId, const String& rName);
+ void setRangeNameTokens(sal_uInt16 nFileId, const String& rName, TokenArrayRef pArray);
+@@ -294,7 +293,7 @@ private:
+ };
+
+ typedef ::std::hash_map<sal_uInt16, SrcShell> DocShellMap;
+- typedef ::std::hash_set<sal_uInt16> LinkedDocSet;
++ typedef ::std::hash_map<sal_uInt16, bool> LinkedDocMap;
+
+ typedef ::std::hash_map<sal_uInt16, RefCells> RefCellMap;
+ typedef ::std::hash_map<sal_uInt16, SvNumberFormatterMergeMap> NumFmtMap;
+@@ -338,7 +337,12 @@ public:
+ * XCT/CRN records.
+ *
+ * @param nFileId file ID
+- * @param rTabName table name
++ * @param rTabName table name
++ * @param bCreateNew if true, create a new table instance if it's not
++ * already present. If false, it returns NULL if the
++ * specified table's cache doesn't exist.
++ * @param pnIndex if non-NULL pointer is passed, it stores the internal
++ * index of a cache table instance.
+ *
+ * @return shared_ptr to the cache table instance
+ */
+@@ -410,6 +414,7 @@ public:
+ const String* getRealTableName(sal_uInt16 nFileId, const String& rTabName) const;
+ const String* getRealRangeName(sal_uInt16 nFileId, const String& rRangeName) const;
+ void refreshNames(sal_uInt16 nFileId);
++ void breakLink(sal_uInt16 nFileId);
+ void switchSrcFile(sal_uInt16 nFileId, const String& rNewFile);
+
+ void setRelativeFileName(sal_uInt16 nFileId, const String& rRelUrl);
+@@ -424,7 +429,6 @@ public:
+ */
+ void setFilterData(sal_uInt16 nFileId, const String& rFilterName, const String& rOptions);
+
+- void removeSrcDocument(sal_uInt16 nFileId, bool bBreakLink);
+ void clear();
+
+ bool hasExternalData() const;
+@@ -503,7 +507,7 @@ private:
+ DocShellMap maDocShells;
+
+ /** list of source documents that are managed by the link manager. */
+- LinkedDocSet maLinkedDocs;
++ LinkedDocMap maLinkedDocs;
+
+ /**
+ * List of referencing cells that may contain external names. There is
diff --git sc/source/ui/docshell/externalrefmgr.cxx sc/source/ui/docshell/externalrefmgr.cxx
-index ae5015d..d3f770b 100644
+index 9dcb2cc..bb39ff5 100644
--- sc/source/ui/docshell/externalrefmgr.cxx
+++ sc/source/ui/docshell/externalrefmgr.cxx
-@@ -161,7 +161,8 @@ ScExternalRefCache::TokenRef ScExternalRefCache::Table::getCell(SCCOL nCol, SCRO
- if (itrTable == maRows.end())
- {
- // this table doesn't have the specified row.
-- return TokenRef();
-+ TokenRef p(new ScEmptyCellToken(false, false));
-+ return p;
+@@ -290,7 +290,8 @@ const String* ScExternalRefCache::getRealRangeName(sal_uInt16 nFileId, const Str
+ }
+
+ ScExternalRefCache::TokenRef ScExternalRefCache::getCellData(
+- sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol, sal_uInt32* pnFmtIndex)
++ sal_uInt16 nFileId, const String& rTabName, SCCOL nCol, SCROW nRow,
++ bool bEmptyCellOnNull, sal_uInt32* pnFmtIndex)
+ {
+ DocDataType::const_iterator itrDoc = maDocs.find(nFileId);
+ if (itrDoc == maDocs.end())
+@@ -314,10 +315,15 @@ ScExternalRefCache::TokenRef ScExternalRefCache::getCellData(
+ // the table data is not instantiated yet.
+ return TokenRef();
}
+- return pTableData->getCell(nCol, nRow, pnFmtIndex);
++
++ TokenRef pToken = pTableData->getCell(nCol, nRow, pnFmtIndex);
++ if (!pToken && bEmptyCellOnNull)
++ pToken.reset(new ScEmptyCellToken(false, false));
++ return pToken;
+ }
+
+-ScExternalRefCache::TokenArrayRef ScExternalRefCache::getCellRangeData(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange)
++ScExternalRefCache::TokenArrayRef ScExternalRefCache::getCellRangeData(
++ sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange, bool bEmptyCellOnNull)
+ {
+ DocDataType::iterator itrDoc = maDocs.find(nFileId);
+ if (itrDoc == maDocs.end())
+@@ -366,9 +372,14 @@ ScExternalRefCache::TokenArrayRef ScExternalRefCache::getCellRangeData(sal_uInt1
+ {
+ for (SCCOL nCol = nCol1; nCol <= nCol2; ++nCol)
+ {
+- ScToken* pToken = pTab->getCell(nCol, nRow).get();
++ TokenRef pToken = pTab->getCell(nCol, nRow);
+ if (!pToken)
+- return TokenArrayRef();
++ {
++ if (bEmptyCellOnNull)
++ pToken.reset(new ScEmptyCellToken(false, false));
++ else
++ return TokenArrayRef();
++ }
+
+ SCSIZE nC = nCol - nCol1, nR = nRow - nRow1;
+ switch (pToken->GetType())
+@@ -724,7 +735,7 @@ ScExternalRefLink::~ScExternalRefLink()
+ void ScExternalRefLink::Closed()
+ {
+ ScExternalRefManager* pMgr = mpDoc->GetExternalRefManager();
+- pMgr->removeSrcDocument(mnFileId, true);
++ pMgr->breakLink(mnFileId);
+ }
+
+ void ScExternalRefLink::DataChanged(const String& /*rMimeType*/, const Any& /*rValue*/)
+@@ -754,7 +765,7 @@ void ScExternalRefLink::DataChanged(const String& /*rMimeType*/, const Any& /*rV
- const RowDataType& rRowData = itrTable->second;
-@@ -169,7 +170,8 @@ ScExternalRefCache::TokenRef ScExternalRefCache::Table::getCell(SCCOL nCol, SCRO
- if (itrRow == rRowData.end())
+ void ScExternalRefLink::Edit(Window* pParent, const Link& /*rEndEditHdl*/)
+ {
+- SvBaseLink::Edit(pParent, LINK(this, ScExternalRefLink, EndEditHdl));
++ SvBaseLink::Edit(pParent, LINK(this, ScExternalRefLink, ExternalRefEndEditHdl));
+ }
+
+ void ScExternalRefLink::SetDoReferesh(bool b)
+@@ -762,7 +773,7 @@ void ScExternalRefLink::SetDoReferesh(bool b)
+ mbDoRefresh = b;
+ }
+
+-IMPL_LINK(ScExternalRefLink, EndEditHdl, void*, EMPTYARG)
++IMPL_LINK( ScExternalRefLink, ExternalRefEndEditHdl, ::sfx2::SvBaseLink*, EMPTYARG )
+ {
+ return 0;
+ }
+@@ -1226,7 +1237,7 @@ ScExternalRefCache::TokenRef ScExternalRefManager::getSingleRefToken(
+ // Check if the given table name and the cell position is cached.
+ sal_uInt32 nFmtIndex = 0;
+ ScExternalRefCache::TokenRef pToken = maRefCache.getCellData(
+- nFileId, rTabName, rCell.Row(), rCell.Col(), &nFmtIndex);
++ nFileId, rTabName, rCell.Col(), rCell.Row(), false, &nFmtIndex);
+ if (pToken)
{
- // this row doesn't have the specified column.
-- return TokenRef();
-+ TokenRef p(new ScEmptyCellToken(false, false));
-+ return p;
+ if (pFmt)
+@@ -1246,7 +1257,12 @@ ScExternalRefCache::TokenRef ScExternalRefManager::getSingleRefToken(
+ ScDocument* pSrcDoc = getSrcDocument(nFileId);
+ if (!pSrcDoc)
+ {
+- return ScExternalRefCache::TokenRef();
++ // Source document is not reachable. Try to get data from the cache
++ // once again, but this time treat a non-cached cell as an empty cell
++ // as long as the table itself is cached.
++ pToken = maRefCache.getCellData(
++ nFileId, rTabName, rCell.Col(), rCell.Row(), true, &nFmtIndex);
++ return pToken;
}
- const Cell& rCell = itrRow->second;
+ ScBaseCell* pCell = NULL;
+@@ -1295,13 +1311,18 @@ ScExternalRefCache::TokenArrayRef ScExternalRefManager::getDoubleRefTokens(sal_u
+ maybeLinkExternalFile(nFileId);
+
+ // Check if the given table name and the cell position is cached.
+- ScExternalRefCache::TokenArrayRef p = maRefCache.getCellRangeData(nFileId, rTabName, rRange);
++ ScExternalRefCache::TokenArrayRef p = maRefCache.getCellRangeData(nFileId, rTabName, rRange, false);
+ if (p.get())
+ return p;
+
+ ScDocument* pSrcDoc = getSrcDocument(nFileId);
+ if (!pSrcDoc)
+- return ScExternalRefCache::TokenArrayRef();
++ {
++ // Source document is not reachable. Try to get data from the cache
++ // once again, but this time treat non-cached cells as empty cells as
++ // long as the table itself is cached.
++ return maRefCache.getCellRangeData(nFileId, rTabName, rRange, true);
++ }
+
+ SCTAB nTab1;
+ if (!pSrcDoc->GetTable(rTabName, nTab1))
+@@ -1431,7 +1452,7 @@ void ScExternalRefManager::refreshAllRefCells(sal_uInt16 nFileId)
+
+ // Repainting the grid also repaints the texts, but is there a better way
+ // to refresh texts?
+- pVShell->Invalidate(FID_TAB_TOGGLE_GRID);
++ pVShell->Invalidate(FID_REPAINT);
+ pVShell->PaintGrid();
+ }
+
+@@ -1595,7 +1616,7 @@ bool ScExternalRefManager::isFileLoadable(const String& rFile) const
+ void ScExternalRefManager::maybeLinkExternalFile(sal_uInt16 nFileId)
+ {
+ if (maLinkedDocs.count(nFileId))
+- // file alerady linked.
++ // file alerady linked, or the link has been broken.
+ return;
+
+ // Source document not linked yet. Link it now.
+@@ -1614,7 +1635,7 @@ void ScExternalRefManager::maybeLinkExternalFile(sal_uInt16 nFileId)
+ pLink->Update();
+ pLink->SetDoReferesh(true);
+
+- maLinkedDocs.insert(nFileId);
++ maLinkedDocs.insert(LinkedDocMap::value_type(nFileId, true));
+ }
+
+ bool ScExternalRefManager::compileTokensByCell(const ScAddress& rCell)
+@@ -1735,12 +1756,28 @@ static void lcl_removeByFileId(sal_uInt16 nFileId, MapContainer& rMap)
+
+ void ScExternalRefManager::refreshNames(sal_uInt16 nFileId)
+ {
+- removeSrcDocument(nFileId, false);
++ maRefCache.clearCache(nFileId);
++ lcl_removeByFileId(nFileId, maDocShells);
++
++ if (maDocShells.empty())
++ maSrcDocTimer.Stop();
+
+ // Update all cells containing names from this source document.
+ refreshAllRefCells(nFileId);
+ }
+
++void ScExternalRefManager::breakLink(sal_uInt16 nFileId)
++{
++ lcl_removeByFileId(nFileId, maDocShells);
++
++ if (maDocShells.empty())
++ maSrcDocTimer.Stop();
++
++ LinkedDocMap::iterator itr = maLinkedDocs.find(nFileId);
++ if (itr != maLinkedDocs.end())
++ itr->second = false;
++}
++
+ void ScExternalRefManager::switchSrcFile(sal_uInt16 nFileId, const String& rNewFile)
+ {
+ maSrcFiles[nFileId].maFileName = rNewFile;
+@@ -1763,18 +1800,6 @@ void ScExternalRefManager::setFilterData(sal_uInt16 nFileId, const String& rFilt
+ maSrcFiles[nFileId].maFilterOptions = rOptions;
+ }
+
+-void ScExternalRefManager::removeSrcDocument(sal_uInt16 nFileId, bool bBreakLink)
+-{
+- maRefCache.clearCache(nFileId);
+- lcl_removeByFileId(nFileId, maDocShells);
+-
+- if (bBreakLink)
+- maLinkedDocs.erase(nFileId);
+-
+- if (maDocShells.empty())
+- maSrcDocTimer.Stop();
+-}
+-
+ void ScExternalRefManager::clear()
+ {
+ DocShellMap::iterator itrEnd = maDocShells.end();
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]