Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*************************************************************************
3 : : *
4 : : * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 : : *
6 : : * Copyright 2000, 2010 Oracle and/or its affiliates.
7 : : *
8 : : * OpenOffice.org - a multi-platform office productivity suite
9 : : *
10 : : * This file is part of OpenOffice.org.
11 : : *
12 : : * OpenOffice.org is free software: you can redistribute it and/or modify
13 : : * it under the terms of the GNU Lesser General Public License version 3
14 : : * only, as published by the Free Software Foundation.
15 : : *
16 : : * OpenOffice.org is distributed in the hope that it will be useful,
17 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 : : * GNU Lesser General Public License version 3 for more details
20 : : * (a copy is included in the LICENSE file that accompanied this code).
21 : : *
22 : : * You should have received a copy of the GNU Lesser General Public License
23 : : * version 3 along with OpenOffice.org. If not, see
24 : : * <http://www.openoffice.org/license.html>
25 : : * for a copy of the LGPLv3 License.
26 : : *
27 : : ************************************************************************/
28 : :
29 : : #include "xmlsubti.hxx"
30 : : #include "global.hxx"
31 : : #include "xmlstyli.hxx"
32 : : #include "xmlimprt.hxx"
33 : : #include "document.hxx"
34 : : #include "markdata.hxx"
35 : : #include "XMLConverter.hxx"
36 : : #include "docuno.hxx"
37 : : #include "cellsuno.hxx"
38 : : #include "XMLStylesImportHelper.hxx"
39 : : #include "sheetdata.hxx"
40 : : #include "tabprotection.hxx"
41 : : #include "tokenarray.hxx"
42 : : #include "convuno.hxx"
43 : : #include <svx/svdpage.hxx>
44 : :
45 : : #include <sax/tools/converter.hxx>
46 : : #include <xmloff/xmltkmap.hxx>
47 : : #include <xmloff/nmspmap.hxx>
48 : : #include <xmloff/xmlerror.hxx>
49 : : #include <com/sun/star/sheet/XSpreadsheetDocument.hpp>
50 : : #include <com/sun/star/sheet/XSheetCellRange.hpp>
51 : : #include <com/sun/star/sheet/XCellRangeAddressable.hpp>
52 : : #include <com/sun/star/sheet/CellInsertMode.hpp>
53 : : #include <com/sun/star/sheet/XCellRangeMovement.hpp>
54 : : #include <com/sun/star/drawing/XDrawPageSupplier.hpp>
55 : : #include <com/sun/star/container/XNamed.hpp>
56 : : #include <com/sun/star/util/XProtectable.hpp>
57 : : #include <com/sun/star/sheet/XArrayFormulaRange.hpp>
58 : :
59 : : #include <memory>
60 : :
61 : : using ::std::auto_ptr;
62 : : using namespace com::sun::star;
63 : :
64 : :
65 : 602 : ScXMLTabProtectionData::ScXMLTabProtectionData() :
66 : : meHash1(PASSHASH_SHA1),
67 : : meHash2(PASSHASH_UNSPECIFIED),
68 : : mbProtected(false),
69 : : mbSelectProtectedCells(true),
70 : 602 : mbSelectUnprotectedCells(true)
71 : : {
72 : 602 : }
73 : :
74 : 378 : ScMyTables::ScMyTables(ScXMLImport& rTempImport)
75 : : : rImport(rTempImport),
76 : : aFixupOLEs(rTempImport),
77 : : maCurrentCellPos(ScAddress::INITIALIZE_INVALID),
78 : : nCurrentColCount(0),
79 : : nCurrentDrawPage( -1 ),
80 [ + - ]: 378 : nCurrentXShapes( -1 )
81 : : {
82 : 378 : }
83 : :
84 [ + - ]: 378 : ScMyTables::~ScMyTables()
85 : : {
86 : 378 : }
87 : :
88 : : namespace {
89 : :
90 : 224 : uno::Reference<sheet::XSpreadsheet> getCurrentSheet(const uno::Reference<frame::XModel>& xModel, SCTAB nSheet)
91 : : {
92 : 224 : uno::Reference<sheet::XSpreadsheet> xSheet;
93 [ + - ]: 224 : uno::Reference<sheet::XSpreadsheetDocument> xSpreadDoc(xModel, uno::UNO_QUERY);
94 [ + - ]: 224 : if (!xSpreadDoc.is())
95 : : return xSheet;
96 : :
97 [ + - ][ + - ]: 224 : uno::Reference <sheet::XSpreadsheets> xSheets(xSpreadDoc->getSheets());
98 [ + - ]: 224 : if (!xSheets.is())
99 : : return xSheet;
100 : :
101 [ + - ]: 224 : uno::Reference <container::XIndexAccess> xIndex(xSheets, uno::UNO_QUERY);
102 [ + - ]: 224 : if (!xIndex.is())
103 : : return xSheet;
104 : :
105 [ + - ][ + - ]: 224 : xSheet.set(xIndex->getByIndex(nSheet), uno::UNO_QUERY);
[ + - ]
106 : 224 : return xSheet;
107 : : }
108 : :
109 : : }
110 : :
111 : 224 : void ScMyTables::NewSheet(const rtl::OUString& sTableName, const rtl::OUString& sStyleName,
112 : : const ScXMLTabProtectionData& rProtectData)
113 : : {
114 [ + - ]: 224 : if (rImport.GetModel().is())
115 : : {
116 : 224 : nCurrentColCount = 0;
117 : 224 : sCurrentSheetName = sTableName;
118 : : //reset cols and rows for new sheet, but increment tab
119 : 224 : maCurrentCellPos.SetCol(-1);
120 : 224 : maCurrentCellPos.SetRow(-1);
121 : 224 : maCurrentCellPos.SetTab(maCurrentCellPos.Tab() + 1);
122 : :
123 : 224 : maProtectionData = rProtectData;
124 [ + - ]: 224 : ScDocument *pDoc = ScXMLConverter::GetScDocument(rImport.GetModel());
125 : :
126 : : // The document contains one sheet when created. So for the first
127 : : // sheet, we only need to set its name.
128 [ + + ]: 224 : if (maCurrentCellPos.Tab() > 0)
129 : 131 : pDoc->AppendTabOnLoad(sTableName);
130 : : else
131 : 93 : pDoc->SetTabNameOnLoad(maCurrentCellPos.Tab(), sTableName);
132 : :
133 : 224 : rImport.SetTableStyle(sStyleName);
134 [ + - ]: 224 : xCurrentSheet = getCurrentSheet(rImport.GetModel(), maCurrentCellPos.Tab());
135 [ + - ]: 224 : if (xCurrentSheet.is())
136 : : {
137 : : // We need to set the current cell range here regardless of
138 : : // presence of style name.
139 : 224 : xCurrentCellRange.set(xCurrentSheet, uno::UNO_QUERY);
140 : 224 : SetTableStyle(sStyleName);
141 : : }
142 : : }
143 : 224 : }
144 : :
145 : 224 : void ScMyTables::SetTableStyle(const rtl::OUString& sStyleName)
146 : : {
147 : : //these uno calls are a bit difficult to remove, XMLTableStyleContext::FillPropertySet uses
148 : : //SvXMLImportPropertyMapper::FillPropertySet
149 [ + - ]: 224 : if ( !sStyleName.isEmpty() )
150 : : {
151 : : // #i57869# All table style properties for all sheets are now applied here,
152 : : // before importing the contents.
153 : : // This is needed for the background color.
154 : : // Sheet visibility has special handling in ScDocFunc::SetTableVisible to
155 : : // allow hiding the first sheet.
156 : : // RTL layout is only remembered, not actually applied, so the shapes can
157 : : // be loaded before mirroring.
158 : :
159 [ + - ]: 224 : if ( xCurrentSheet.is() )
160 : : {
161 [ + - ]: 224 : xCurrentCellRange.set(xCurrentSheet, uno::UNO_QUERY);
162 [ + - ]: 224 : uno::Reference <beans::XPropertySet> xProperties(xCurrentSheet, uno::UNO_QUERY);
163 [ + - ]: 224 : if ( xProperties.is() )
164 : : {
165 [ + - ]: 224 : XMLTableStylesContext *pStyles = (XMLTableStylesContext *)rImport.GetAutoStyles();
166 [ + - ]: 224 : if ( pStyles )
167 : : {
168 : : XMLTableStyleContext* pStyle = (XMLTableStyleContext *)pStyles->FindStyleChildContext(
169 [ + - ]: 224 : XML_STYLE_FAMILY_TABLE_TABLE, sStyleName, true);
170 [ + - ]: 224 : if ( pStyle )
171 : : {
172 [ + - ]: 224 : pStyle->FillPropertySet(xProperties);
173 : :
174 [ + - ][ + - ]: 224 : ScSheetSaveData* pSheetData = ScModelObj::getImplementation(rImport.GetModel())->GetSheetSaveData();
175 [ + - ]: 224 : pSheetData->AddTableStyle( sStyleName, ScAddress( 0, 0, maCurrentCellPos.Tab() ) );
176 : : }
177 : : }
178 : 224 : }
179 : : }
180 : : }
181 : 224 : }
182 : :
183 : 6296091 : void ScMyTables::AddRow()
184 : : {
185 : 6296091 : maCurrentCellPos.SetRow(maCurrentCellPos.Row() + 1);
186 : 6296091 : maCurrentCellPos.SetCol(-1); //reset columns for new row
187 : 6296091 : }
188 : :
189 : 4404 : void ScMyTables::SetRowStyle(const rtl::OUString& rCellStyleName)
190 : : {
191 : 4404 : rImport.GetStylesImportHelper()->SetRowStyle(rCellStyleName);
192 : 4404 : }
193 : :
194 : 6310116 : void ScMyTables::AddColumn(bool bIsCovered)
195 : : {
196 : 6310116 : maCurrentCellPos.SetCol( maCurrentCellPos.Col() + 1 );
197 : : //here only need to set column style if this is the first row and
198 : : //the cell is not covered.
199 [ + + ][ + + ]: 6310116 : if(maCurrentCellPos.Row() == 0 && !bIsCovered)
[ + + ]
200 : 1862 : rImport.GetStylesImportHelper()->InsertCol(maCurrentCellPos.Col(), maCurrentCellPos.Tab(), rImport.GetDocument());
201 : 6310116 : }
202 : :
203 : 224 : void ScMyTables::DeleteTable()
204 : : {
205 [ + - ]: 224 : ScXMLImport::MutexGuard aGuard(rImport);
206 : :
207 [ + - ]: 224 : rImport.GetStylesImportHelper()->SetStylesToRanges();
208 [ + - ]: 224 : rImport.SetStylesToRangesFinished();
209 : :
210 [ + - ]: 224 : maMatrixRangeList.RemoveAll();
211 : :
212 [ + - ][ - + ]: 224 : if (rImport.GetDocument() && maProtectionData.mbProtected)
[ - + ]
213 : : {
214 [ # # ]: 0 : uno::Sequence<sal_Int8> aHash;
215 [ # # ]: 0 : ::sax::Converter::decodeBase64(aHash, maProtectionData.maPassword);
216 : :
217 : : SAL_WNODEPRECATED_DECLARATIONS_PUSH
218 [ # # ][ # # ]: 0 : auto_ptr<ScTableProtection> pProtect(new ScTableProtection);
219 : : SAL_WNODEPRECATED_DECLARATIONS_POP
220 [ # # ]: 0 : pProtect->setProtected(maProtectionData.mbProtected);
221 [ # # ]: 0 : pProtect->setPasswordHash(aHash, maProtectionData.meHash1, maProtectionData.meHash2);
222 [ # # ]: 0 : pProtect->setOption(ScTableProtection::SELECT_LOCKED_CELLS, maProtectionData.mbSelectProtectedCells);
223 [ # # ]: 0 : pProtect->setOption(ScTableProtection::SELECT_UNLOCKED_CELLS, maProtectionData.mbSelectUnprotectedCells);
224 [ # # ][ # # ]: 0 : rImport.GetDocument()->SetTabProtection(maCurrentCellPos.Tab(), pProtect.get());
[ # # ]
225 [ + - ]: 224 : }
226 : 224 : }
227 : :
228 : 329 : void ScMyTables::AddColStyle(const sal_Int32 nRepeat, const rtl::OUString& rCellStyleName)
229 : : {
230 : 329 : rImport.GetStylesImportHelper()->AddColumnStyle(rCellStyleName, nCurrentColCount, nRepeat);
231 : 329 : nCurrentColCount += nRepeat;
232 : 329 : }
233 : :
234 : 39 : uno::Reference< drawing::XDrawPage > ScMyTables::GetCurrentXDrawPage()
235 : : {
236 [ + + ][ - + ]: 39 : if( (maCurrentCellPos.Tab() != nCurrentDrawPage) || !xDrawPage.is() )
[ + + ]
237 : : {
238 [ + - ]: 34 : uno::Reference<drawing::XDrawPageSupplier> xDrawPageSupplier( xCurrentSheet, uno::UNO_QUERY );
239 [ + - ]: 34 : if( xDrawPageSupplier.is() )
240 [ + - ][ + - ]: 34 : xDrawPage.set(xDrawPageSupplier->getDrawPage());
[ + - ]
241 : 34 : nCurrentDrawPage = sal::static_int_cast<sal_Int16>(maCurrentCellPos.Tab());
242 : : }
243 : 39 : return xDrawPage;
244 : : }
245 : :
246 : 152 : uno::Reference< drawing::XShapes > ScMyTables::GetCurrentXShapes()
247 : : {
248 [ + + ][ - + ]: 152 : if( (maCurrentCellPos.Tab() != nCurrentXShapes) || !xShapes.is() )
[ + + ]
249 : : {
250 [ + - ]: 12 : xShapes.set(GetCurrentXDrawPage(), uno::UNO_QUERY);
251 [ + - ][ + - ]: 12 : rImport.GetShapeImport()->startPage(xShapes);
252 [ + - ][ + - ]: 12 : rImport.GetShapeImport()->pushGroupForSorting ( xShapes );
253 : 12 : nCurrentXShapes = sal::static_int_cast<sal_Int16>(maCurrentCellPos.Tab());
254 : 12 : return xShapes;
255 : : }
256 : : else
257 : 152 : return xShapes;
258 : : }
259 : :
260 : 224 : bool ScMyTables::HasDrawPage()
261 : : {
262 [ + + ][ + - ]: 224 : return !((maCurrentCellPos.Tab() != nCurrentDrawPage) || !xDrawPage.is());
263 : : }
264 : :
265 : 34 : bool ScMyTables::HasXShapes()
266 : : {
267 [ + + ][ + - ]: 34 : return !((maCurrentCellPos.Tab() != nCurrentXShapes) || !xShapes.is());
268 : : }
269 : :
270 : 0 : void ScMyTables::AddOLE(uno::Reference <drawing::XShape>& rShape,
271 : : const rtl::OUString &rRangeList)
272 : : {
273 : 0 : aFixupOLEs.AddOLE(rShape, rRangeList);
274 : 0 : }
275 : :
276 : 75 : void ScMyTables::AddMatrixRange(
277 : : const SCCOL nStartColumn, const SCROW nStartRow, const SCCOL nEndColumn, const SCROW nEndRow,
278 : : const rtl::OUString& rFormula, const rtl::OUString& rFormulaNmsp, const formula::FormulaGrammar::Grammar eGrammar)
279 : : {
280 : : OSL_ENSURE(nEndRow >= nStartRow, "wrong row order");
281 : : OSL_ENSURE(nEndColumn >= nStartColumn, "wrong column order");
282 : : ScRange aScRange(
283 : 75 : nStartColumn, nStartRow, maCurrentCellPos.Tab(),
284 : 75 : nEndColumn, nEndRow, maCurrentCellPos.Tab()
285 : 75 : );
286 : :
287 [ + - ]: 75 : maMatrixRangeList.Append(aScRange);
288 : :
289 : 75 : ScDocument* pDoc = rImport.GetDocument();
290 [ + - ]: 75 : ScMarkData aMark;
291 [ + - ]: 75 : aMark.SetMarkArea( aScRange );
292 [ + - ]: 75 : aMark.SelectTable( aScRange.aStart.Tab(), sal_True );
293 [ + - ][ + - ]: 75 : ScTokenArray* pCode = new ScTokenArray;
294 [ + - ][ + - ]: 75 : pCode->AddStringXML( rFormula );
[ + - ]
295 [ - + ][ # # ]: 75 : if( (eGrammar == formula::FormulaGrammar::GRAM_EXTERNAL) && !rFormulaNmsp.isEmpty() )
[ - + ]
296 [ # # ][ # # ]: 0 : pCode->AddStringXML( rFormulaNmsp );
[ # # ]
297 : : pDoc->InsertMatrixFormula(
298 : 75 : aScRange.aStart.Col(), aScRange.aStart.Row(),
299 : 75 : aScRange.aEnd.Col(), aScRange.aEnd.Row(),
300 [ + - ][ + - ]: 225 : aMark, EMPTY_STRING, pCode, eGrammar );
[ + - ]
301 [ + - ][ + - ]: 75 : delete pCode;
302 [ + - ]: 75 : pDoc->IncXMLImportedFormulaCount( rFormula.getLength() );
303 : 75 : }
304 : :
305 : 4905 : bool ScMyTables::IsPartOfMatrix(const ScAddress& rScAddress) const
306 : : {
307 [ + + ]: 4905 : if (!maMatrixRangeList.empty())
308 [ + - ]: 3321 : return maMatrixRangeList.In(rScAddress);
309 : 4905 : return false;
310 : : }
311 : :
312 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|