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
28
29 #include <tools/debug.hxx>
30 #include <svl/smplhint.hxx>
31 #include <svl/zforlist.hxx>
32 #include <rtl/uuid.h>
33
34 #include <com/sun/star/awt/XBitmap.hpp>
35 #include <com/sun/star/util/SortField.hpp>
36 #include <com/sun/star/table/TableSortField.hpp>
37 #include <com/sun/star/beans/PropertyAttribute.hpp>
38 #include <com/sun/star/table/TableOrientation.hpp>
39 #include <com/sun/star/table/CellRangeAddress.hpp>
40 #include <com/sun/star/sheet/DataImportMode.hpp>
41 #include <com/sun/star/sheet/FilterOperator2.hpp>
42 #include <com/sun/star/sheet/TableFilterField2.hpp>
43
44 #include "datauno.hxx"
45 #include "dapiuno.hxx"
46 #include "cellsuno.hxx"
47 #include "miscuno.hxx"
48 #include "targuno.hxx"
49 #include "rangeutl.hxx"
50 #include "dbcolect.hxx"
51 #include "docsh.hxx"
52 #include "dbdocfun.hxx"
53 #include "unoguard.hxx"
54 #include "unonames.hxx"
55 #include "globstr.hrc"
56 #ifndef SC_CONVUNO_HXX
57 #include "convuno.hxx"
58 #include "hints.hxx"
59 #endif
60 #include "attrib.hxx"
61 #include "dpshttab.hxx"
62 #include <comphelper/extract.hxx>
63 #include <svx/dataaccessdescriptor.hxx>
64
65 using namespace com::sun::star;
66
67 SV_IMPL_PTRARR( XDBRefreshListenerArr_Impl, XDBRefreshListenerPtr );
68
69 //------------------------------------------------------------------------
70
71 // alles ohne Which-ID, Map nur fuer PropertySetInfo
72
lcl_GetSubTotalPropertyMap()73 const SfxItemPropertyMapEntry* lcl_GetSubTotalPropertyMap()
74 {
75 // some old property names are for 5.2 compatibility
76
77 static SfxItemPropertyMapEntry aSubTotalPropertyMap_Impl[] =
78 {
79 {MAP_CHAR_LEN(SC_UNONAME_BINDFMT), 0, &getBooleanCppuType(), 0, 0},
80 {MAP_CHAR_LEN(SC_UNONAME_CASE), 0, &getBooleanCppuType(), 0, 0},
81 {MAP_CHAR_LEN(SC_UNONAME_ENABSORT), 0, &getBooleanCppuType(), 0, 0},
82 {MAP_CHAR_LEN(SC_UNONAME_ENUSLIST), 0, &getBooleanCppuType(), 0, 0},
83 {MAP_CHAR_LEN(SC_UNONAME_FORMATS), 0, &getBooleanCppuType(), 0, 0},
84 {MAP_CHAR_LEN(SC_UNONAME_INSBRK), 0, &getBooleanCppuType(), 0, 0},
85 {MAP_CHAR_LEN(SC_UNONAME_ISCASE), 0, &getBooleanCppuType(), 0, 0},
86 {MAP_CHAR_LEN(SC_UNONAME_MAXFLD), 0, &getCppuType((sal_Int32*)0), beans::PropertyAttribute::READONLY, 0},
87 {MAP_CHAR_LEN(SC_UNONAME_SORTASC), 0, &getBooleanCppuType(), 0, 0},
88 {MAP_CHAR_LEN(SC_UNONAME_ULIST), 0, &getBooleanCppuType(), 0, 0},
89 {MAP_CHAR_LEN(SC_UNONAME_UINDEX), 0, &getCppuType((sal_Int32*)0), 0, 0},
90 {MAP_CHAR_LEN(SC_UNONAME_USINDEX), 0, &getCppuType((sal_Int32*)0), 0, 0},
91 {0,0,0,0,0,0}
92 };
93 return aSubTotalPropertyMap_Impl;
94 }
95
lcl_GetFilterPropertyMap()96 const SfxItemPropertyMapEntry* lcl_GetFilterPropertyMap()
97 {
98 static SfxItemPropertyMapEntry aFilterPropertyMap_Impl[] =
99 {
100 {MAP_CHAR_LEN(SC_UNONAME_CONTHDR), 0, &getBooleanCppuType(), 0, 0},
101 {MAP_CHAR_LEN(SC_UNONAME_COPYOUT), 0, &getBooleanCppuType(), 0, 0},
102 {MAP_CHAR_LEN(SC_UNONAME_ISCASE), 0, &getBooleanCppuType(), 0, 0},
103 {MAP_CHAR_LEN(SC_UNONAME_MAXFLD), 0, &getCppuType((sal_Int32*)0), beans::PropertyAttribute::READONLY, 0},
104 {MAP_CHAR_LEN(SC_UNONAME_ORIENT), 0, &getCppuType((table::TableOrientation*)0), 0, 0},
105 {MAP_CHAR_LEN(SC_UNONAME_OUTPOS), 0, &getCppuType((table::CellAddress*)0), 0, 0},
106 {MAP_CHAR_LEN(SC_UNONAME_SAVEOUT), 0, &getBooleanCppuType(), 0, 0},
107 {MAP_CHAR_LEN(SC_UNONAME_SKIPDUP), 0, &getBooleanCppuType(), 0, 0},
108 {MAP_CHAR_LEN(SC_UNONAME_USEREGEX), 0, &getBooleanCppuType(), 0, 0},
109 {0,0,0,0,0,0}
110 };
111 return aFilterPropertyMap_Impl;
112 }
113
lcl_GetDBRangePropertyMap()114 const SfxItemPropertyMapEntry* lcl_GetDBRangePropertyMap()
115 {
116 static SfxItemPropertyMapEntry aDBRangePropertyMap_Impl[] =
117 {
118 {MAP_CHAR_LEN(SC_UNONAME_AUTOFLT), 0, &getBooleanCppuType(), 0, 0},
119 {MAP_CHAR_LEN(SC_UNONAME_FLTCRT), 0, &getCppuType((table::CellRangeAddress*)0), 0, 0},
120 {MAP_CHAR_LEN(SC_UNONAME_FROMSELECT),0, &getBooleanCppuType(), 0, 0},
121 {MAP_CHAR_LEN(SC_UNONAME_ISUSER), 0, &getBooleanCppuType(), beans::PropertyAttribute::READONLY, 0 },
122 {MAP_CHAR_LEN(SC_UNONAME_KEEPFORM), 0, &getBooleanCppuType(), 0, 0},
123 {MAP_CHAR_LEN(SC_UNO_LINKDISPBIT), 0, &getCppuType((uno::Reference<awt::XBitmap>*)0), beans::PropertyAttribute::READONLY, 0 },
124 {MAP_CHAR_LEN(SC_UNO_LINKDISPNAME), 0, &getCppuType((rtl::OUString*)0), beans::PropertyAttribute::READONLY, 0 },
125 {MAP_CHAR_LEN(SC_UNONAME_MOVCELLS), 0, &getBooleanCppuType(), 0, 0},
126 {MAP_CHAR_LEN(SC_UNONAME_REFPERIOD), 0, &getCppuType((sal_Int32*)0), 0, 0},
127 {MAP_CHAR_LEN(SC_UNONAME_STRIPDAT), 0, &getBooleanCppuType(), 0, 0},
128 {MAP_CHAR_LEN(SC_UNONAME_TOKENINDEX),0, &getCppuType((sal_Int32*)0), beans::PropertyAttribute::READONLY, 0 },
129 {MAP_CHAR_LEN(SC_UNONAME_USEFLTCRT),0, &getBooleanCppuType(), 0, 0},
130 {0,0,0,0,0,0}
131 };
132 return aDBRangePropertyMap_Impl;
133 }
134
135
136 //------------------------------------------------------------------------
137
138 #define SCDATABASERANGEOBJ_SERVICE "com.sun.star.sheet.DatabaseRange"
139
140 SC_SIMPLE_SERVICE_INFO( ScConsolidationDescriptor, "ScConsolidationDescriptor", "com.sun.star.sheet.ConsolidationDescriptor" )
141 SC_SIMPLE_SERVICE_INFO( ScDatabaseRangesObj, "ScDatabaseRangesObj", "com.sun.star.sheet.DatabaseRanges" )
142 SC_SIMPLE_SERVICE_INFO( ScFilterDescriptorBase, "ScFilterDescriptorBase", "com.sun.star.sheet.SheetFilterDescriptor" )
143 SC_SIMPLE_SERVICE_INFO( ScSubTotalDescriptorBase, "ScSubTotalDescriptorBase", "com.sun.star.sheet.SubTotalDescriptor" )
144 SC_SIMPLE_SERVICE_INFO( ScSubTotalFieldObj, "ScSubTotalFieldObj", "com.sun.star.sheet.SubTotalField" )
145
146
147 //------------------------------------------------------------------------
148
149 // static
GeneralToSubTotal(sheet::GeneralFunction eSummary)150 ScSubTotalFunc ScDataUnoConversion::GeneralToSubTotal( sheet::GeneralFunction eSummary )
151 {
152 ScSubTotalFunc eSubTotal;
153 switch (eSummary)
154 {
155 case sheet::GeneralFunction_NONE: eSubTotal = SUBTOTAL_FUNC_NONE; break;
156 case sheet::GeneralFunction_SUM: eSubTotal = SUBTOTAL_FUNC_SUM; break;
157 case sheet::GeneralFunction_COUNT: eSubTotal = SUBTOTAL_FUNC_CNT2; break;
158 case sheet::GeneralFunction_AVERAGE: eSubTotal = SUBTOTAL_FUNC_AVE; break;
159 case sheet::GeneralFunction_MAX: eSubTotal = SUBTOTAL_FUNC_MAX; break;
160 case sheet::GeneralFunction_MIN: eSubTotal = SUBTOTAL_FUNC_MIN; break;
161 case sheet::GeneralFunction_PRODUCT: eSubTotal = SUBTOTAL_FUNC_PROD; break;
162 case sheet::GeneralFunction_COUNTNUMS: eSubTotal = SUBTOTAL_FUNC_CNT; break;
163 case sheet::GeneralFunction_STDEV: eSubTotal = SUBTOTAL_FUNC_STD; break;
164 case sheet::GeneralFunction_STDEVP: eSubTotal = SUBTOTAL_FUNC_STDP; break;
165 case sheet::GeneralFunction_VAR: eSubTotal = SUBTOTAL_FUNC_VAR; break;
166 case sheet::GeneralFunction_VARP: eSubTotal = SUBTOTAL_FUNC_VARP; break;
167 case sheet::GeneralFunction_AUTO:
168 default:
169 DBG_ERROR("GeneralToSubTotal: falscher enum");
170 eSubTotal = SUBTOTAL_FUNC_NONE;
171 }
172 return eSubTotal;
173 }
174
175 // static
SubTotalToGeneral(ScSubTotalFunc eSubTotal)176 sheet::GeneralFunction ScDataUnoConversion::SubTotalToGeneral( ScSubTotalFunc eSubTotal )
177 {
178 sheet::GeneralFunction eGeneral;
179 switch (eSubTotal)
180 {
181 case SUBTOTAL_FUNC_NONE: eGeneral = sheet::GeneralFunction_NONE; break;
182 case SUBTOTAL_FUNC_AVE: eGeneral = sheet::GeneralFunction_AVERAGE; break;
183 case SUBTOTAL_FUNC_CNT: eGeneral = sheet::GeneralFunction_COUNTNUMS; break;
184 case SUBTOTAL_FUNC_CNT2: eGeneral = sheet::GeneralFunction_COUNT; break;
185 case SUBTOTAL_FUNC_MAX: eGeneral = sheet::GeneralFunction_MAX; break;
186 case SUBTOTAL_FUNC_MIN: eGeneral = sheet::GeneralFunction_MIN; break;
187 case SUBTOTAL_FUNC_PROD: eGeneral = sheet::GeneralFunction_PRODUCT; break;
188 case SUBTOTAL_FUNC_STD: eGeneral = sheet::GeneralFunction_STDEV; break;
189 case SUBTOTAL_FUNC_STDP: eGeneral = sheet::GeneralFunction_STDEVP; break;
190 case SUBTOTAL_FUNC_SUM: eGeneral = sheet::GeneralFunction_SUM; break;
191 case SUBTOTAL_FUNC_VAR: eGeneral = sheet::GeneralFunction_VAR; break;
192 case SUBTOTAL_FUNC_VARP: eGeneral = sheet::GeneralFunction_VARP; break;
193 default:
194 DBG_ERROR("SubTotalToGeneral: falscher enum");
195 eGeneral = sheet::GeneralFunction_NONE;
196 break;
197 }
198 return eGeneral;
199 }
200
201 //------------------------------------------------------------------------
202
203 // ScImportDescriptor: alles static
204
GetPropertyCount()205 long ScImportDescriptor::GetPropertyCount()
206 {
207 return 4;
208 }
209
FillProperties(uno::Sequence<beans::PropertyValue> & rSeq,const ScImportParam & rParam)210 void ScImportDescriptor::FillProperties( uno::Sequence<beans::PropertyValue>& rSeq, const ScImportParam& rParam )
211 {
212 DBG_ASSERT( rSeq.getLength() == GetPropertyCount(), "falscher Count" );
213
214 beans::PropertyValue* pArray = rSeq.getArray();
215
216 sheet::DataImportMode eMode = sheet::DataImportMode_NONE;
217 if ( rParam.bImport )
218 {
219 if ( rParam.bSql )
220 eMode = sheet::DataImportMode_SQL;
221 else if ( rParam.nType == ScDbQuery )
222 eMode = sheet::DataImportMode_QUERY;
223 else
224 eMode = sheet::DataImportMode_TABLE; // Type ist immer ScDbQuery oder ScDbTable
225 }
226
227 ::svx::ODataAccessDescriptor aDescriptor;
228 aDescriptor.setDataSource(rParam.aDBName);
229 if (aDescriptor.has( svx::daDataSource ))
230 {
231 pArray[0].Name = rtl::OUString::createFromAscii( SC_UNONAME_DBNAME );
232 pArray[0].Value <<= rtl::OUString( rParam.aDBName );
233 }
234 else if (aDescriptor.has( svx::daConnectionResource ))
235 {
236 pArray[0].Name = rtl::OUString::createFromAscii( SC_UNONAME_CONRES );
237 pArray[0].Value <<= rtl::OUString( rParam.aDBName );
238 }
239
240 pArray[1].Name = rtl::OUString::createFromAscii( SC_UNONAME_SRCTYPE );
241 pArray[1].Value <<= eMode;
242
243 pArray[2].Name = rtl::OUString::createFromAscii( SC_UNONAME_SRCOBJ );
244 pArray[2].Value <<= rtl::OUString( rParam.aStatement );
245
246 pArray[3].Name = rtl::OUString::createFromAscii( SC_UNONAME_ISNATIVE );
247 ScUnoHelpFunctions::SetBoolInAny( pArray[3].Value, rParam.bNative );
248 }
249
FillImportParam(ScImportParam & rParam,const uno::Sequence<beans::PropertyValue> & rSeq)250 void ScImportDescriptor::FillImportParam( ScImportParam& rParam, const uno::Sequence<beans::PropertyValue>& rSeq )
251 {
252 rtl::OUString aStrVal;
253 const beans::PropertyValue* pPropArray = rSeq.getConstArray();
254 long nPropCount = rSeq.getLength();
255 for (long i = 0; i < nPropCount; i++)
256 {
257 const beans::PropertyValue& rProp = pPropArray[i];
258 String aPropName(rProp.Name);
259
260 if (aPropName.EqualsAscii( SC_UNONAME_ISNATIVE ))
261 rParam.bNative = ScUnoHelpFunctions::GetBoolFromAny( rProp.Value );
262 else if (aPropName.EqualsAscii( SC_UNONAME_DBNAME ))
263 {
264 if ( rProp.Value >>= aStrVal )
265 rParam.aDBName = String( aStrVal );
266 }
267 else if (aPropName.EqualsAscii( SC_UNONAME_CONRES ))
268 {
269 if ( rProp.Value >>= aStrVal )
270 rParam.aDBName = String( aStrVal );
271 }
272 else if (aPropName.EqualsAscii( SC_UNONAME_SRCOBJ ))
273 {
274 if ( rProp.Value >>= aStrVal )
275 rParam.aStatement = String( aStrVal );
276 }
277 else if (aPropName.EqualsAscii( SC_UNONAME_SRCTYPE ))
278 {
279 //! test for correct enum type?
280 sheet::DataImportMode eMode = (sheet::DataImportMode)
281 ScUnoHelpFunctions::GetEnumFromAny( rProp.Value );
282 switch (eMode)
283 {
284 case sheet::DataImportMode_NONE:
285 rParam.bImport = sal_False;
286 break;
287 case sheet::DataImportMode_SQL:
288 rParam.bImport = sal_True;
289 rParam.bSql = sal_True;
290 break;
291 case sheet::DataImportMode_TABLE:
292 rParam.bImport = sal_True;
293 rParam.bSql = sal_False;
294 rParam.nType = ScDbTable;
295 break;
296 case sheet::DataImportMode_QUERY:
297 rParam.bImport = sal_True;
298 rParam.bSql = sal_False;
299 rParam.nType = ScDbQuery;
300 break;
301 default:
302 DBG_ERROR("falscher Mode");
303 rParam.bImport = sal_False;
304 }
305 }
306 }
307 }
308
309 //------------------------------------------------------------------------
310
311 // ScSortDescriptor: alles static
312
313 //! SortAscending muss aus der SheetSortDescriptor service-Beschreibung raus
314
GetPropertyCount()315 long ScSortDescriptor::GetPropertyCount()
316 {
317 return 9; // TableSortDescriptor and SheetSortDescriptor
318 }
319
FillProperties(uno::Sequence<beans::PropertyValue> & rSeq,const ScSortParam & rParam)320 void ScSortDescriptor::FillProperties( uno::Sequence<beans::PropertyValue>& rSeq, const ScSortParam& rParam )
321 {
322 DBG_ASSERT( rSeq.getLength() == GetPropertyCount(), "falscher Count" );
323
324 beans::PropertyValue* pArray = rSeq.getArray();
325
326 // Uno-Werte zusammensuchen
327
328 table::CellAddress aOutPos;
329 aOutPos.Sheet = rParam.nDestTab;
330 aOutPos.Column = rParam.nDestCol;
331 aOutPos.Row = rParam.nDestRow;
332
333 sal_uInt16 nSortCount = 0;
334 while ( nSortCount < MAXSORT && rParam.bDoSort[nSortCount] )
335 ++nSortCount;
336
337 uno::Sequence<table::TableSortField> aFields(nSortCount);
338 if (nSortCount)
339 {
340 table::TableSortField* pFieldArray = aFields.getArray();
341 for (sal_uInt16 i=0; i<nSortCount; i++)
342 {
343 pFieldArray[i].Field = rParam.nField[i];
344 pFieldArray[i].IsAscending = rParam.bAscending[i];
345 pFieldArray[i].FieldType = table::TableSortFieldType_AUTOMATIC; // immer Automatic
346 pFieldArray[i].IsCaseSensitive = rParam.bCaseSens;
347 pFieldArray[i].CollatorLocale = rParam.aCollatorLocale;
348 pFieldArray[i].CollatorAlgorithm = rtl::OUString( rParam.aCollatorAlgorithm );
349 }
350 }
351
352 // Sequence fuellen
353
354 pArray[0].Name = rtl::OUString::createFromAscii( SC_UNONAME_ISSORTCOLUMNS );
355 pArray[0].Value = ::cppu::bool2any(!rParam.bByRow);
356
357 pArray[1].Name = rtl::OUString::createFromAscii( SC_UNONAME_CONTHDR );
358 ScUnoHelpFunctions::SetBoolInAny( pArray[1].Value, rParam.bHasHeader );
359
360 pArray[2].Name = rtl::OUString::createFromAscii( SC_UNONAME_MAXFLD );
361 pArray[2].Value <<= (sal_Int32) MAXSORT;
362
363 pArray[3].Name = rtl::OUString::createFromAscii( SC_UNONAME_SORTFLD );
364 pArray[3].Value <<= aFields;
365
366 pArray[4].Name = rtl::OUString::createFromAscii( SC_UNONAME_BINDFMT );
367 ScUnoHelpFunctions::SetBoolInAny( pArray[4].Value, rParam.bIncludePattern );
368
369 pArray[5].Name = rtl::OUString::createFromAscii( SC_UNONAME_COPYOUT );
370 ScUnoHelpFunctions::SetBoolInAny( pArray[5].Value, !rParam.bInplace );
371
372 pArray[6].Name = rtl::OUString::createFromAscii( SC_UNONAME_OUTPOS );
373 pArray[6].Value <<= aOutPos;
374
375 pArray[7].Name = rtl::OUString::createFromAscii( SC_UNONAME_ISULIST );
376 ScUnoHelpFunctions::SetBoolInAny( pArray[7].Value, rParam.bUserDef );
377
378 pArray[8].Name = rtl::OUString::createFromAscii( SC_UNONAME_UINDEX );
379 pArray[8].Value <<= (sal_Int32) rParam.nUserIndex;
380 }
381
FillSortParam(ScSortParam & rParam,const uno::Sequence<beans::PropertyValue> & rSeq)382 void ScSortDescriptor::FillSortParam( ScSortParam& rParam, const uno::Sequence<beans::PropertyValue>& rSeq )
383 {
384 sal_Bool bOldSortDescriptor(sal_False);
385 sal_Bool bNewSortDescriptor(sal_False);
386 const beans::PropertyValue* pPropArray = rSeq.getConstArray();
387 long nPropCount = rSeq.getLength();
388 for (long nProp = 0; nProp < nPropCount; nProp++)
389 {
390 const beans::PropertyValue& rProp = pPropArray[nProp];
391 String aPropName(rProp.Name);
392
393 if (aPropName.EqualsAscii( SC_UNONAME_ORIENT ))
394 {
395 bOldSortDescriptor = sal_True;
396 //! test for correct enum type?
397 table::TableOrientation eOrient = (table::TableOrientation)
398 ScUnoHelpFunctions::GetEnumFromAny( rProp.Value );
399 rParam.bByRow = ( eOrient != table::TableOrientation_COLUMNS );
400 }
401 else if (aPropName.EqualsAscii( SC_UNONAME_ISSORTCOLUMNS ))
402 {
403 bNewSortDescriptor = sal_True;
404 rParam.bByRow = !::cppu::any2bool(rProp.Value);
405 }
406 else if (aPropName.EqualsAscii( SC_UNONAME_CONTHDR ))
407 rParam.bHasHeader = ScUnoHelpFunctions::GetBoolFromAny( rProp.Value );
408 else if (aPropName.EqualsAscii( SC_UNONAME_MAXFLD ))
409 {
410 sal_Int32 nVal;
411 if ( (rProp.Value >>= nVal) && nVal > MAXSORT )
412 {
413 //! specify exceptions
414 //! throw lang::IllegalArgumentException();
415 }
416 }
417 else if (aPropName.EqualsAscii( SC_UNONAME_SORTFLD ))
418 {
419 uno::Sequence<util::SortField> aSeq;
420 uno::Sequence<table::TableSortField> aNewSeq;
421 if ( rProp.Value >>= aSeq )
422 {
423 bOldSortDescriptor = sal_True;
424 sal_Int32 nCount = aSeq.getLength();
425 sal_Int32 i;
426 if ( nCount > MAXSORT )
427 {
428 DBG_ERROR("Zu viele Sortierfelder");
429 nCount = MAXSORT;
430 }
431 const util::SortField* pFieldArray = aSeq.getConstArray();
432 for (i=0; i<nCount; i++)
433 {
434 rParam.nField[i] = (SCCOLROW)pFieldArray[i].Field;
435 rParam.bAscending[i] = pFieldArray[i].SortAscending;
436
437 // FieldType wird ignoriert
438 rParam.bDoSort[i] = sal_True;
439 }
440 for (i=nCount; i<MAXSORT; i++)
441 rParam.bDoSort[i] = sal_False;
442 }
443 else if ( rProp.Value >>= aNewSeq )
444 {
445 bNewSortDescriptor = sal_True;
446 sal_Int32 nCount = aNewSeq.getLength();
447 sal_Int32 i;
448 if ( nCount > MAXSORT )
449 {
450 DBG_ERROR("Zu viele Sortierfelder");
451 nCount = MAXSORT;
452 }
453 const table::TableSortField* pFieldArray = aNewSeq.getConstArray();
454 for (i=0; i<nCount; i++)
455 {
456 rParam.nField[i] = (SCCOLROW)pFieldArray[i].Field;
457 rParam.bAscending[i] = pFieldArray[i].IsAscending;
458
459 // only one is possible, sometime we should make it possible to have different for every entry
460 rParam.bCaseSens = pFieldArray[i].IsCaseSensitive;
461 rParam.aCollatorLocale = pFieldArray[i].CollatorLocale;
462 rParam.aCollatorAlgorithm = pFieldArray[i].CollatorAlgorithm;
463
464 // FieldType wird ignoriert
465 rParam.bDoSort[i] = sal_True;
466 }
467 for (i=nCount; i<MAXSORT; i++)
468 rParam.bDoSort[i] = sal_False;
469 }
470 }
471 else if (aPropName.EqualsAscii( SC_UNONAME_ISCASE ))
472 {
473 bOldSortDescriptor = sal_True;
474 rParam.bCaseSens = ScUnoHelpFunctions::GetBoolFromAny( rProp.Value );
475 }
476 else if (aPropName.EqualsAscii( SC_UNONAME_BINDFMT ))
477 rParam.bIncludePattern = ScUnoHelpFunctions::GetBoolFromAny( rProp.Value );
478 else if (aPropName.EqualsAscii( SC_UNONAME_COPYOUT ))
479 rParam.bInplace = !ScUnoHelpFunctions::GetBoolFromAny( rProp.Value );
480 else if (aPropName.EqualsAscii( SC_UNONAME_OUTPOS ))
481 {
482 table::CellAddress aAddress;
483 if ( rProp.Value >>= aAddress )
484 {
485 rParam.nDestTab = aAddress.Sheet;
486 rParam.nDestCol = (SCCOL)aAddress.Column;
487 rParam.nDestRow = (SCROW)aAddress.Row;
488 }
489 }
490 else if (aPropName.EqualsAscii( SC_UNONAME_ISULIST ))
491 rParam.bUserDef = ScUnoHelpFunctions::GetBoolFromAny( rProp.Value );
492 else if (aPropName.EqualsAscii( SC_UNONAME_UINDEX ))
493 {
494 sal_Int32 nVal = 0;
495 if ( rProp.Value >>= nVal )
496 rParam.nUserIndex = (sal_uInt16)nVal;
497 }
498 else if (aPropName.EqualsAscii( SC_UNONAME_COLLLOC ))
499 {
500 bOldSortDescriptor = sal_True;
501 rProp.Value >>= rParam.aCollatorLocale;
502 }
503 else if (aPropName.EqualsAscii( SC_UNONAME_COLLALG ))
504 {
505 bOldSortDescriptor = sal_True;
506 rtl::OUString sStr;
507 if ( rProp.Value >>= sStr )
508 rParam.aCollatorAlgorithm = sStr;
509 }
510 }
511 }
512
513 //------------------------------------------------------------------------
514
ScSubTotalFieldObj(ScSubTotalDescriptorBase * pDesc,sal_uInt16 nP)515 ScSubTotalFieldObj::ScSubTotalFieldObj( ScSubTotalDescriptorBase* pDesc, sal_uInt16 nP ) :
516 xRef( pDesc ), // Objekt festhalten
517 rParent( *pDesc ),
518 nPos( nP )
519 {
520 DBG_ASSERT(pDesc, "ScSubTotalFieldObj: Parent ist 0");
521 }
522
~ScSubTotalFieldObj()523 ScSubTotalFieldObj::~ScSubTotalFieldObj()
524 {
525 }
526
527 // XSubTotalField
528
getGroupColumn()529 sal_Int32 SAL_CALL ScSubTotalFieldObj::getGroupColumn()
530 {
531 ScUnoGuard aGuard;
532 ScSubTotalParam aParam;
533 rParent.GetData(aParam);
534
535 return aParam.nField[nPos];
536 }
537
setGroupColumn(sal_Int32 nGroupColumn)538 void SAL_CALL ScSubTotalFieldObj::setGroupColumn( sal_Int32 nGroupColumn )
539 {
540 ScUnoGuard aGuard;
541 ScSubTotalParam aParam;
542 rParent.GetData(aParam);
543
544 aParam.nField[nPos] = (SCCOL)nGroupColumn;
545
546 rParent.PutData(aParam);
547 }
548
getSubTotalColumns()549 uno::Sequence<sheet::SubTotalColumn> SAL_CALL ScSubTotalFieldObj::getSubTotalColumns()
550 {
551 ScUnoGuard aGuard;
552 ScSubTotalParam aParam;
553 rParent.GetData(aParam);
554
555 SCCOL nCount = aParam.nSubTotals[nPos];
556 uno::Sequence<sheet::SubTotalColumn> aSeq(nCount);
557 sheet::SubTotalColumn* pAry = aSeq.getArray();
558 for (SCCOL i=0; i<nCount; i++)
559 {
560 pAry[i].Column = aParam.pSubTotals[nPos][i];
561 pAry[i].Function = ScDataUnoConversion::SubTotalToGeneral(
562 aParam.pFunctions[nPos][i] );
563 }
564 return aSeq;
565 }
566
setSubTotalColumns(const uno::Sequence<sheet::SubTotalColumn> & aSubTotalColumns)567 void SAL_CALL ScSubTotalFieldObj::setSubTotalColumns(
568 const uno::Sequence<sheet::SubTotalColumn>& aSubTotalColumns )
569 {
570 ScUnoGuard aGuard;
571 ScSubTotalParam aParam;
572 rParent.GetData(aParam);
573
574 sal_uInt32 nColCount = aSubTotalColumns.getLength();
575 if ( nColCount <= sal::static_int_cast<sal_uInt32>(SCCOL_MAX) )
576 {
577 SCCOL nCount = static_cast<SCCOL>(nColCount);
578 aParam.nSubTotals[nPos] = nCount;
579 if (nCount != 0)
580 {
581 aParam.pSubTotals[nPos] = new SCCOL[nCount];
582 aParam.pFunctions[nPos] = new ScSubTotalFunc[nCount];
583
584 const sheet::SubTotalColumn* pAry = aSubTotalColumns.getConstArray();
585 for (SCCOL i=0; i<nCount; i++)
586 {
587 aParam.pSubTotals[nPos][i] = static_cast<SCCOL>(pAry[i].Column);
588 aParam.pFunctions[nPos][i] =
589 ScDataUnoConversion::GeneralToSubTotal( pAry[i].Function );
590 }
591 }
592 else
593 {
594 aParam.pSubTotals[nPos] = NULL;
595 aParam.pFunctions[nPos] = NULL;
596 }
597 }
598 //! sonst Exception oder so? (zuviele Spalten)
599
600 rParent.PutData(aParam);
601 }
602
603 //------------------------------------------------------------------------
604
ScSubTotalDescriptorBase()605 ScSubTotalDescriptorBase::ScSubTotalDescriptorBase() :
606 aPropSet( lcl_GetSubTotalPropertyMap() )
607 {
608 }
609
~ScSubTotalDescriptorBase()610 ScSubTotalDescriptorBase::~ScSubTotalDescriptorBase()
611 {
612 }
613
614 // GetData/PutData hier nur wegen NewInstance-Krempel implementiert...
615
GetData(ScSubTotalParam &) const616 void ScSubTotalDescriptorBase::GetData( ScSubTotalParam& /* rParam */ ) const
617 {
618 DBG_ERROR("ScSubTotalDescriptorBase::GetData soll nicht gerufen werden");
619 }
620
PutData(const ScSubTotalParam &)621 void ScSubTotalDescriptorBase::PutData( const ScSubTotalParam& /* rParam */ )
622 {
623 DBG_ERROR("ScSubTotalDescriptorBase::PutData soll nicht gerufen werden");
624 }
625
626 // XSubTotalDesctiptor
627
GetObjectByIndex_Impl(sal_uInt16 nIndex)628 ScSubTotalFieldObj* ScSubTotalDescriptorBase::GetObjectByIndex_Impl(sal_uInt16 nIndex)
629 {
630 if ( nIndex < getCount() )
631 return new ScSubTotalFieldObj( this, nIndex );
632 return NULL;
633 }
634
clear()635 void SAL_CALL ScSubTotalDescriptorBase::clear()
636 {
637 ScUnoGuard aGuard;
638 ScSubTotalParam aParam;
639 GetData(aParam);
640
641 for (sal_uInt16 i=0; i<MAXSUBTOTAL; i++)
642 aParam.bGroupActive[i] = sal_False;
643
644 //! Notify oder so fuer die Field-Objekte???
645
646 PutData(aParam);
647 }
648
addNew(const uno::Sequence<sheet::SubTotalColumn> & aSubTotalColumns,sal_Int32 nGroupColumn)649 void SAL_CALL ScSubTotalDescriptorBase::addNew(
650 const uno::Sequence<sheet::SubTotalColumn>& aSubTotalColumns,
651 sal_Int32 nGroupColumn )
652 {
653 ScUnoGuard aGuard;
654 ScSubTotalParam aParam;
655 GetData(aParam);
656
657 sal_uInt16 nPos = 0;
658 while ( nPos < MAXSUBTOTAL && aParam.bGroupActive[nPos] )
659 ++nPos;
660
661 sal_uInt32 nColCount = aSubTotalColumns.getLength();
662
663 if ( nPos < MAXSUBTOTAL && nColCount <= sal::static_int_cast<sal_uInt32>(SCCOL_MAX) )
664 {
665 aParam.bGroupActive[nPos] = sal_True;
666 aParam.nField[nPos] = static_cast<SCCOL>(nGroupColumn);
667
668 delete aParam.pSubTotals[nPos];
669 delete aParam.pFunctions[nPos];
670
671 SCCOL nCount = static_cast<SCCOL>(nColCount);
672 aParam.nSubTotals[nPos] = nCount;
673 if (nCount != 0)
674 {
675 aParam.pSubTotals[nPos] = new SCCOL[nCount];
676 aParam.pFunctions[nPos] = new ScSubTotalFunc[nCount];
677
678 const sheet::SubTotalColumn* pAry = aSubTotalColumns.getConstArray();
679 for (SCCOL i=0; i<nCount; i++)
680 {
681 aParam.pSubTotals[nPos][i] = static_cast<SCCOL>(pAry[i].Column);
682 aParam.pFunctions[nPos][i] =
683 ScDataUnoConversion::GeneralToSubTotal( pAry[i].Function );
684 }
685 }
686 else
687 {
688 aParam.pSubTotals[nPos] = NULL;
689 aParam.pFunctions[nPos] = NULL;
690 }
691 }
692 else // too many fields / columns
693 throw uno::RuntimeException(); // no other exceptions specified
694
695 PutData(aParam);
696 }
697
698 // Flags/Einstellungen als Properties
699
700 // XEnumerationAccess
701
createEnumeration()702 uno::Reference<container::XEnumeration> SAL_CALL ScSubTotalDescriptorBase::createEnumeration()
703 {
704 ScUnoGuard aGuard;
705 return new ScIndexEnumeration(this, rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.sheet.SubTotalFieldsEnumeration")));
706 }
707
708 // XIndexAccess
709
getCount()710 sal_Int32 SAL_CALL ScSubTotalDescriptorBase::getCount()
711 {
712 ScUnoGuard aGuard;
713 ScSubTotalParam aParam;
714 GetData(aParam);
715
716 sal_uInt16 nCount = 0;
717 while ( nCount < MAXSUBTOTAL && aParam.bGroupActive[nCount] )
718 ++nCount;
719 return nCount;
720 }
721
getByIndex(sal_Int32 nIndex)722 uno::Any SAL_CALL ScSubTotalDescriptorBase::getByIndex( sal_Int32 nIndex )
723 {
724 ScUnoGuard aGuard;
725 uno::Reference<sheet::XSubTotalField> xField(GetObjectByIndex_Impl((sal_uInt16)nIndex));
726 if (xField.is())
727 return uno::makeAny(xField);
728 else
729 throw lang::IndexOutOfBoundsException();
730 // return uno::Any();
731 }
732
getElementType()733 uno::Type SAL_CALL ScSubTotalDescriptorBase::getElementType()
734 {
735 ScUnoGuard aGuard;
736 return getCppuType((uno::Reference<sheet::XSubTotalField>*)0);
737 }
738
hasElements()739 sal_Bool SAL_CALL ScSubTotalDescriptorBase::hasElements()
740 {
741 ScUnoGuard aGuard;
742 return ( getCount() != 0 );
743 }
744
745 // XPropertySet
746
getPropertySetInfo()747 uno::Reference<beans::XPropertySetInfo> SAL_CALL ScSubTotalDescriptorBase::getPropertySetInfo()
748 {
749 ScUnoGuard aGuard;
750 static uno::Reference<beans::XPropertySetInfo> aRef(
751 new SfxItemPropertySetInfo( aPropSet.getPropertyMap() ));
752 return aRef;
753 }
754
setPropertyValue(const rtl::OUString & aPropertyName,const uno::Any & aValue)755 void SAL_CALL ScSubTotalDescriptorBase::setPropertyValue(
756 const rtl::OUString& aPropertyName, const uno::Any& aValue )
757 {
758 ScUnoGuard aGuard;
759 ScSubTotalParam aParam;
760 GetData(aParam);
761
762 String aString(aPropertyName);
763
764 // some old property names are for 5.2 compatibility
765
766 if (aString.EqualsAscii( SC_UNONAME_CASE ) || aString.EqualsAscii( SC_UNONAME_ISCASE ))
767 aParam.bCaseSens = ScUnoHelpFunctions::GetBoolFromAny( aValue );
768 else if (aString.EqualsAscii( SC_UNONAME_FORMATS ) || aString.EqualsAscii( SC_UNONAME_BINDFMT ))
769 aParam.bIncludePattern = ScUnoHelpFunctions::GetBoolFromAny( aValue );
770 else if (aString.EqualsAscii( SC_UNONAME_ENABSORT ))
771 aParam.bDoSort = ScUnoHelpFunctions::GetBoolFromAny( aValue );
772 else if (aString.EqualsAscii( SC_UNONAME_SORTASC ))
773 aParam.bAscending = ScUnoHelpFunctions::GetBoolFromAny( aValue );
774 else if (aString.EqualsAscii( SC_UNONAME_INSBRK ))
775 aParam.bPagebreak = ScUnoHelpFunctions::GetBoolFromAny( aValue );
776 else if (aString.EqualsAscii( SC_UNONAME_ULIST ) || aString.EqualsAscii( SC_UNONAME_ENUSLIST ))
777 aParam.bUserDef = ScUnoHelpFunctions::GetBoolFromAny( aValue );
778 else if (aString.EqualsAscii( SC_UNONAME_UINDEX ) || aString.EqualsAscii( SC_UNONAME_USINDEX ))
779 {
780 sal_Int32 nVal = 0;
781 if ( aValue >>= nVal )
782 aParam.nUserIndex = (sal_uInt16)nVal;
783 }
784 else if (aString.EqualsAscii( SC_UNONAME_MAXFLD ))
785 {
786 sal_Int32 nVal = 0;
787 if ( (aValue >>= nVal) && nVal > sal::static_int_cast<sal_Int32>(MAXSUBTOTAL) )
788 {
789 throw lang::IllegalArgumentException();
790 }
791 }
792
793 PutData(aParam);
794 }
795
getPropertyValue(const rtl::OUString & aPropertyName)796 uno::Any SAL_CALL ScSubTotalDescriptorBase::getPropertyValue( const rtl::OUString& aPropertyName )
797 {
798 ScUnoGuard aGuard;
799 ScSubTotalParam aParam;
800 GetData(aParam);
801
802 String aString(aPropertyName);
803 uno::Any aRet;
804
805 // some old property names are for 5.2 compatibility
806
807 if (aString.EqualsAscii( SC_UNONAME_CASE ) || aString.EqualsAscii( SC_UNONAME_ISCASE ))
808 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bCaseSens );
809 else if (aString.EqualsAscii( SC_UNONAME_FORMATS ) || aString.EqualsAscii( SC_UNONAME_BINDFMT ))
810 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bIncludePattern );
811 else if (aString.EqualsAscii( SC_UNONAME_ENABSORT ))
812 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bDoSort );
813 else if (aString.EqualsAscii( SC_UNONAME_SORTASC ))
814 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bAscending );
815 else if (aString.EqualsAscii( SC_UNONAME_INSBRK ))
816 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bPagebreak );
817 else if (aString.EqualsAscii( SC_UNONAME_ULIST ) || aString.EqualsAscii( SC_UNONAME_ENUSLIST ))
818 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bUserDef );
819 else if (aString.EqualsAscii( SC_UNONAME_UINDEX ) || aString.EqualsAscii( SC_UNONAME_USINDEX ))
820 aRet <<= (sal_Int32) aParam.nUserIndex;
821 else if (aString.EqualsAscii( SC_UNONAME_MAXFLD ))
822 aRet <<= (sal_Int32) MAXSUBTOTAL;
823
824 return aRet;
825 }
826
SC_IMPL_DUMMY_PROPERTY_LISTENER(ScSubTotalDescriptorBase)827 SC_IMPL_DUMMY_PROPERTY_LISTENER( ScSubTotalDescriptorBase )
828
829 // XUnoTunnel
830
831 sal_Int64 SAL_CALL ScSubTotalDescriptorBase::getSomething(
832 const uno::Sequence<sal_Int8 >& rId )
833 {
834 if ( rId.getLength() == 16 &&
835 0 == rtl_compareMemory( getUnoTunnelId().getConstArray(),
836 rId.getConstArray(), 16 ) )
837 {
838 return sal::static_int_cast<sal_Int64>(reinterpret_cast<sal_IntPtr>(this));
839 }
840 return 0;
841 }
842
843 // static
getUnoTunnelId()844 const uno::Sequence<sal_Int8>& ScSubTotalDescriptorBase::getUnoTunnelId()
845 {
846 static uno::Sequence<sal_Int8> * pSeq = 0;
847 if( !pSeq )
848 {
849 osl::Guard< osl::Mutex > aGuard( osl::Mutex::getGlobalMutex() );
850 if( !pSeq )
851 {
852 static uno::Sequence< sal_Int8 > aSeq( 16 );
853 rtl_createUuid( (sal_uInt8*)aSeq.getArray(), 0, sal_True );
854 pSeq = &aSeq;
855 }
856 }
857 return *pSeq;
858 }
859
860 // static
getImplementation(const uno::Reference<sheet::XSubTotalDescriptor> xObj)861 ScSubTotalDescriptorBase* ScSubTotalDescriptorBase::getImplementation(
862 const uno::Reference<sheet::XSubTotalDescriptor> xObj )
863 {
864 ScSubTotalDescriptorBase* pRet = NULL;
865 uno::Reference<lang::XUnoTunnel> xUT( xObj, uno::UNO_QUERY );
866 if (xUT.is())
867 pRet = reinterpret_cast<ScSubTotalDescriptorBase*>(sal::static_int_cast<sal_IntPtr>(xUT->getSomething(getUnoTunnelId())));
868 return pRet;
869 }
870
871 //------------------------------------------------------------------------
872
ScSubTotalDescriptor()873 ScSubTotalDescriptor::ScSubTotalDescriptor()
874 {
875 }
876
~ScSubTotalDescriptor()877 ScSubTotalDescriptor::~ScSubTotalDescriptor()
878 {
879 }
880
GetData(ScSubTotalParam & rParam) const881 void ScSubTotalDescriptor::GetData( ScSubTotalParam& rParam ) const
882 {
883 rParam = aStoredParam; // Abfrage fuer Interface
884 }
885
PutData(const ScSubTotalParam & rParam)886 void ScSubTotalDescriptor::PutData( const ScSubTotalParam& rParam )
887 {
888 aStoredParam = rParam; // vom Interface gesetzt
889 }
890
SetParam(const ScSubTotalParam & rNew)891 void ScSubTotalDescriptor::SetParam( const ScSubTotalParam& rNew )
892 {
893 aStoredParam = rNew; // von aussen gesetzt
894 }
895
896 //------------------------------------------------------------------------
897
ScRangeSubTotalDescriptor(ScDatabaseRangeObj * pPar)898 ScRangeSubTotalDescriptor::ScRangeSubTotalDescriptor(ScDatabaseRangeObj* pPar) :
899 pParent(pPar)
900 {
901 if (pParent)
902 pParent->acquire();
903 }
904
~ScRangeSubTotalDescriptor()905 ScRangeSubTotalDescriptor::~ScRangeSubTotalDescriptor()
906 {
907 if (pParent)
908 pParent->release();
909 }
910
GetData(ScSubTotalParam & rParam) const911 void ScRangeSubTotalDescriptor::GetData( ScSubTotalParam& rParam ) const
912 {
913 if (pParent)
914 pParent->GetSubTotalParam( rParam );
915 }
916
PutData(const ScSubTotalParam & rParam)917 void ScRangeSubTotalDescriptor::PutData( const ScSubTotalParam& rParam )
918 {
919 if (pParent)
920 pParent->SetSubTotalParam( rParam );
921 }
922
923 //------------------------------------------------------------------------
924
ScConsolidationDescriptor()925 ScConsolidationDescriptor::ScConsolidationDescriptor()
926 {
927 }
928
~ScConsolidationDescriptor()929 ScConsolidationDescriptor::~ScConsolidationDescriptor()
930 {
931 }
932
SetParam(const ScConsolidateParam & rNew)933 void ScConsolidationDescriptor::SetParam( const ScConsolidateParam& rNew )
934 {
935 aParam = rNew;
936 }
937
938 // XConsolidationDescriptor
939
getFunction()940 sheet::GeneralFunction SAL_CALL ScConsolidationDescriptor::getFunction()
941 {
942 ScUnoGuard aGuard;
943 return ScDataUnoConversion::SubTotalToGeneral(aParam.eFunction);
944 }
945
setFunction(sheet::GeneralFunction nFunction)946 void SAL_CALL ScConsolidationDescriptor::setFunction( sheet::GeneralFunction nFunction )
947 {
948 ScUnoGuard aGuard;
949 aParam.eFunction = ScDataUnoConversion::GeneralToSubTotal(nFunction);
950 }
951
getSources()952 uno::Sequence<table::CellRangeAddress> SAL_CALL ScConsolidationDescriptor::getSources()
953 {
954 ScUnoGuard aGuard;
955 sal_uInt16 nCount = aParam.nDataAreaCount;
956 if (!aParam.ppDataAreas)
957 nCount = 0;
958 table::CellRangeAddress aRange;
959 uno::Sequence<table::CellRangeAddress> aSeq(nCount);
960 table::CellRangeAddress* pAry = aSeq.getArray();
961 for (sal_uInt16 i=0; i<nCount; i++)
962 {
963 ScArea* pArea = aParam.ppDataAreas[i];
964 if (pArea)
965 {
966 aRange.Sheet = pArea->nTab;
967 aRange.StartColumn = pArea->nColStart;
968 aRange.StartRow = pArea->nRowStart;
969 aRange.EndColumn = pArea->nColEnd;
970 aRange.EndRow = pArea->nRowEnd;
971 }
972 pAry[i] = aRange;
973 }
974 return aSeq;
975 }
976
setSources(const uno::Sequence<table::CellRangeAddress> & aSources)977 void SAL_CALL ScConsolidationDescriptor::setSources(
978 const uno::Sequence<table::CellRangeAddress>& aSources )
979 {
980 ScUnoGuard aGuard;
981 sal_uInt16 nCount = (sal_uInt16)aSources.getLength();
982 if (nCount)
983 {
984 const table::CellRangeAddress* pAry = aSources.getConstArray();
985 ScArea** pNew = new ScArea*[nCount];
986 sal_uInt16 i;
987 for (i=0; i<nCount; i++)
988 pNew[i] = new ScArea( pAry[i].Sheet,
989 static_cast<SCCOL>(pAry[i].StartColumn), pAry[i].StartRow,
990 static_cast<SCCOL>(pAry[i].EndColumn), pAry[i].EndRow );
991
992 aParam.SetAreas( pNew, nCount ); // kopiert alles
993
994 for (i=0; i<nCount; i++)
995 delete pNew[i];
996 delete[] pNew;
997 }
998 else
999 aParam.ClearDataAreas();
1000 }
1001
getStartOutputPosition()1002 table::CellAddress SAL_CALL ScConsolidationDescriptor::getStartOutputPosition()
1003 {
1004 ScUnoGuard aGuard;
1005 table::CellAddress aPos;
1006 aPos.Column = aParam.nCol;
1007 aPos.Row = aParam.nRow;
1008 aPos.Sheet = aParam.nTab;
1009 return aPos;
1010 }
1011
setStartOutputPosition(const table::CellAddress & aStartOutputPosition)1012 void SAL_CALL ScConsolidationDescriptor::setStartOutputPosition(
1013 const table::CellAddress& aStartOutputPosition )
1014 {
1015 ScUnoGuard aGuard;
1016 aParam.nCol = (SCCOL)aStartOutputPosition.Column;
1017 aParam.nRow = (SCROW)aStartOutputPosition.Row;
1018 aParam.nTab = aStartOutputPosition.Sheet;
1019 }
1020
getUseColumnHeaders()1021 sal_Bool SAL_CALL ScConsolidationDescriptor::getUseColumnHeaders()
1022 {
1023 ScUnoGuard aGuard;
1024 return aParam.bByCol;
1025 }
1026
setUseColumnHeaders(sal_Bool bUseColumnHeaders)1027 void SAL_CALL ScConsolidationDescriptor::setUseColumnHeaders( sal_Bool bUseColumnHeaders )
1028 {
1029 ScUnoGuard aGuard;
1030 aParam.bByCol = bUseColumnHeaders;
1031 }
1032
getUseRowHeaders()1033 sal_Bool SAL_CALL ScConsolidationDescriptor::getUseRowHeaders()
1034 {
1035 ScUnoGuard aGuard;
1036 return aParam.bByRow;
1037 }
1038
setUseRowHeaders(sal_Bool bUseRowHeaders)1039 void SAL_CALL ScConsolidationDescriptor::setUseRowHeaders( sal_Bool bUseRowHeaders )
1040 {
1041 ScUnoGuard aGuard;
1042 aParam.bByRow = bUseRowHeaders;
1043 }
1044
getInsertLinks()1045 sal_Bool SAL_CALL ScConsolidationDescriptor::getInsertLinks()
1046 {
1047 ScUnoGuard aGuard;
1048 return aParam.bReferenceData;
1049 }
1050
setInsertLinks(sal_Bool bInsertLinks)1051 void SAL_CALL ScConsolidationDescriptor::setInsertLinks( sal_Bool bInsertLinks )
1052 {
1053 ScUnoGuard aGuard;
1054 aParam.bReferenceData = bInsertLinks;
1055 }
1056
1057 //------------------------------------------------------------------------
1058
ScFilterDescriptorBase(ScDocShell * pDocShell)1059 ScFilterDescriptorBase::ScFilterDescriptorBase(ScDocShell* pDocShell) :
1060 aPropSet( lcl_GetFilterPropertyMap() ),
1061 pDocSh(pDocShell)
1062 {
1063 if (pDocSh)
1064 pDocSh->GetDocument()->AddUnoObject(*this);
1065 }
1066
~ScFilterDescriptorBase()1067 ScFilterDescriptorBase::~ScFilterDescriptorBase()
1068 {
1069 if (pDocSh)
1070 pDocSh->GetDocument()->RemoveUnoObject(*this);
1071 }
1072
Notify(SfxBroadcaster &,const SfxHint & rHint)1073 void ScFilterDescriptorBase::Notify( SfxBroadcaster&, const SfxHint& rHint )
1074 {
1075 if ( rHint.ISA( SfxSimpleHint ) )
1076 {
1077 sal_uLong nId = ((const SfxSimpleHint&)rHint).GetId();
1078 if ( nId == SFX_HINT_DYING )
1079 {
1080 pDocSh = NULL; // invalid
1081 }
1082 }
1083 }
1084
1085 // XSheetFilterDescriptor and XSheetFilterDescriptor2
1086
getFilterFields()1087 uno::Sequence<sheet::TableFilterField> SAL_CALL ScFilterDescriptorBase::getFilterFields()
1088 {
1089 ScUnoGuard aGuard;
1090 ScQueryParam aParam;
1091 GetData(aParam);
1092
1093 SCSIZE nEntries = aParam.GetEntryCount(); // allozierte Eintraege im Param
1094 SCSIZE nCount = 0; // aktive
1095 while ( nCount < nEntries &&
1096 aParam.GetEntry(nCount).bDoQuery )
1097 ++nCount;
1098
1099 sheet::TableFilterField aField;
1100 uno::Sequence<sheet::TableFilterField> aSeq(static_cast<sal_Int32>(nCount));
1101 sheet::TableFilterField* pAry = aSeq.getArray();
1102 for (SCSIZE i=0; i<nCount; i++)
1103 {
1104 const ScQueryEntry& rEntry = aParam.GetEntry(i);
1105
1106 rtl::OUString aStringValue;
1107 if (rEntry.pStr)
1108 aStringValue = *rEntry.pStr;
1109
1110 aField.Connection = (rEntry.eConnect == SC_AND) ? sheet::FilterConnection_AND :
1111 sheet::FilterConnection_OR;
1112 aField.Field = rEntry.nField;
1113 aField.IsNumeric = !rEntry.bQueryByString;
1114 aField.StringValue = aStringValue;
1115 aField.NumericValue = rEntry.nVal;
1116
1117 switch (rEntry.eOp) // ScQueryOp
1118 {
1119 case SC_EQUAL:
1120 {
1121 aField.Operator = sheet::FilterOperator_EQUAL;
1122 if (!rEntry.bQueryByString && *rEntry.pStr == EMPTY_STRING)
1123 {
1124 if (rEntry.nVal == SC_EMPTYFIELDS)
1125 {
1126 aField.Operator = sheet::FilterOperator_EMPTY;
1127 aField.NumericValue = 0;
1128 }
1129 else if (rEntry.nVal == SC_NONEMPTYFIELDS)
1130 {
1131 aField.Operator = sheet::FilterOperator_NOT_EMPTY;
1132 aField.NumericValue = 0;
1133 }
1134 }
1135 }
1136 break;
1137 case SC_LESS: aField.Operator = sheet::FilterOperator_LESS; break;
1138 case SC_GREATER: aField.Operator = sheet::FilterOperator_GREATER; break;
1139 case SC_LESS_EQUAL: aField.Operator = sheet::FilterOperator_LESS_EQUAL; break;
1140 case SC_GREATER_EQUAL: aField.Operator = sheet::FilterOperator_GREATER_EQUAL; break;
1141 case SC_NOT_EQUAL: aField.Operator = sheet::FilterOperator_NOT_EQUAL; break;
1142 case SC_TOPVAL: aField.Operator = sheet::FilterOperator_TOP_VALUES; break;
1143 case SC_BOTVAL: aField.Operator = sheet::FilterOperator_BOTTOM_VALUES; break;
1144 case SC_TOPPERC: aField.Operator = sheet::FilterOperator_TOP_PERCENT; break;
1145 case SC_BOTPERC: aField.Operator = sheet::FilterOperator_BOTTOM_PERCENT; break;
1146 default:
1147 DBG_ERROR("Falscher Filter-enum");
1148 aField.Operator = sheet::FilterOperator_EMPTY;
1149 }
1150 pAry[i] = aField;
1151 }
1152 return aSeq;
1153 }
1154
getFilterFields2()1155 uno::Sequence<sheet::TableFilterField2> SAL_CALL ScFilterDescriptorBase::getFilterFields2()
1156 {
1157 ScUnoGuard aGuard;
1158 ScQueryParam aParam;
1159 GetData(aParam);
1160
1161 SCSIZE nEntries = aParam.GetEntryCount(); // allozierte Eintraege im Param
1162 SCSIZE nCount = 0; // aktive
1163 while ( nCount < nEntries &&
1164 aParam.GetEntry(nCount).bDoQuery )
1165 ++nCount;
1166
1167 sheet::TableFilterField2 aField;
1168 uno::Sequence<sheet::TableFilterField2> aSeq(static_cast<sal_Int32>(nCount));
1169 sheet::TableFilterField2* pAry = aSeq.getArray();
1170 for (SCSIZE i=0; i<nCount; i++)
1171 {
1172 const ScQueryEntry& rEntry = aParam.GetEntry(i);
1173
1174 rtl::OUString aStringValue;
1175 if (rEntry.pStr)
1176 aStringValue = *rEntry.pStr;
1177
1178 aField.Connection = (rEntry.eConnect == SC_AND) ? sheet::FilterConnection_AND : sheet::FilterConnection_OR;
1179 aField.Field = rEntry.nField;
1180 aField.IsNumeric = !rEntry.bQueryByString;
1181 aField.StringValue = aStringValue;
1182 aField.NumericValue = rEntry.nVal;
1183
1184 switch (rEntry.eOp) // ScQueryOp
1185 {
1186 case SC_EQUAL:
1187 {
1188 aField.Operator = sheet::FilterOperator2::EQUAL;
1189 if (!rEntry.bQueryByString && *rEntry.pStr == EMPTY_STRING)
1190 {
1191 if (rEntry.nVal == SC_EMPTYFIELDS)
1192 {
1193 aField.Operator = sheet::FilterOperator2::EMPTY;
1194 aField.NumericValue = 0;
1195 }
1196 else if (rEntry.nVal == SC_NONEMPTYFIELDS)
1197 {
1198 aField.Operator = sheet::FilterOperator2::NOT_EMPTY;
1199 aField.NumericValue = 0;
1200 }
1201 }
1202 }
1203 break;
1204 case SC_LESS: aField.Operator = sheet::FilterOperator2::LESS; break;
1205 case SC_GREATER: aField.Operator = sheet::FilterOperator2::GREATER; break;
1206 case SC_LESS_EQUAL: aField.Operator = sheet::FilterOperator2::LESS_EQUAL; break;
1207 case SC_GREATER_EQUAL: aField.Operator = sheet::FilterOperator2::GREATER_EQUAL; break;
1208 case SC_NOT_EQUAL: aField.Operator = sheet::FilterOperator2::NOT_EQUAL; break;
1209 case SC_TOPVAL: aField.Operator = sheet::FilterOperator2::TOP_VALUES; break;
1210 case SC_BOTVAL: aField.Operator = sheet::FilterOperator2::BOTTOM_VALUES; break;
1211 case SC_TOPPERC: aField.Operator = sheet::FilterOperator2::TOP_PERCENT; break;
1212 case SC_BOTPERC: aField.Operator = sheet::FilterOperator2::BOTTOM_PERCENT; break;
1213 case SC_CONTAINS: aField.Operator = sheet::FilterOperator2::CONTAINS; break;
1214 case SC_DOES_NOT_CONTAIN: aField.Operator = sheet::FilterOperator2::DOES_NOT_CONTAIN; break;
1215 case SC_BEGINS_WITH: aField.Operator = sheet::FilterOperator2::BEGINS_WITH; break;
1216 case SC_DOES_NOT_BEGIN_WITH: aField.Operator = sheet::FilterOperator2::DOES_NOT_BEGIN_WITH; break;
1217 case SC_ENDS_WITH: aField.Operator = sheet::FilterOperator2::ENDS_WITH; break;
1218 case SC_DOES_NOT_END_WITH: aField.Operator = sheet::FilterOperator2::DOES_NOT_END_WITH; break;
1219 default:
1220 DBG_ERROR("Falscher Filter-enum");
1221 aField.Operator = sheet::FilterOperator2::EMPTY;
1222 }
1223 pAry[i] = aField;
1224 }
1225 return aSeq;
1226 }
1227
setFilterFields(const uno::Sequence<sheet::TableFilterField> & aFilterFields)1228 void SAL_CALL ScFilterDescriptorBase::setFilterFields(
1229 const uno::Sequence<sheet::TableFilterField>& aFilterFields )
1230 {
1231 ScUnoGuard aGuard;
1232 ScQueryParam aParam;
1233 GetData(aParam);
1234
1235 SCSIZE nCount = static_cast<SCSIZE>(aFilterFields.getLength());
1236 DBG_ASSERT( nCount <= MAXQUERY, "setFilterFields: zu viele" );
1237
1238 aParam.Resize( nCount );
1239
1240 const sheet::TableFilterField* pAry = aFilterFields.getConstArray();
1241 SCSIZE i;
1242 for (i=0; i<nCount; i++)
1243 {
1244 ScQueryEntry& rEntry = aParam.GetEntry(i);
1245 if (!rEntry.pStr)
1246 rEntry.pStr = new String; // sollte nicht sein (soll immer initialisiert sein)
1247
1248 rEntry.bDoQuery = sal_True;
1249 rEntry.eConnect = (pAry[i].Connection == sheet::FilterConnection_AND) ? SC_AND : SC_OR;
1250 rEntry.nField = pAry[i].Field;
1251 rEntry.bQueryByString = !pAry[i].IsNumeric;
1252 *rEntry.pStr = String( pAry[i].StringValue );
1253 rEntry.nVal = pAry[i].NumericValue;
1254
1255 if (!rEntry.bQueryByString && pDocSh)
1256 {
1257 pDocSh->GetDocument()->GetFormatTable()->GetInputLineString(rEntry.nVal, 0, *rEntry.pStr);
1258 }
1259
1260 switch (pAry[i].Operator) // FilterOperator
1261 {
1262 case sheet::FilterOperator_EQUAL: rEntry.eOp = SC_EQUAL; break;
1263 case sheet::FilterOperator_LESS: rEntry.eOp = SC_LESS; break;
1264 case sheet::FilterOperator_GREATER: rEntry.eOp = SC_GREATER; break;
1265 case sheet::FilterOperator_LESS_EQUAL: rEntry.eOp = SC_LESS_EQUAL; break;
1266 case sheet::FilterOperator_GREATER_EQUAL: rEntry.eOp = SC_GREATER_EQUAL; break;
1267 case sheet::FilterOperator_NOT_EQUAL: rEntry.eOp = SC_NOT_EQUAL; break;
1268 case sheet::FilterOperator_TOP_VALUES: rEntry.eOp = SC_TOPVAL; break;
1269 case sheet::FilterOperator_BOTTOM_VALUES: rEntry.eOp = SC_BOTVAL; break;
1270 case sheet::FilterOperator_TOP_PERCENT: rEntry.eOp = SC_TOPPERC; break;
1271 case sheet::FilterOperator_BOTTOM_PERCENT: rEntry.eOp = SC_BOTPERC; break;
1272 case sheet::FilterOperator_EMPTY:
1273 {
1274 rEntry.eOp = SC_EQUAL;
1275 rEntry.nVal = SC_EMPTYFIELDS;
1276 rEntry.bQueryByString = sal_False;
1277 *rEntry.pStr = EMPTY_STRING;
1278 }
1279 break;
1280 case sheet::FilterOperator_NOT_EMPTY:
1281 {
1282 rEntry.eOp = SC_EQUAL;
1283 rEntry.nVal = SC_NONEMPTYFIELDS;
1284 rEntry.bQueryByString = sal_False;
1285 *rEntry.pStr = EMPTY_STRING;
1286 }
1287 break;
1288 default:
1289 DBG_ERROR("Falscher Query-enum");
1290 rEntry.eOp = SC_EQUAL;
1291 }
1292 }
1293
1294 SCSIZE nParamCount = aParam.GetEntryCount(); // Param wird nicht unter 8 resized
1295 for (i=nCount; i<nParamCount; i++)
1296 aParam.GetEntry(i).bDoQuery = sal_False; // ueberzaehlige Felder zuruecksetzen
1297
1298 PutData(aParam);
1299 }
1300
setFilterFields2(const uno::Sequence<sheet::TableFilterField2> & aFilterFields)1301 void SAL_CALL ScFilterDescriptorBase::setFilterFields2(
1302 const uno::Sequence<sheet::TableFilterField2>& aFilterFields )
1303 {
1304 ScUnoGuard aGuard;
1305 ScQueryParam aParam;
1306 GetData(aParam);
1307
1308 SCSIZE nCount = static_cast<SCSIZE>(aFilterFields.getLength());
1309 DBG_ASSERT( nCount <= MAXQUERY, "setFilterFields: zu viele" );
1310
1311 aParam.Resize( nCount );
1312
1313 const sheet::TableFilterField2* pAry = aFilterFields.getConstArray();
1314 SCSIZE i;
1315 for (i=0; i<nCount; i++)
1316 {
1317 ScQueryEntry& rEntry = aParam.GetEntry(i);
1318 if (!rEntry.pStr)
1319 rEntry.pStr = new String; // sollte nicht sein (soll immer initialisiert sein)
1320
1321 rEntry.bDoQuery = sal_True;
1322 rEntry.eConnect = (pAry[i].Connection == sheet::FilterConnection_AND) ? SC_AND : SC_OR;
1323 rEntry.nField = pAry[i].Field;
1324 rEntry.bQueryByString = !pAry[i].IsNumeric;
1325 *rEntry.pStr = String( pAry[i].StringValue );
1326 rEntry.nVal = pAry[i].NumericValue;
1327
1328 if (!rEntry.bQueryByString && pDocSh)
1329 {
1330 pDocSh->GetDocument()->GetFormatTable()->GetInputLineString(rEntry.nVal, 0, *rEntry.pStr);
1331 }
1332
1333 switch (pAry[i].Operator) // FilterOperator
1334 {
1335 case sheet::FilterOperator2::EQUAL: rEntry.eOp = SC_EQUAL; break;
1336 case sheet::FilterOperator2::LESS: rEntry.eOp = SC_LESS; break;
1337 case sheet::FilterOperator2::GREATER: rEntry.eOp = SC_GREATER; break;
1338 case sheet::FilterOperator2::LESS_EQUAL: rEntry.eOp = SC_LESS_EQUAL; break;
1339 case sheet::FilterOperator2::GREATER_EQUAL: rEntry.eOp = SC_GREATER_EQUAL; break;
1340 case sheet::FilterOperator2::NOT_EQUAL: rEntry.eOp = SC_NOT_EQUAL; break;
1341 case sheet::FilterOperator2::TOP_VALUES: rEntry.eOp = SC_TOPVAL; break;
1342 case sheet::FilterOperator2::BOTTOM_VALUES: rEntry.eOp = SC_BOTVAL; break;
1343 case sheet::FilterOperator2::TOP_PERCENT: rEntry.eOp = SC_TOPPERC; break;
1344 case sheet::FilterOperator2::BOTTOM_PERCENT: rEntry.eOp = SC_BOTPERC; break;
1345 case sheet::FilterOperator2::CONTAINS: rEntry.eOp = SC_CONTAINS; break;
1346 case sheet::FilterOperator2::DOES_NOT_CONTAIN: rEntry.eOp = SC_DOES_NOT_CONTAIN; break;
1347 case sheet::FilterOperator2::BEGINS_WITH: rEntry.eOp = SC_BEGINS_WITH; break;
1348 case sheet::FilterOperator2::DOES_NOT_BEGIN_WITH: rEntry.eOp = SC_DOES_NOT_BEGIN_WITH;break;
1349 case sheet::FilterOperator2::ENDS_WITH: rEntry.eOp = SC_ENDS_WITH; break;
1350 case sheet::FilterOperator2::DOES_NOT_END_WITH: rEntry.eOp = SC_DOES_NOT_END_WITH; break;
1351 case sheet::FilterOperator2::EMPTY:
1352 {
1353 rEntry.eOp = SC_EQUAL;
1354 rEntry.nVal = SC_EMPTYFIELDS;
1355 rEntry.bQueryByString = sal_False;
1356 *rEntry.pStr = EMPTY_STRING;
1357 }
1358 break;
1359 case sheet::FilterOperator2::NOT_EMPTY:
1360 {
1361 rEntry.eOp = SC_EQUAL;
1362 rEntry.nVal = SC_NONEMPTYFIELDS;
1363 rEntry.bQueryByString = sal_False;
1364 *rEntry.pStr = EMPTY_STRING;
1365 }
1366 break;
1367 default:
1368 DBG_ERROR("Falscher Query-enum");
1369 rEntry.eOp = SC_EQUAL;
1370 }
1371 }
1372
1373 SCSIZE nParamCount = aParam.GetEntryCount(); // Param wird nicht unter 8 resized
1374 for (i=nCount; i<nParamCount; i++)
1375 aParam.GetEntry(i).bDoQuery = sal_False; // ueberzaehlige Felder zuruecksetzen
1376
1377 PutData(aParam);
1378 }
1379
1380 // Rest sind Properties
1381
1382 // XPropertySet
1383
getPropertySetInfo()1384 uno::Reference<beans::XPropertySetInfo> SAL_CALL ScFilterDescriptorBase::getPropertySetInfo()
1385 {
1386 ScUnoGuard aGuard;
1387 static uno::Reference<beans::XPropertySetInfo> aRef(
1388 new SfxItemPropertySetInfo( aPropSet.getPropertyMap() ));
1389 return aRef;
1390 }
1391
setPropertyValue(const rtl::OUString & aPropertyName,const uno::Any & aValue)1392 void SAL_CALL ScFilterDescriptorBase::setPropertyValue(
1393 const rtl::OUString& aPropertyName, const uno::Any& aValue )
1394 {
1395 ScUnoGuard aGuard;
1396 ScQueryParam aParam;
1397 GetData(aParam);
1398
1399 String aString(aPropertyName);
1400 if (aString.EqualsAscii( SC_UNONAME_CONTHDR ))
1401 aParam.bHasHeader = ScUnoHelpFunctions::GetBoolFromAny( aValue );
1402 else if (aString.EqualsAscii( SC_UNONAME_COPYOUT ))
1403 aParam.bInplace = !(ScUnoHelpFunctions::GetBoolFromAny( aValue ));
1404 else if (aString.EqualsAscii( SC_UNONAME_ISCASE ))
1405 aParam.bCaseSens = ScUnoHelpFunctions::GetBoolFromAny( aValue );
1406 else if (aString.EqualsAscii( SC_UNONAME_MAXFLD ))
1407 {
1408 sal_Int32 nVal = 0;
1409 if ( (aValue >>= nVal) && nVal > sal::static_int_cast<sal_Int32>(MAXQUERY) )
1410 {
1411 throw lang::IllegalArgumentException();
1412 }
1413 }
1414 else if (aString.EqualsAscii( SC_UNONAME_ORIENT ))
1415 {
1416 //! test for correct enum type?
1417 table::TableOrientation eOrient = (table::TableOrientation)
1418 ScUnoHelpFunctions::GetEnumFromAny( aValue );
1419 aParam.bByRow = ( eOrient != table::TableOrientation_COLUMNS );
1420 }
1421 else if (aString.EqualsAscii( SC_UNONAME_OUTPOS ))
1422 {
1423 table::CellAddress aAddress;
1424 if ( aValue >>= aAddress )
1425 {
1426 aParam.nDestTab = aAddress.Sheet;
1427 aParam.nDestCol = (SCCOL)aAddress.Column;
1428 aParam.nDestRow = (SCROW)aAddress.Row;
1429 }
1430 }
1431 else if (aString.EqualsAscii( SC_UNONAME_SAVEOUT ))
1432 aParam.bDestPers = ScUnoHelpFunctions::GetBoolFromAny( aValue );
1433 else if (aString.EqualsAscii( SC_UNONAME_SKIPDUP ))
1434 aParam.bDuplicate = !(ScUnoHelpFunctions::GetBoolFromAny( aValue ));
1435 else if (aString.EqualsAscii( SC_UNONAME_USEREGEX ))
1436 aParam.bRegExp = ScUnoHelpFunctions::GetBoolFromAny( aValue );
1437
1438 PutData(aParam);
1439 }
1440
getPropertyValue(const rtl::OUString & aPropertyName)1441 uno::Any SAL_CALL ScFilterDescriptorBase::getPropertyValue( const rtl::OUString& aPropertyName )
1442 {
1443 ScUnoGuard aGuard;
1444 ScQueryParam aParam;
1445 GetData(aParam);
1446
1447 String aString(aPropertyName);
1448 uno::Any aRet;
1449
1450 if (aString.EqualsAscii( SC_UNONAME_CONTHDR ))
1451 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bHasHeader );
1452 else if (aString.EqualsAscii( SC_UNONAME_COPYOUT ))
1453 ScUnoHelpFunctions::SetBoolInAny( aRet, !(aParam.bInplace) );
1454 else if (aString.EqualsAscii( SC_UNONAME_ISCASE ))
1455 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bCaseSens );
1456 else if (aString.EqualsAscii( SC_UNONAME_MAXFLD ))
1457 aRet <<= (sal_Int32) MAXQUERY;
1458 else if (aString.EqualsAscii( SC_UNONAME_ORIENT ))
1459 {
1460 table::TableOrientation eOrient = aParam.bByRow ? table::TableOrientation_ROWS :
1461 table::TableOrientation_COLUMNS;
1462 aRet <<= eOrient;
1463 }
1464 else if (aString.EqualsAscii( SC_UNONAME_OUTPOS ))
1465 {
1466 table::CellAddress aOutPos;
1467 aOutPos.Sheet = aParam.nDestTab;
1468 aOutPos.Column = aParam.nDestCol;
1469 aOutPos.Row = aParam.nDestRow;
1470 aRet <<= aOutPos;
1471 }
1472 else if (aString.EqualsAscii( SC_UNONAME_SAVEOUT ))
1473 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bDestPers );
1474 else if (aString.EqualsAscii( SC_UNONAME_SKIPDUP ))
1475 ScUnoHelpFunctions::SetBoolInAny( aRet, !(aParam.bDuplicate) );
1476 else if (aString.EqualsAscii( SC_UNONAME_USEREGEX ))
1477 ScUnoHelpFunctions::SetBoolInAny( aRet, aParam.bRegExp );
1478
1479 return aRet;
1480 }
1481
SC_IMPL_DUMMY_PROPERTY_LISTENER(ScFilterDescriptorBase)1482 SC_IMPL_DUMMY_PROPERTY_LISTENER( ScFilterDescriptorBase )
1483
1484 //------------------------------------------------------------------------
1485
1486 ScFilterDescriptor::ScFilterDescriptor(ScDocShell* pDocShell)
1487 :
1488 ScFilterDescriptorBase(pDocShell)
1489 {
1490 }
1491
~ScFilterDescriptor()1492 ScFilterDescriptor::~ScFilterDescriptor()
1493 {
1494 }
1495
GetData(ScQueryParam & rParam) const1496 void ScFilterDescriptor::GetData( ScQueryParam& rParam ) const
1497 {
1498 rParam = aStoredParam; // Abfrage fuer Interface
1499 }
1500
PutData(const ScQueryParam & rParam)1501 void ScFilterDescriptor::PutData( const ScQueryParam& rParam )
1502 {
1503 aStoredParam = rParam; // vom Interface gesetzt
1504 }
1505
SetParam(const ScQueryParam & rNew)1506 void ScFilterDescriptor::SetParam( const ScQueryParam& rNew )
1507 {
1508 aStoredParam = rNew; // von aussen gesetzt
1509 }
1510
1511 //------------------------------------------------------------------------
1512
ScRangeFilterDescriptor(ScDocShell * pDocShell,ScDatabaseRangeObj * pPar)1513 ScRangeFilterDescriptor::ScRangeFilterDescriptor(ScDocShell* pDocShell, ScDatabaseRangeObj* pPar) :
1514 ScFilterDescriptorBase(pDocShell),
1515 pParent(pPar)
1516 {
1517 if (pParent)
1518 pParent->acquire();
1519 }
1520
~ScRangeFilterDescriptor()1521 ScRangeFilterDescriptor::~ScRangeFilterDescriptor()
1522 {
1523 if (pParent)
1524 pParent->release();
1525 }
1526
GetData(ScQueryParam & rParam) const1527 void ScRangeFilterDescriptor::GetData( ScQueryParam& rParam ) const
1528 {
1529 if (pParent)
1530 pParent->GetQueryParam( rParam );
1531 }
1532
PutData(const ScQueryParam & rParam)1533 void ScRangeFilterDescriptor::PutData( const ScQueryParam& rParam )
1534 {
1535 if (pParent)
1536 pParent->SetQueryParam( rParam );
1537 }
1538
1539 //------------------------------------------------------------------------
1540
ScDataPilotFilterDescriptor(ScDocShell * pDocShell,ScDataPilotDescriptorBase * pPar)1541 ScDataPilotFilterDescriptor::ScDataPilotFilterDescriptor(ScDocShell* pDocShell, ScDataPilotDescriptorBase* pPar) :
1542 ScFilterDescriptorBase(pDocShell),
1543 pParent(pPar)
1544 {
1545 if (pParent)
1546 pParent->acquire();
1547 }
1548
~ScDataPilotFilterDescriptor()1549 ScDataPilotFilterDescriptor::~ScDataPilotFilterDescriptor()
1550 {
1551 if (pParent)
1552 pParent->release();
1553 }
1554
GetData(ScQueryParam & rParam) const1555 void ScDataPilotFilterDescriptor::GetData( ScQueryParam& rParam ) const
1556 {
1557 if (pParent)
1558 {
1559 ScDPObject* pDPObj = pParent->GetDPObject();
1560 if (pDPObj && pDPObj->IsSheetData())
1561 rParam = pDPObj->GetSheetDesc()->aQueryParam;
1562 }
1563 }
1564
PutData(const ScQueryParam & rParam)1565 void ScDataPilotFilterDescriptor::PutData( const ScQueryParam& rParam )
1566 {
1567 if (pParent)
1568 {
1569 ScDPObject* pDPObj = pParent->GetDPObject();
1570 if (pDPObj)
1571 {
1572 ScSheetSourceDesc aSheetDesc;
1573 if (pDPObj->IsSheetData())
1574 aSheetDesc = *pDPObj->GetSheetDesc();
1575 aSheetDesc.aQueryParam = rParam;
1576 pDPObj->SetSheetDesc(aSheetDesc);
1577 pParent->SetDPObject(pDPObj);
1578 }
1579 }
1580 }
1581
1582 //------------------------------------------------------------------------
1583
ScDatabaseRangeObj(ScDocShell * pDocSh,const String & rNm)1584 ScDatabaseRangeObj::ScDatabaseRangeObj(ScDocShell* pDocSh, const String& rNm) :
1585 pDocShell( pDocSh ),
1586 aName( rNm ),
1587 aPropSet( lcl_GetDBRangePropertyMap() )
1588 {
1589 pDocShell->GetDocument()->AddUnoObject(*this);
1590 }
1591
~ScDatabaseRangeObj()1592 ScDatabaseRangeObj::~ScDatabaseRangeObj()
1593 {
1594 if (pDocShell)
1595 pDocShell->GetDocument()->RemoveUnoObject(*this);
1596 }
1597
Notify(SfxBroadcaster &,const SfxHint & rHint)1598 void ScDatabaseRangeObj::Notify( SfxBroadcaster&, const SfxHint& rHint )
1599 {
1600
1601 if ( rHint.ISA( SfxSimpleHint ) && ((const SfxSimpleHint&)rHint).GetId() == SFX_HINT_DYING )
1602 pDocShell = NULL; // ungueltig geworden
1603 else if ( rHint.ISA (ScDBRangeRefreshedHint) )
1604 {
1605 ScDBData* pDBData = GetDBData_Impl();
1606 const ScDBRangeRefreshedHint& rRef = (const ScDBRangeRefreshedHint&)rHint;
1607 ScImportParam aParam;
1608 pDBData->GetImportParam(aParam);
1609 if (aParam == rRef.GetImportParam())
1610 Refreshed_Impl();
1611 }
1612 }
1613
1614 // Hilfsfuntionen
1615
GetDBData_Impl() const1616 ScDBData* ScDatabaseRangeObj::GetDBData_Impl() const
1617 {
1618 ScDBData* pRet = NULL;
1619 if (pDocShell)
1620 {
1621 ScDBCollection* pNames = pDocShell->GetDocument()->GetDBCollection();
1622 if (pNames)
1623 {
1624 sal_uInt16 nPos = 0;
1625 if (pNames->SearchName( aName, nPos ))
1626 pRet = (*pNames)[nPos];
1627 }
1628 }
1629 return pRet;
1630 }
1631
1632 // XNamed
1633
getName()1634 rtl::OUString SAL_CALL ScDatabaseRangeObj::getName()
1635 {
1636 ScUnoGuard aGuard;
1637 return aName;
1638 }
1639
setName(const rtl::OUString & aNewName)1640 void SAL_CALL ScDatabaseRangeObj::setName( const rtl::OUString& aNewName )
1641 {
1642 ScUnoGuard aGuard;
1643 if (pDocShell)
1644 {
1645 ScDBDocFunc aFunc(*pDocShell);
1646 String aNewStr(aNewName);
1647 sal_Bool bOk = aFunc.RenameDBRange( aName, aNewStr, sal_True );
1648 if (bOk)
1649 aName = aNewStr;
1650 }
1651 }
1652
1653 // XDatabaseRange
1654
getDataArea()1655 table::CellRangeAddress SAL_CALL ScDatabaseRangeObj::getDataArea()
1656 {
1657 ScUnoGuard aGuard;
1658 table::CellRangeAddress aAddress;
1659 ScDBData* pData = GetDBData_Impl();
1660 if (pData)
1661 {
1662 ScRange aRange;
1663 pData->GetArea(aRange);
1664 aAddress.Sheet = aRange.aStart.Tab();
1665 aAddress.StartColumn = aRange.aStart.Col();
1666 aAddress.StartRow = aRange.aStart.Row();
1667 aAddress.EndColumn = aRange.aEnd.Col();
1668 aAddress.EndRow = aRange.aEnd.Row();
1669 }
1670 return aAddress;
1671 }
1672
setDataArea(const table::CellRangeAddress & aDataArea)1673 void SAL_CALL ScDatabaseRangeObj::setDataArea( const table::CellRangeAddress& aDataArea )
1674 {
1675 ScUnoGuard aGuard;
1676 ScDBData* pData = GetDBData_Impl();
1677 if ( pDocShell && pData )
1678 {
1679 ScDBData aNewData( *pData );
1680 //! MoveTo ???
1681 aNewData.SetArea( aDataArea.Sheet, (SCCOL)aDataArea.StartColumn, (SCROW)aDataArea.StartRow,
1682 (SCCOL)aDataArea.EndColumn, (SCROW)aDataArea.EndRow );
1683 ScDBDocFunc aFunc(*pDocShell);
1684 aFunc.ModifyDBData(aNewData, sal_True);
1685 }
1686 }
1687
getSortDescriptor()1688 uno::Sequence<beans::PropertyValue> SAL_CALL ScDatabaseRangeObj::getSortDescriptor()
1689 {
1690 ScUnoGuard aGuard;
1691 ScSortParam aParam;
1692 const ScDBData* pData = GetDBData_Impl();
1693 if (pData)
1694 {
1695 pData->GetSortParam(aParam);
1696
1697 // im SortDescriptor sind die Fields innerhalb des Bereichs gezaehlt
1698 ScRange aDBRange;
1699 pData->GetArea(aDBRange);
1700 SCCOLROW nFieldStart = aParam.bByRow ? static_cast<SCCOLROW>(aDBRange.aStart.Col()) : static_cast<SCCOLROW>(aDBRange.aStart.Row());
1701 for (sal_uInt16 i=0; i<MAXSORT; i++)
1702 if ( aParam.bDoSort[i] && aParam.nField[i] >= nFieldStart )
1703 aParam.nField[i] -= nFieldStart;
1704 }
1705
1706 uno::Sequence<beans::PropertyValue> aSeq( ScSortDescriptor::GetPropertyCount() );
1707 ScSortDescriptor::FillProperties( aSeq, aParam );
1708 return aSeq;
1709 }
1710
GetQueryParam(ScQueryParam & rQueryParam) const1711 void ScDatabaseRangeObj::GetQueryParam(ScQueryParam& rQueryParam) const
1712 {
1713 const ScDBData* pData = GetDBData_Impl();
1714 if (pData)
1715 {
1716 pData->GetQueryParam(rQueryParam);
1717
1718 // im FilterDescriptor sind die Fields innerhalb des Bereichs gezaehlt
1719 ScRange aDBRange;
1720 pData->GetArea(aDBRange);
1721 SCCOLROW nFieldStart = rQueryParam.bByRow ? static_cast<SCCOLROW>(aDBRange.aStart.Col()) : static_cast<SCCOLROW>(aDBRange.aStart.Row());
1722 SCSIZE nCount = rQueryParam.GetEntryCount();
1723 for (SCSIZE i=0; i<nCount; i++)
1724 {
1725 ScQueryEntry& rEntry = rQueryParam.GetEntry(i);
1726 if (rEntry.bDoQuery && rEntry.nField >= nFieldStart)
1727 rEntry.nField -= nFieldStart;
1728 }
1729 }
1730 }
1731
SetQueryParam(const ScQueryParam & rQueryParam)1732 void ScDatabaseRangeObj::SetQueryParam(const ScQueryParam& rQueryParam)
1733 {
1734 const ScDBData* pData = GetDBData_Impl();
1735 if (pData)
1736 {
1737 // im FilterDescriptor sind die Fields innerhalb des Bereichs gezaehlt
1738 ScQueryParam aParam(rQueryParam);
1739 ScRange aDBRange;
1740 pData->GetArea(aDBRange);
1741 SCCOLROW nFieldStart = aParam.bByRow ? static_cast<SCCOLROW>(aDBRange.aStart.Col()) : static_cast<SCCOLROW>(aDBRange.aStart.Row());
1742
1743 SCSIZE nCount = aParam.GetEntryCount();
1744 for (SCSIZE i=0; i<nCount; i++)
1745 {
1746 ScQueryEntry& rEntry = aParam.GetEntry(i);
1747 if (rEntry.bDoQuery)
1748 rEntry.nField += nFieldStart;
1749 }
1750
1751 ScDBData aNewData( *pData );
1752 aNewData.SetQueryParam(aParam);
1753 aNewData.SetHeader(aParam.bHasHeader); // not in ScDBData::SetQueryParam
1754 ScDBDocFunc aFunc(*pDocShell);
1755 aFunc.ModifyDBData(aNewData, sal_True);
1756 }
1757 }
1758
getFilterDescriptor()1759 uno::Reference<sheet::XSheetFilterDescriptor> SAL_CALL ScDatabaseRangeObj::getFilterDescriptor()
1760 {
1761 ScUnoGuard aGuard;
1762 return new ScRangeFilterDescriptor(pDocShell, this);
1763 }
1764
GetSubTotalParam(ScSubTotalParam & rSubTotalParam) const1765 void ScDatabaseRangeObj::GetSubTotalParam(ScSubTotalParam& rSubTotalParam) const
1766 {
1767 const ScDBData* pData = GetDBData_Impl();
1768 if (pData)
1769 {
1770 pData->GetSubTotalParam(rSubTotalParam);
1771
1772 // im FilterDescriptor sind die Fields innerhalb des Bereichs gezaehlt
1773 ScRange aDBRange;
1774 pData->GetArea(aDBRange);
1775 SCCOL nFieldStart = aDBRange.aStart.Col();
1776 for (sal_uInt16 i=0; i<MAXSUBTOTAL; i++)
1777 {
1778 if ( rSubTotalParam.bGroupActive[i] )
1779 {
1780 if ( rSubTotalParam.nField[i] >= nFieldStart )
1781 rSubTotalParam.nField[i] = sal::static_int_cast<SCCOL>( rSubTotalParam.nField[i] - nFieldStart );
1782 for (SCCOL j=0; j<rSubTotalParam.nSubTotals[i]; j++)
1783 if ( rSubTotalParam.pSubTotals[i][j] >= nFieldStart )
1784 rSubTotalParam.pSubTotals[i][j] =
1785 sal::static_int_cast<SCCOL>( rSubTotalParam.pSubTotals[i][j] - nFieldStart );
1786 }
1787 }
1788 }
1789 }
1790
SetSubTotalParam(const ScSubTotalParam & rSubTotalParam)1791 void ScDatabaseRangeObj::SetSubTotalParam(const ScSubTotalParam& rSubTotalParam)
1792 {
1793 const ScDBData* pData = GetDBData_Impl();
1794 if (pData)
1795 {
1796 // im FilterDescriptor sind die Fields innerhalb des Bereichs gezaehlt
1797 ScSubTotalParam aParam(rSubTotalParam);
1798 ScRange aDBRange;
1799 pData->GetArea(aDBRange);
1800 SCCOL nFieldStart = aDBRange.aStart.Col();
1801 for (sal_uInt16 i=0; i<MAXSUBTOTAL; i++)
1802 {
1803 if ( aParam.bGroupActive[i] )
1804 {
1805 aParam.nField[i] = sal::static_int_cast<SCCOL>( aParam.nField[i] + nFieldStart );
1806 for (SCCOL j=0; j<aParam.nSubTotals[i]; j++)
1807 aParam.pSubTotals[i][j] = sal::static_int_cast<SCCOL>( aParam.pSubTotals[i][j] + nFieldStart );
1808 }
1809 }
1810
1811 ScDBData aNewData( *pData );
1812 aNewData.SetSubTotalParam(aParam);
1813 ScDBDocFunc aFunc(*pDocShell);
1814 aFunc.ModifyDBData(aNewData, sal_True);
1815 }
1816 }
1817
getSubTotalDescriptor()1818 uno::Reference<sheet::XSubTotalDescriptor> SAL_CALL ScDatabaseRangeObj::getSubTotalDescriptor()
1819 {
1820 ScUnoGuard aGuard;
1821 return new ScRangeSubTotalDescriptor(this);
1822 }
1823
getImportDescriptor()1824 uno::Sequence<beans::PropertyValue> SAL_CALL ScDatabaseRangeObj::getImportDescriptor()
1825 {
1826 ScUnoGuard aGuard;
1827 ScImportParam aParam;
1828 const ScDBData* pData = GetDBData_Impl();
1829 if (pData)
1830 pData->GetImportParam(aParam);
1831
1832 uno::Sequence<beans::PropertyValue> aSeq( ScImportDescriptor::GetPropertyCount() );
1833 ScImportDescriptor::FillProperties( aSeq, aParam );
1834 return aSeq;
1835 }
1836
1837 // XRefreshable
1838
refresh()1839 void SAL_CALL ScDatabaseRangeObj::refresh()
1840 {
1841 ScUnoGuard aGuard;
1842 ScDBData* pData = GetDBData_Impl();
1843 if ( pDocShell && pData )
1844 {
1845 ScDBDocFunc aFunc(*pDocShell);
1846
1847 // Import zu wiederholen?
1848 sal_Bool bContinue = sal_True;
1849 ScImportParam aImportParam;
1850 pData->GetImportParam( aImportParam );
1851 if (aImportParam.bImport && !pData->HasImportSelection())
1852 {
1853 SCTAB nTab;
1854 SCCOL nDummyCol;
1855 SCROW nDummyRow;
1856 pData->GetArea( nTab, nDummyCol,nDummyRow,nDummyCol,nDummyRow );
1857 bContinue = aFunc.DoImport( nTab, aImportParam, NULL, sal_True ); //! Api-Flag as parameter
1858 }
1859
1860 // interne Operationen (sort, query, subtotal) nur, wenn kein Fehler
1861 if (bContinue)
1862 aFunc.RepeatDB( pData->GetName(), sal_True, sal_True );
1863 }
1864 }
1865
addRefreshListener(const uno::Reference<util::XRefreshListener> & xListener)1866 void SAL_CALL ScDatabaseRangeObj::addRefreshListener(
1867 const uno::Reference<util::XRefreshListener >& xListener )
1868 {
1869 ScUnoGuard aGuard;
1870 uno::Reference<util::XRefreshListener>* pObj =
1871 new uno::Reference<util::XRefreshListener>( xListener );
1872 aRefreshListeners.Insert( pObj, aRefreshListeners.Count() );
1873
1874 // hold one additional ref to keep this object alive as long as there are listeners
1875 if ( aRefreshListeners.Count() == 1 )
1876 acquire();
1877 }
1878
removeRefreshListener(const uno::Reference<util::XRefreshListener> & xListener)1879 void SAL_CALL ScDatabaseRangeObj::removeRefreshListener(
1880 const uno::Reference<util::XRefreshListener >& xListener )
1881 {
1882 ScUnoGuard aGuard;
1883 sal_uInt16 nCount = aRefreshListeners.Count();
1884 for ( sal_uInt16 n=nCount; n--; )
1885 {
1886 uno::Reference<util::XRefreshListener>* pObj = aRefreshListeners[n];
1887 if ( *pObj == xListener )
1888 {
1889 aRefreshListeners.DeleteAndDestroy( n );
1890 if ( aRefreshListeners.Count() == 0 )
1891 release(); // release ref for listeners
1892 break;
1893 }
1894 }
1895 }
1896
Refreshed_Impl()1897 void ScDatabaseRangeObj::Refreshed_Impl()
1898 {
1899 lang::EventObject aEvent;
1900 aEvent.Source = (cppu::OWeakObject*)this;
1901 for ( sal_uInt16 n=0; n<aRefreshListeners.Count(); n++ )
1902 (*aRefreshListeners[n])->refreshed( aEvent );
1903 }
1904
1905 // XCellRangeSource
1906
getReferredCells()1907 uno::Reference<table::XCellRange> SAL_CALL ScDatabaseRangeObj::getReferredCells()
1908 {
1909 ScUnoGuard aGuard;
1910 ScRange aRange;
1911 ScDBData* pData = GetDBData_Impl();
1912 if ( pData )
1913 {
1914 //! static Funktion um ScCellObj/ScCellRangeObj zu erzeugen am ScCellRangeObj ???
1915
1916 pData->GetArea(aRange);
1917 if ( aRange.aStart == aRange.aEnd )
1918 return new ScCellObj( pDocShell, aRange.aStart );
1919 else
1920 return new ScCellRangeObj( pDocShell, aRange );
1921 }
1922 return NULL;
1923 }
1924
1925 // XPropertySet
1926
getPropertySetInfo()1927 uno::Reference<beans::XPropertySetInfo> SAL_CALL ScDatabaseRangeObj::getPropertySetInfo()
1928 {
1929 ScUnoGuard aGuard;
1930 static uno::Reference<beans::XPropertySetInfo> aRef(
1931 new SfxItemPropertySetInfo( aPropSet.getPropertyMap() ));
1932 return aRef;
1933 }
1934
setPropertyValue(const rtl::OUString & aPropertyName,const uno::Any & aValue)1935 void SAL_CALL ScDatabaseRangeObj::setPropertyValue(
1936 const rtl::OUString& aPropertyName, const uno::Any& aValue )
1937 {
1938 ScUnoGuard aGuard;
1939 ScDBData* pData = GetDBData_Impl();
1940 if ( pDocShell && pData )
1941 {
1942 ScDBData aNewData( *pData );
1943 sal_Bool bDo = sal_True;
1944
1945 String aString(aPropertyName);
1946 if ( aString.EqualsAscii( SC_UNONAME_KEEPFORM ) )
1947 aNewData.SetKeepFmt( ScUnoHelpFunctions::GetBoolFromAny( aValue ) );
1948 else if ( aString.EqualsAscii( SC_UNONAME_MOVCELLS ) )
1949 aNewData.SetDoSize( ScUnoHelpFunctions::GetBoolFromAny( aValue ) );
1950 else if ( aString.EqualsAscii( SC_UNONAME_STRIPDAT ) )
1951 aNewData.SetStripData( ScUnoHelpFunctions::GetBoolFromAny( aValue ) );
1952 else if (aString.EqualsAscii( SC_UNONAME_AUTOFLT ))
1953 {
1954 sal_Bool bAutoFilter(ScUnoHelpFunctions::GetBoolFromAny( aValue ));
1955 aNewData.SetAutoFilter(bAutoFilter);
1956 ScRange aRange;
1957 aNewData.GetArea(aRange);
1958 ScDocument* pDoc = pDocShell->GetDocument();
1959 if (bAutoFilter && pDoc)
1960 pDoc->ApplyFlagsTab( aRange.aStart.Col(), aRange.aStart.Row(),
1961 aRange.aEnd.Col(), aRange.aStart.Row(),
1962 aRange.aStart.Tab(), SC_MF_AUTO );
1963 else if (!bAutoFilter && pDoc)
1964 pDoc->RemoveFlagsTab(aRange.aStart.Col(), aRange.aStart.Row(),
1965 aRange.aEnd.Col(), aRange.aStart.Row(),
1966 aRange.aStart.Tab(), SC_MF_AUTO );
1967 ScRange aPaintRange(aRange.aStart, aRange.aEnd);
1968 aPaintRange.aEnd.SetRow(aPaintRange.aStart.Row());
1969 pDocShell->PostPaint(aPaintRange, PAINT_GRID);
1970 }
1971 else if (aString.EqualsAscii( SC_UNONAME_USEFLTCRT ))
1972 {
1973 if (ScUnoHelpFunctions::GetBoolFromAny( aValue ))
1974 {
1975 ScRange aRange;
1976 aNewData.GetAdvancedQuerySource(aRange);
1977 aNewData.SetAdvancedQuerySource(&aRange);
1978 }
1979 else
1980 aNewData.SetAdvancedQuerySource(NULL);
1981 }
1982 else if (aString.EqualsAscii( SC_UNONAME_FLTCRT ))
1983 {
1984 table::CellRangeAddress aRange;
1985 if (aValue >>= aRange)
1986 {
1987 ScRange aCoreRange;
1988 ScUnoConversion::FillScRange(aCoreRange, aRange);
1989
1990 aNewData.SetAdvancedQuerySource(&aCoreRange);
1991 }
1992 }
1993 else if (aString.EqualsAscii( SC_UNONAME_FROMSELECT ))
1994 {
1995 aNewData.SetImportSelection(::cppu::any2bool(aValue));
1996 }
1997 else if (aString.EqualsAscii( SC_UNONAME_REFPERIOD ))
1998 {
1999 sal_Int32 nRefresh = 0;
2000 if (aValue >>= nRefresh)
2001 {
2002 ScDocument* pDoc = pDocShell->GetDocument();
2003 aNewData.SetRefreshDelay(nRefresh);
2004 if (pDoc && pDoc->GetDBCollection())
2005 {
2006 aNewData.SetRefreshHandler( pDoc->GetDBCollection()->GetRefreshHandler() );
2007 aNewData.SetRefreshControl( pDoc->GetRefreshTimerControlAddress() );
2008 }
2009 }
2010 }
2011 else if (aString.EqualsAscii( SC_UNONAME_CONRES ))
2012 {
2013 }
2014 else
2015 bDo = sal_False;
2016
2017 if (bDo)
2018 {
2019 ScDBDocFunc aFunc(*pDocShell);
2020 aFunc.ModifyDBData(aNewData, sal_True);
2021 }
2022 }
2023 }
2024
getPropertyValue(const rtl::OUString & aPropertyName)2025 uno::Any SAL_CALL ScDatabaseRangeObj::getPropertyValue( const rtl::OUString& aPropertyName )
2026 {
2027 ScUnoGuard aGuard;
2028 uno::Any aRet;
2029 ScDBData* pData = GetDBData_Impl();
2030 if ( pData )
2031 {
2032 String aString(aPropertyName);
2033 if ( aString.EqualsAscii( SC_UNONAME_KEEPFORM ) )
2034 ScUnoHelpFunctions::SetBoolInAny( aRet, pData->IsKeepFmt() );
2035 else if ( aString.EqualsAscii( SC_UNONAME_MOVCELLS ) )
2036 ScUnoHelpFunctions::SetBoolInAny( aRet, pData->IsDoSize() );
2037 else if ( aString.EqualsAscii( SC_UNONAME_STRIPDAT ) )
2038 ScUnoHelpFunctions::SetBoolInAny( aRet, pData->IsStripData() );
2039 else if ( aString.EqualsAscii( SC_UNONAME_ISUSER ) )
2040 {
2041 // all database ranges except "unnamed" are user defined
2042 ScUnoHelpFunctions::SetBoolInAny( aRet,
2043 ( pData->GetName() != ScGlobal::GetRscString(STR_DB_NONAME) ) );
2044 }
2045 else if ( aString.EqualsAscii( SC_UNO_LINKDISPBIT ) )
2046 {
2047 // no target bitmaps for individual entries (would be all equal)
2048 // ScLinkTargetTypeObj::SetLinkTargetBitmap( aRet, SC_LINKTARGETTYPE_DBAREA );
2049 }
2050 else if ( aString.EqualsAscii( SC_UNO_LINKDISPNAME ) )
2051 aRet <<= rtl::OUString( aName );
2052 else if (aString.EqualsAscii( SC_UNONAME_AUTOFLT ))
2053 {
2054 sal_Bool bAutoFilter(GetDBData_Impl()->HasAutoFilter());
2055
2056 ScUnoHelpFunctions::SetBoolInAny( aRet, bAutoFilter );
2057 }
2058 else if (aString.EqualsAscii( SC_UNONAME_USEFLTCRT ))
2059 {
2060 ScRange aRange;
2061 sal_Bool bIsAdvancedSource(GetDBData_Impl()->GetAdvancedQuerySource(aRange));
2062
2063 ScUnoHelpFunctions::SetBoolInAny( aRet, bIsAdvancedSource );
2064 }
2065 else if (aString.EqualsAscii( SC_UNONAME_FLTCRT ))
2066 {
2067 table::CellRangeAddress aRange;
2068 ScRange aCoreRange;
2069 if (GetDBData_Impl()->GetAdvancedQuerySource(aCoreRange))
2070 ScUnoConversion::FillApiRange(aRange, aCoreRange);
2071
2072 aRet <<= aRange;
2073 }
2074 else if (aString.EqualsAscii( SC_UNONAME_FROMSELECT ))
2075 {
2076 ScUnoHelpFunctions::SetBoolInAny( aRet, GetDBData_Impl()->HasImportSelection() );
2077 }
2078 else if (aString.EqualsAscii( SC_UNONAME_REFPERIOD ))
2079 {
2080 sal_Int32 nRefresh(GetDBData_Impl()->GetRefreshDelay());
2081 aRet <<= nRefresh;
2082 }
2083 else if (aString.EqualsAscii( SC_UNONAME_CONRES ))
2084 {
2085 }
2086 else if (aString.EqualsAscii( SC_UNONAME_TOKENINDEX ))
2087 {
2088 // get index for use in formula tokens (read-only)
2089 aRet <<= static_cast<sal_Int32>(GetDBData_Impl()->GetIndex());
2090 }
2091 }
2092 return aRet;
2093 }
2094
SC_IMPL_DUMMY_PROPERTY_LISTENER(ScDatabaseRangeObj)2095 SC_IMPL_DUMMY_PROPERTY_LISTENER( ScDatabaseRangeObj )
2096
2097 // XServiceInfo
2098
2099 rtl::OUString SAL_CALL ScDatabaseRangeObj::getImplementationName()
2100 {
2101 return rtl::OUString::createFromAscii( "ScDatabaseRangeObj" );
2102 }
2103
supportsService(const rtl::OUString & rServiceName)2104 sal_Bool SAL_CALL ScDatabaseRangeObj::supportsService( const rtl::OUString& rServiceName )
2105 {
2106 String aServiceStr( rServiceName );
2107 return aServiceStr.EqualsAscii( SCDATABASERANGEOBJ_SERVICE ) ||
2108 aServiceStr.EqualsAscii( SCLINKTARGET_SERVICE );
2109 }
2110
getSupportedServiceNames()2111 uno::Sequence<rtl::OUString> SAL_CALL ScDatabaseRangeObj::getSupportedServiceNames()
2112 {
2113 uno::Sequence<rtl::OUString> aRet(2);
2114 rtl::OUString* pArray = aRet.getArray();
2115 pArray[0] = rtl::OUString::createFromAscii( SCDATABASERANGEOBJ_SERVICE );
2116 pArray[1] = rtl::OUString::createFromAscii( SCLINKTARGET_SERVICE );
2117 return aRet;
2118 }
2119
2120 //------------------------------------------------------------------------
2121
ScDatabaseRangesObj(ScDocShell * pDocSh)2122 ScDatabaseRangesObj::ScDatabaseRangesObj(ScDocShell* pDocSh) :
2123 pDocShell( pDocSh )
2124 {
2125 pDocShell->GetDocument()->AddUnoObject(*this);
2126 }
2127
~ScDatabaseRangesObj()2128 ScDatabaseRangesObj::~ScDatabaseRangesObj()
2129 {
2130 if (pDocShell)
2131 pDocShell->GetDocument()->RemoveUnoObject(*this);
2132 }
2133
Notify(SfxBroadcaster &,const SfxHint & rHint)2134 void ScDatabaseRangesObj::Notify( SfxBroadcaster&, const SfxHint& rHint )
2135 {
2136 // Referenz-Update interessiert hier nicht
2137
2138 if ( rHint.ISA( SfxSimpleHint ) &&
2139 ((const SfxSimpleHint&)rHint).GetId() == SFX_HINT_DYING )
2140 {
2141 pDocShell = NULL; // ungueltig geworden
2142 }
2143 }
2144
2145 // XDatabaseRanges
2146
GetObjectByIndex_Impl(sal_uInt16 nIndex)2147 ScDatabaseRangeObj* ScDatabaseRangesObj::GetObjectByIndex_Impl(sal_uInt16 nIndex)
2148 {
2149 if (pDocShell)
2150 {
2151 ScDBCollection* pNames = pDocShell->GetDocument()->GetDBCollection();
2152 if (pNames && nIndex < pNames->GetCount())
2153 return new ScDatabaseRangeObj( pDocShell, (*pNames)[nIndex]->GetName() );
2154 }
2155 return NULL;
2156 }
2157
GetObjectByName_Impl(const rtl::OUString & aName)2158 ScDatabaseRangeObj* ScDatabaseRangesObj::GetObjectByName_Impl(const rtl::OUString& aName)
2159 {
2160 if ( pDocShell && hasByName(aName) )
2161 {
2162 String aString(aName);
2163 return new ScDatabaseRangeObj( pDocShell, aString );
2164 }
2165 return NULL;
2166 }
2167
2168
addNewByName(const rtl::OUString & aName,const table::CellRangeAddress & aRange)2169 void SAL_CALL ScDatabaseRangesObj::addNewByName( const rtl::OUString& aName,
2170 const table::CellRangeAddress& aRange )
2171 {
2172 ScUnoGuard aGuard;
2173 sal_Bool bDone = sal_False;
2174 if (pDocShell)
2175 {
2176 ScDBDocFunc aFunc(*pDocShell);
2177
2178 String aString(aName);
2179 ScRange aNameRange( (SCCOL)aRange.StartColumn, (SCROW)aRange.StartRow, aRange.Sheet,
2180 (SCCOL)aRange.EndColumn, (SCROW)aRange.EndRow, aRange.Sheet );
2181 bDone = aFunc.AddDBRange( aString, aNameRange, sal_True );
2182 }
2183 if (!bDone)
2184 throw uno::RuntimeException(); // no other exceptions specified
2185 }
2186
removeByName(const rtl::OUString & aName)2187 void SAL_CALL ScDatabaseRangesObj::removeByName( const rtl::OUString& aName )
2188 {
2189 ScUnoGuard aGuard;
2190 sal_Bool bDone = sal_False;
2191 if (pDocShell)
2192 {
2193 ScDBDocFunc aFunc(*pDocShell);
2194 String aString(aName);
2195 bDone = aFunc.DeleteDBRange( aString, sal_True );
2196 }
2197 if (!bDone)
2198 throw uno::RuntimeException(); // no other exceptions specified
2199 }
2200
2201 // XEnumerationAccess
2202
createEnumeration()2203 uno::Reference<container::XEnumeration> SAL_CALL ScDatabaseRangesObj::createEnumeration()
2204 {
2205 ScUnoGuard aGuard;
2206 return new ScIndexEnumeration(this, rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.sheet.DatabaseRangesEnumeration")));
2207 }
2208
2209 // XIndexAccess
2210
getCount()2211 sal_Int32 SAL_CALL ScDatabaseRangesObj::getCount()
2212 {
2213 ScUnoGuard aGuard;
2214
2215 //! "unbenannt" weglassen ?
2216
2217 if (pDocShell)
2218 {
2219 ScDBCollection* pNames = pDocShell->GetDocument()->GetDBCollection();
2220 if (pNames)
2221 return pNames->GetCount();
2222 }
2223 return 0;
2224 }
2225
getByIndex(sal_Int32 nIndex)2226 uno::Any SAL_CALL ScDatabaseRangesObj::getByIndex( sal_Int32 nIndex )
2227 {
2228 ScUnoGuard aGuard;
2229 uno::Reference<sheet::XDatabaseRange> xRange(GetObjectByIndex_Impl((sal_uInt16)nIndex));
2230 if (xRange.is())
2231 return uno::makeAny(xRange);
2232 else
2233 throw lang::IndexOutOfBoundsException();
2234 // return uno::Any();
2235 }
2236
getElementType()2237 uno::Type SAL_CALL ScDatabaseRangesObj::getElementType()
2238 {
2239 ScUnoGuard aGuard;
2240 return getCppuType((uno::Reference<sheet::XDatabaseRange>*)0);
2241 }
2242
hasElements()2243 sal_Bool SAL_CALL ScDatabaseRangesObj::hasElements()
2244 {
2245 ScUnoGuard aGuard;
2246 return ( getCount() != 0 );
2247 }
2248
2249 // XNameAccess
2250
getByName(const rtl::OUString & aName)2251 uno::Any SAL_CALL ScDatabaseRangesObj::getByName( const rtl::OUString& aName )
2252 {
2253 ScUnoGuard aGuard;
2254 uno::Reference<sheet::XDatabaseRange> xRange(GetObjectByName_Impl(aName));
2255 if (xRange.is())
2256 return uno::makeAny(xRange);
2257 else
2258 throw container::NoSuchElementException();
2259 // return uno::Any();
2260 }
2261
getElementNames()2262 uno::Sequence<rtl::OUString> SAL_CALL ScDatabaseRangesObj::getElementNames()
2263 {
2264 ScUnoGuard aGuard;
2265
2266 //! "unbenannt" weglassen ?
2267
2268 if (pDocShell)
2269 {
2270 ScDBCollection* pNames = pDocShell->GetDocument()->GetDBCollection();
2271 if (pNames)
2272 {
2273 sal_uInt16 nCount = pNames->GetCount();
2274 String aName;
2275 uno::Sequence<rtl::OUString> aSeq(nCount);
2276 rtl::OUString* pAry = aSeq.getArray();
2277 for (sal_uInt16 i=0; i<nCount; i++)
2278 pAry[i] = (*pNames)[i]->GetName();
2279
2280 return aSeq;
2281 }
2282 }
2283 return uno::Sequence<rtl::OUString>(0);
2284 }
2285
hasByName(const rtl::OUString & aName)2286 sal_Bool SAL_CALL ScDatabaseRangesObj::hasByName( const rtl::OUString& aName )
2287 {
2288 ScUnoGuard aGuard;
2289
2290 //! "unbenannt" weglassen ?
2291
2292 if (pDocShell)
2293 {
2294 ScDBCollection* pNames = pDocShell->GetDocument()->GetDBCollection();
2295 if (pNames)
2296 {
2297 String aString(aName);
2298 sal_uInt16 nPos = 0;
2299 if (pNames->SearchName( aString, nPos ))
2300 return sal_True;
2301 }
2302 }
2303 return sal_False;
2304 }
2305
2306 //------------------------------------------------------------------------
2307