1 
2 using System;
3 
4 // __________  implementation  ____________________________________
5 
6 /** Create and modify a spreadsheet document.
7  */
8 public class SpreadsheetSample : SpreadsheetDocHelper
9 {
10 
11     public static void Main( String [] args )
12     {
13         try
14         {
15             using ( SpreadsheetSample aSample = new SpreadsheetSample( args ) )
16             {
17                 aSample.doSampleFunctions();
18             }
19             Console.WriteLine( "\nSamples done." );
20         }
21         catch (Exception ex)
22         {
23             Console.WriteLine( "Sample caught exception! " + ex );
24         }
25     }
26 
27     public SpreadsheetSample( String[] args )
28         : base( args )
29     {
30     }
31 
32     /** This sample function performs all changes on the document. */
33     public void doSampleFunctions()
34     {
35         doCellSamples();
36         doCellRangeSamples();
37         doCellRangesSamples();
38         doCellCursorSamples();
39         doFormattingSamples();
40         doDocumentSamples();
41         doDatabaseSamples();
42         doDataPilotSamples();
43         doNamedRangesSamples();
44         doFunctionAccessSamples();
45         doApplicationSettingsSamples();
46     }
47 
48 // ________________________________________________________________
49 
50     /** All samples regarding the service com.sun.star.sheet.SheetCell. */
51     private void doCellSamples()
52     {
53         Console.WriteLine( "\n*** Samples for service sheet.SheetCell ***\n" );
54         unoidl.com.sun.star.sheet.XSpreadsheet xSheet = getSpreadsheet( 0 );
55         unoidl.com.sun.star.table.XCell xCell = null;
56         unoidl.com.sun.star.beans.XPropertySet xPropSet = null;
57         String aText;
58         prepareRange( xSheet, "A1:C7", "Cells and Cell Ranges" );
59 
60         // --- Get cell B3 by position - (column, row) ---
61         xCell = xSheet.getCellByPosition( 1, 2 );
62 
63         // --- Insert two text paragraphs into the cell. ---
64         unoidl.com.sun.star.text.XText xText =
65             (unoidl.com.sun.star.text.XText) xCell;
66         unoidl.com.sun.star.text.XTextCursor xTextCursor =
67             xText.createTextCursor();
68 
69         xText.insertString( xTextCursor, "Text in first line.", false );
70         xText.insertControlCharacter( xTextCursor,
71             unoidl.com.sun.star.text.ControlCharacter.PARAGRAPH_BREAK, false );
72         xText.insertString( xTextCursor, "And a ", false );
73 
74         // create a hyperlink
75         unoidl.com.sun.star.lang.XMultiServiceFactory xServiceMan =
76             (unoidl.com.sun.star.lang.XMultiServiceFactory) getDocument();
77         Object aHyperlinkObj =
78             xServiceMan.createInstance( "com.sun.star.text.TextField.URL" );
79         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) aHyperlinkObj;
80         xPropSet.setPropertyValue(
81             "URL", new uno.Any( "http://www.example.org" ) );
82         xPropSet.setPropertyValue(
83             "Representation", new uno.Any( "hyperlink" ) );
84         // ... and insert
85         unoidl.com.sun.star.text.XTextContent xContent =
86             (unoidl.com.sun.star.text.XTextContent) aHyperlinkObj;
87         xText.insertTextContent( xTextCursor, xContent, false );
88 
89         // --- Query the separate paragraphs. ---
90         unoidl.com.sun.star.container.XEnumerationAccess xParaEA =
91             (unoidl.com.sun.star.container.XEnumerationAccess) xCell;
92         unoidl.com.sun.star.container.XEnumeration xParaEnum =
93             xParaEA.createEnumeration();
94         // Go through the paragraphs
95         while( xParaEnum.hasMoreElements() )
96         {
97             uno.Any aPortionObj = xParaEnum.nextElement();
98             unoidl.com.sun.star.container.XEnumerationAccess xPortionEA =
99                 (unoidl.com.sun.star.container.XEnumerationAccess)
100                 aPortionObj.Value;
101             unoidl.com.sun.star.container.XEnumeration xPortionEnum =
102                 xPortionEA.createEnumeration();
103             aText = "";
104             // Go through all text portions of a paragraph and construct string.
105             while( xPortionEnum.hasMoreElements() )
106             {
107                 unoidl.com.sun.star.text.XTextRange xRange =
108                     (unoidl.com.sun.star.text.XTextRange)
109                     xPortionEnum.nextElement().Value;
110                 aText += xRange.getString();
111             }
112             Console.WriteLine( "Paragraph text: " + aText );
113         }
114 
115 
116         // --- Change cell properties. ---
117         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) xCell;
118         // from styles.CharacterProperties
119         xPropSet.setPropertyValue(
120             "CharColor", new uno.Any( (Int32) 0x003399 ) );
121         xPropSet.setPropertyValue(
122             "CharHeight", new uno.Any( (Single) 20.0 ) );
123         // from styles.ParagraphProperties
124         xPropSet.setPropertyValue(
125             "ParaLeftMargin", new uno.Any( (Int32) 500 ) );
126         // from table.CellProperties
127         xPropSet.setPropertyValue(
128             "IsCellBackgroundTransparent", new uno.Any( false ) );
129         xPropSet.setPropertyValue(
130             "CellBackColor", new uno.Any( (Int32) 0x99CCFF ) );
131 
132 
133         // --- Get cell address. ---
134         unoidl.com.sun.star.sheet.XCellAddressable xCellAddr =
135             (unoidl.com.sun.star.sheet.XCellAddressable) xCell;
136         unoidl.com.sun.star.table.CellAddress aAddress =
137             xCellAddr.getCellAddress();
138         aText = "Address of this cell:  Column=" + aAddress.Column;
139         aText += ";  Row=" + aAddress.Row;
140         aText += ";  Sheet=" + aAddress.Sheet;
141         Console.WriteLine( aText );
142 
143 
144         // --- Insert an annotation ---
145         unoidl.com.sun.star.sheet.XSheetAnnotationsSupplier xAnnotationsSupp =
146         (unoidl.com.sun.star.sheet.XSheetAnnotationsSupplier) xSheet;
147         unoidl.com.sun.star.sheet.XSheetAnnotations xAnnotations =
148             xAnnotationsSupp.getAnnotations();
149         xAnnotations.insertNew( aAddress, "This is an annotation" );
150 
151         unoidl.com.sun.star.sheet.XSheetAnnotationAnchor xAnnotAnchor =
152             (unoidl.com.sun.star.sheet.XSheetAnnotationAnchor) xCell;
153         unoidl.com.sun.star.sheet.XSheetAnnotation xAnnotation =
154             xAnnotAnchor.getAnnotation();
155         xAnnotation.setIsVisible( true );
156     }
157 
158 // ________________________________________________________________
159 
160     /** All samples regarding the service com.sun.star.sheet.SheetCellRange. */
161     private void doCellRangeSamples()
162     {
163         Console.WriteLine(
164             "\n*** Samples for service sheet.SheetCellRange ***\n" );
165         unoidl.com.sun.star.sheet.XSpreadsheet xSheet = getSpreadsheet( 0 );
166         unoidl.com.sun.star.table.XCellRange xCellRange = null;
167         unoidl.com.sun.star.beans.XPropertySet xPropSet = null;
168         unoidl.com.sun.star.table.CellRangeAddress aRangeAddress = null;
169 
170         // Preparation
171         setFormula( xSheet, "B5", "First cell" );
172         setFormula( xSheet, "B6", "Second cell" );
173         // Get cell range B5:B6 by position - (column, row, column, row)
174         xCellRange = xSheet.getCellRangeByPosition( 1, 4, 1, 5 );
175 
176 
177         // --- Change cell range properties. ---
178         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) xCellRange;
179         // from com.sun.star.styles.CharacterProperties
180         xPropSet.setPropertyValue(
181             "CharColor", new uno.Any( (Int32) 0x003399 ) );
182         xPropSet.setPropertyValue(
183             "CharHeight", new uno.Any( (Single) 20.0 ) );
184         // from com.sun.star.styles.ParagraphProperties
185         xPropSet.setPropertyValue(
186             "ParaLeftMargin", new uno.Any( (Int32) 500 ) );
187         // from com.sun.star.table.CellProperties
188         xPropSet.setPropertyValue(
189             "IsCellBackgroundTransparent", new uno.Any( false ) );
190         xPropSet.setPropertyValue(
191             "CellBackColor", new uno.Any( (Int32) 0x99CCFF ) );
192 
193 
194         // --- Replace text in all cells. ---
195         unoidl.com.sun.star.util.XReplaceable xReplace =
196             (unoidl.com.sun.star.util.XReplaceable) xCellRange;
197         unoidl.com.sun.star.util.XReplaceDescriptor xReplaceDesc =
198             xReplace.createReplaceDescriptor();
199         xReplaceDesc.setSearchString( "cell" );
200         xReplaceDesc.setReplaceString( "text" );
201         // property SearchWords searches for whole cells!
202         xReplaceDesc.setPropertyValue( "SearchWords", new uno.Any( false ) );
203         int nCount = xReplace.replaceAll( xReplaceDesc );
204         Console.WriteLine( "Search text replaced " + nCount + " times." );
205 
206 
207         // --- Merge cells. ---
208         xCellRange = xSheet.getCellRangeByName( "F3:G6" );
209         prepareRange( xSheet, "E1:H7", "XMergeable" );
210         unoidl.com.sun.star.util.XMergeable xMerge =
211             (unoidl.com.sun.star.util.XMergeable) xCellRange;
212         xMerge.merge( true );
213 
214 
215         // --- Change indentation. ---
216 /* does not work (bug in XIndent implementation)
217         prepareRange( xSheet, "I20:I23", "XIndent" );
218         setValue( xSheet, "I21", 1 );
219         setValue( xSheet, "I22", 1 );
220         setValue( xSheet, "I23", 1 );
221 
222         xCellRange = xSheet.getCellRangeByName( "I21:I22" );
223         unoidl.com.sun.star.util.XIndent xIndent =
224         (unoidl.com.sun.star.util.XIndent) xCellRange;
225         xIndent.incrementIndent();
226 
227         xCellRange = xSheet.getCellRangeByName( "I22:I23" );
228         xIndent = (unoidl.com.sun.star.util.XIndent) xCellRange;
229         xIndent.incrementIndent();
230 */
231 
232 
233         // --- Column properties. ---
234         xCellRange = xSheet.getCellRangeByName( "B1" );
235         unoidl.com.sun.star.table.XColumnRowRange xColRowRange =
236             (unoidl.com.sun.star.table.XColumnRowRange) xCellRange;
237         unoidl.com.sun.star.table.XTableColumns xColumns =
238             xColRowRange.getColumns();
239 
240         uno.Any aColumnObj = xColumns.getByIndex( 0 );
241         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) aColumnObj.Value;
242         xPropSet.setPropertyValue( "Width", new uno.Any( (Int32) 6000 ) );
243 
244         unoidl.com.sun.star.container.XNamed xNamed =
245             (unoidl.com.sun.star.container.XNamed) aColumnObj.Value;
246         Console.WriteLine(
247             "The name of the wide column is " + xNamed.getName() + "." );
248 
249 
250         // --- Cell range data ---
251         prepareRange( xSheet, "A9:C30", "XCellRangeData" );
252 
253         xCellRange = xSheet.getCellRangeByName( "A10:C30" );
254         unoidl.com.sun.star.sheet.XCellRangeData xData =
255             (unoidl.com.sun.star.sheet.XCellRangeData) xCellRange;
256         uno.Any [][] aValues =
257         {
258             new uno.Any [] { new uno.Any( "Name" ),
259                              new uno.Any( "Fruit" ),
260                              new uno.Any( "Quantity" ) },
261             new uno.Any [] { new uno.Any( "Alice" ),
262                              new uno.Any( "Apples" ),
263                              new uno.Any( (Double) 3.0 ) },
264             new uno.Any [] { new uno.Any( "Alice" ),
265                              new uno.Any( "Oranges" ),
266                              new uno.Any( (Double) 7.0 ) },
267             new uno.Any [] { new uno.Any( "Bob" ),
268                              new uno.Any( "Apples" ),
269                              new uno.Any( (Double) 3.0 ) },
270             new uno.Any [] { new uno.Any( "Alice" ),
271                              new uno.Any( "Apples" ),
272                              new uno.Any( (Double) 9.0 ) },
273             new uno.Any [] { new uno.Any( "Bob" ),
274                              new uno.Any( "Apples" ),
275                              new uno.Any( (Double) 5.0 ) },
276             new uno.Any [] { new uno.Any( "Bob" ),
277                              new uno.Any( "Oranges" ),
278                              new uno.Any( (Double) 6.0 ) },
279             new uno.Any [] { new uno.Any( "Alice" ),
280                              new uno.Any( "Oranges" ),
281                              new uno.Any( (Double) 3.0 ) },
282             new uno.Any [] { new uno.Any( "Alice" ),
283                              new uno.Any( "Apples" ),
284                              new uno.Any( (Double) 8.0 ) },
285             new uno.Any [] { new uno.Any( "Alice" ),
286                              new uno.Any( "Oranges" ),
287                              new uno.Any( (Double) 1.0 ) },
288             new uno.Any [] { new uno.Any( "Bob" ),
289                              new uno.Any( "Oranges" ),
290                              new uno.Any( (Double) 2.0 ) },
291             new uno.Any [] { new uno.Any( "Bob" ),
292                              new uno.Any( "Oranges" ),
293                              new uno.Any( (Double) 7.0 ) },
294             new uno.Any [] { new uno.Any( "Bob" ),
295                              new uno.Any( "Apples" ),
296                              new uno.Any( (Double) 1.0 ) },
297             new uno.Any [] { new uno.Any( "Alice" ),
298                              new uno.Any( "Apples" ),
299                              new uno.Any( (Double) 8.0 ) },
300             new uno.Any [] { new uno.Any( "Alice" ),
301                              new uno.Any( "Oranges" ),
302                              new uno.Any( (Double) 8.0 ) },
303             new uno.Any [] { new uno.Any( "Alice" ),
304                              new uno.Any( "Apples" ),
305                              new uno.Any( (Double) 7.0 ) },
306             new uno.Any [] { new uno.Any( "Bob" ),
307                              new uno.Any( "Apples" ),
308                              new uno.Any( (Double) 1.0 ) },
309             new uno.Any [] { new uno.Any( "Bob" ),
310                              new uno.Any( "Oranges" ),
311                              new uno.Any( (Double) 9.0 ) },
312             new uno.Any [] { new uno.Any( "Bob" ),
313                              new uno.Any( "Oranges" ),
314                              new uno.Any( (Double) 3.0 ) },
315             new uno.Any [] { new uno.Any( "Alice" ),
316                              new uno.Any( "Oranges" ),
317                              new uno.Any( (Double) 4.0 ) },
318             new uno.Any [] { new uno.Any( "Alice" ),
319                              new uno.Any( "Apples" ),
320                              new uno.Any( (Double) 9.0 ) }
321         };
322         xData.setDataArray( aValues );
323 
324 
325         // --- Get cell range address. ---
326         unoidl.com.sun.star.sheet.XCellRangeAddressable xRangeAddr =
327             (unoidl.com.sun.star.sheet.XCellRangeAddressable) xCellRange;
328         aRangeAddress = xRangeAddr.getRangeAddress();
329         Console.WriteLine(
330             "Address of this range:  Sheet=" + aRangeAddress.Sheet );
331         Console.WriteLine(
332             "Start column=" + aRangeAddress.StartColumn + ";  Start row=" +
333             aRangeAddress.StartRow );
334         Console.WriteLine(
335             "End column  =" + aRangeAddress.EndColumn   + ";  End row  =" +
336             aRangeAddress.EndRow );
337 
338 
339         // --- Sheet operation. ---
340         // uses the range filled with XCellRangeData
341         unoidl.com.sun.star.sheet.XSheetOperation xSheetOp =
342             (unoidl.com.sun.star.sheet.XSheetOperation) xData;
343         double fResult = xSheetOp.computeFunction(
344             unoidl.com.sun.star.sheet.GeneralFunction.AVERAGE );
345         Console.WriteLine(
346             "Average value of the data table A10:C30: " + fResult );
347 
348 
349         // --- Fill series ---
350         // Prepare the example
351         setValue( xSheet, "E10", 1 );
352         setValue( xSheet, "E11", 4 );
353         setDate( xSheet, "E12", 30, 1, 2002 );
354         setFormula( xSheet, "I13", "Text 10" );
355         setFormula( xSheet, "E14", "Jan" );
356         setValue( xSheet, "K14", 10 );
357         setValue( xSheet, "E16", 1 );
358         setValue( xSheet, "F16", 2 );
359         setDate( xSheet, "E17", 28, 2, 2002 );
360         setDate( xSheet, "F17", 28, 1, 2002 );
361         setValue( xSheet, "E18", 6 );
362         setValue( xSheet, "F18", 4 );
363 
364         unoidl.com.sun.star.sheet.XCellSeries xSeries = null;
365         // Fill 2 rows linear with end value
366         // -> 2nd series is not filled completely
367         xSeries = getCellSeries( xSheet, "E10:I11" );
368         xSeries.fillSeries(
369             unoidl.com.sun.star.sheet.FillDirection.TO_RIGHT,
370             unoidl.com.sun.star.sheet.FillMode.LINEAR,
371             unoidl.com.sun.star.sheet.FillDateMode.FILL_DATE_DAY, 2, 9 );
372         // Add months to a date
373         xSeries = getCellSeries( xSheet, "E12:I12" );
374         xSeries.fillSeries(
375             unoidl.com.sun.star.sheet.FillDirection.TO_RIGHT,
376             unoidl.com.sun.star.sheet.FillMode.DATE,
377             unoidl.com.sun.star.sheet.FillDateMode.FILL_DATE_MONTH,
378             1, 0x7FFFFFFF );
379         // Fill right to left with a text containing a value
380         xSeries = getCellSeries( xSheet, "E13:I13" );
381         xSeries.fillSeries(
382             unoidl.com.sun.star.sheet.FillDirection.TO_LEFT,
383             unoidl.com.sun.star.sheet.FillMode.LINEAR,
384             unoidl.com.sun.star.sheet.FillDateMode.FILL_DATE_DAY,
385             10, 0x7FFFFFFF );
386         // Fill with an user defined list
387         xSeries = getCellSeries( xSheet, "E14:I14" );
388         xSeries.fillSeries(
389             unoidl.com.sun.star.sheet.FillDirection.TO_RIGHT,
390             unoidl.com.sun.star.sheet.FillMode.AUTO,
391             unoidl.com.sun.star.sheet.FillDateMode.FILL_DATE_DAY,
392             1, 0x7FFFFFFF );
393         // Fill bottom to top with a geometric series
394         xSeries = getCellSeries( xSheet, "K10:K14" );
395         xSeries.fillSeries(
396             unoidl.com.sun.star.sheet.FillDirection.TO_TOP,
397             unoidl.com.sun.star.sheet.FillMode.GROWTH,
398             unoidl.com.sun.star.sheet.FillDateMode.FILL_DATE_DAY,
399             2, 0x7FFFFFFF );
400         // Auto fill
401         xSeries = getCellSeries( xSheet, "E16:K18" );
402         xSeries.fillAuto(
403             unoidl.com.sun.star.sheet.FillDirection.TO_RIGHT, 2 );
404         // Fill series copies cell formats -> draw border here
405         prepareRange( xSheet, "E9:K18", "XCellSeries" );
406 
407 
408         // --- Array formulas ---
409         xCellRange = xSheet.getCellRangeByName( "E21:G23" );
410         prepareRange( xSheet, "E20:G23", "XArrayFormulaRange" );
411         unoidl.com.sun.star.sheet.XArrayFormulaRange xArrayFormula =
412             (unoidl.com.sun.star.sheet.XArrayFormulaRange) xCellRange;
413         // Insert a 3x3 unit matrix.
414         xArrayFormula.setArrayFormula( "=A10:C12" );
415         Console.WriteLine(
416             "Array formula is: " + xArrayFormula.getArrayFormula() );
417 
418 
419         // --- Multiple operations ---
420         setFormula( xSheet, "E26", "=E27^F26" );
421         setValue( xSheet, "E27", 1 );
422         setValue( xSheet, "F26", 1 );
423         getCellSeries( xSheet, "E27:E31" ).fillAuto(
424             unoidl.com.sun.star.sheet.FillDirection.TO_BOTTOM, 1 );
425         getCellSeries( xSheet, "F26:J26" ).fillAuto(
426             unoidl.com.sun.star.sheet.FillDirection.TO_RIGHT, 1 );
427         setFormula( xSheet, "F33", "=SIN(E33)" );
428         setFormula( xSheet, "G33", "=COS(E33)" );
429         setFormula( xSheet, "H33", "=TAN(E33)" );
430         setValue( xSheet, "E34", 0 );
431         setValue( xSheet, "E35", 0.2 );
432         getCellSeries( xSheet, "E34:E38" ).fillAuto(
433             unoidl.com.sun.star.sheet.FillDirection.TO_BOTTOM, 2 );
434         prepareRange( xSheet, "E25:J38", "XMultipleOperation" );
435 
436         unoidl.com.sun.star.table.CellRangeAddress aFormulaRange =
437             createCellRangeAddress( xSheet, "E26" );
438         unoidl.com.sun.star.table.CellAddress aColCell =
439             createCellAddress( xSheet, "E27" );
440         unoidl.com.sun.star.table.CellAddress aRowCell =
441             createCellAddress( xSheet, "F26" );
442 
443         xCellRange = xSheet.getCellRangeByName( "E26:J31" );
444         unoidl.com.sun.star.sheet.XMultipleOperation xMultOp =
445             (unoidl.com.sun.star.sheet.XMultipleOperation) xCellRange;
446         xMultOp.setTableOperation(
447             aFormulaRange, unoidl.com.sun.star.sheet.TableOperationMode.BOTH,
448             aColCell, aRowCell );
449 
450         aFormulaRange = createCellRangeAddress( xSheet, "F33:H33" );
451         aColCell = createCellAddress( xSheet, "E33" );
452         // Row cell not needed
453 
454         xCellRange = xSheet.getCellRangeByName( "E34:H38" );
455         xMultOp = (unoidl.com.sun.star.sheet.XMultipleOperation) xCellRange;
456         xMultOp.setTableOperation(
457             aFormulaRange, unoidl.com.sun.star.sheet.TableOperationMode.COLUMN,
458             aColCell, aRowCell );
459 
460 
461         // --- Cell Ranges Query ---
462         xCellRange = xSheet.getCellRangeByName( "A10:C30" );
463         unoidl.com.sun.star.sheet.XCellRangesQuery xRangesQuery =
464             (unoidl.com.sun.star.sheet.XCellRangesQuery) xCellRange;
465         unoidl.com.sun.star.sheet.XSheetCellRanges xCellRanges =
466             xRangesQuery.queryContentCells(
467                 (short) unoidl.com.sun.star.sheet.CellFlags.STRING );
468         Console.WriteLine(
469             "Cells in A10:C30 containing text: "
470             + xCellRanges.getRangeAddressesAsString() );
471     }
472 
473     /** Returns the XCellSeries interface of a cell range.
474         @param xSheet  The spreadsheet containing the cell range.
475         @param aRange  The address of the cell range.
476         @return  The XCellSeries interface. */
477     private unoidl.com.sun.star.sheet.XCellSeries getCellSeries(
478             unoidl.com.sun.star.sheet.XSpreadsheet xSheet, String aRange )
479     {
480         return (unoidl.com.sun.star.sheet.XCellSeries)
481             xSheet.getCellRangeByName( aRange );
482     }
483 
484 // ________________________________________________________________
485 
486     /** All samples regarding cell range collections. */
487     private void doCellRangesSamples()
488     {
489         Console.WriteLine( "\n*** Samples for cell range collections ***\n" );
490 
491         // Create a new cell range container
492         unoidl.com.sun.star.lang.XMultiServiceFactory xDocFactory =
493             (unoidl.com.sun.star.lang.XMultiServiceFactory) getDocument();
494         unoidl.com.sun.star.sheet.XSheetCellRangeContainer xRangeCont =
495             (unoidl.com.sun.star.sheet.XSheetCellRangeContainer)
496             xDocFactory.createInstance(
497                 "com.sun.star.sheet.SheetCellRanges" );
498 
499 
500         // --- Insert ranges ---
501         insertRange( xRangeCont, 0, 0, 0, 0, 0, false );    // A1:A1
502         insertRange( xRangeCont, 0, 0, 1, 0, 2, true );     // A2:A3
503         insertRange( xRangeCont, 0, 1, 0, 1, 2, false );    // B1:B3
504 
505 
506         // --- Query the list of filled cells ---
507         Console.WriteLine( "All filled cells: " );
508         unoidl.com.sun.star.container.XEnumerationAccess xCellsEA =
509             xRangeCont.getCells();
510         unoidl.com.sun.star.container.XEnumeration xEnum =
511             xCellsEA.createEnumeration();
512         while( xEnum.hasMoreElements() )
513         {
514             uno.Any aCellObj = xEnum.nextElement();
515             unoidl.com.sun.star.sheet.XCellAddressable xAddr =
516                 (unoidl.com.sun.star.sheet.XCellAddressable) aCellObj.Value;
517             unoidl.com.sun.star.table.CellAddress aAddr =
518                 xAddr.getCellAddress();
519             Console.WriteLine(
520                 getCellAddressString( aAddr.Column, aAddr.Row ) + " " );
521         }
522         Console.WriteLine();
523     }
524 
525     /** Inserts a cell range address into a cell range container and prints
526         a message.
527         @param xContainer  unoidl.com.sun.star.sheet.XSheetCellRangeContainer
528                            interface of the container.
529         @param nSheet  Index of sheet of the range.
530         @param nStartCol  Index of first column of the range.
531         @param nStartRow  Index of first row of the range.
532         @param nEndCol  Index of last column of the range.
533         @param nEndRow  Index of last row of the range.
534         @param bMerge  Determines whether the new range should be merged
535                        with the existing ranges.
536     */
537     private void insertRange(
538             unoidl.com.sun.star.sheet.XSheetCellRangeContainer xContainer,
539             int nSheet, int nStartCol, int nStartRow, int nEndCol, int nEndRow,
540             bool bMerge )
541     {
542         unoidl.com.sun.star.table.CellRangeAddress aAddress =
543             new unoidl.com.sun.star.table.CellRangeAddress();
544         aAddress.Sheet = (short)nSheet;
545         aAddress.StartColumn = nStartCol;
546         aAddress.StartRow = nStartRow;
547         aAddress.EndColumn = nEndCol;
548         aAddress.EndRow = nEndRow;
549         xContainer.addRangeAddress( aAddress, bMerge );
550         Console.WriteLine(
551             "Inserting " + getCellRangeAddressString( aAddress )
552             + " " + (bMerge ? "   with" : "without") + " merge,"
553             + " resulting list: " + xContainer.getRangeAddressesAsString() );
554     }
555 
556 // ________________________________________________________________
557 
558     /** All samples regarding cell cursors. */
559     private void doCellCursorSamples()
560     {
561         Console.WriteLine( "\n*** Samples for cell cursor ***\n" );
562         unoidl.com.sun.star.sheet.XSpreadsheet xSheet = getSpreadsheet( 0 );
563 
564 
565         // --- Find the array formula using a cell cursor ---
566         unoidl.com.sun.star.table.XCellRange xRange =
567             xSheet.getCellRangeByName( "F22" );
568         unoidl.com.sun.star.sheet.XSheetCellRange xCellRange =
569             (unoidl.com.sun.star.sheet.XSheetCellRange) xRange;
570         unoidl.com.sun.star.sheet.XSheetCellCursor xCursor =
571             xSheet.createCursorByRange( xCellRange );
572 
573         xCursor.collapseToCurrentArray();
574         unoidl.com.sun.star.sheet.XArrayFormulaRange xArray =
575             (unoidl.com.sun.star.sheet.XArrayFormulaRange) xCursor;
576         Console.WriteLine(
577             "Array formula in " + getCellRangeAddressString( xCursor, false )
578             + " contains formula " + xArray.getArrayFormula() );
579 
580 
581         // --- Find the used area ---
582         unoidl.com.sun.star.sheet.XUsedAreaCursor xUsedCursor =
583             (unoidl.com.sun.star.sheet.XUsedAreaCursor) xCursor;
584         xUsedCursor.gotoStartOfUsedArea( false );
585         xUsedCursor.gotoEndOfUsedArea( true );
586         // xUsedCursor and xCursor are interfaces of the same object -
587         // so modifying xUsedCursor takes effect on xCursor:
588         Console.WriteLine(
589             "The used area is: " + getCellRangeAddressString( xCursor, true ) );
590     }
591 
592 // ________________________________________________________________
593 
594     /** All samples regarding the formatting of cells and ranges. */
595     private void doFormattingSamples()
596     {
597         Console.WriteLine( "\n*** Formatting samples ***\n" );
598         unoidl.com.sun.star.sheet.XSpreadsheet xSheet = getSpreadsheet( 1 );
599         unoidl.com.sun.star.table.XCellRange xCellRange;
600         unoidl.com.sun.star.beans.XPropertySet xPropSet = null;
601         unoidl.com.sun.star.container.XIndexAccess xRangeIA = null;
602         unoidl.com.sun.star.lang.XMultiServiceFactory xServiceManager;
603 
604 
605         // --- Cell styles ---
606         // get the cell style container
607         unoidl.com.sun.star.style.XStyleFamiliesSupplier xFamiliesSupplier =
608             (unoidl.com.sun.star.style.XStyleFamiliesSupplier) getDocument();
609         unoidl.com.sun.star.container.XNameAccess xFamiliesNA =
610             xFamiliesSupplier.getStyleFamilies();
611         uno.Any aCellStylesObj = xFamiliesNA.getByName( "CellStyles" );
612         unoidl.com.sun.star.container.XNameContainer xCellStylesNA =
613             (unoidl.com.sun.star.container.XNameContainer) aCellStylesObj.Value;
614 
615         // create a new cell style
616         xServiceManager =
617             (unoidl.com.sun.star.lang.XMultiServiceFactory) getDocument();
618         Object aCellStyle = xServiceManager.createInstance(
619             "com.sun.star.style.CellStyle" );
620         String aStyleName = "MyNewCellStyle";
621         xCellStylesNA.insertByName(
622             aStyleName, new uno.Any( typeof (Object), aCellStyle ) );
623 
624         // modify properties of the new style
625         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) aCellStyle;
626         xPropSet.setPropertyValue(
627             "CellBackColor", new uno.Any( (Int32) 0x888888 ) );
628         xPropSet.setPropertyValue(
629             "IsCellBackgroundTransparent", new uno.Any( false ) );
630 
631 
632 
633         // --- Query equal-formatted cell ranges ---
634         // prepare example, use the new cell style
635         xCellRange = xSheet.getCellRangeByName( "D2:F2" );
636         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) xCellRange;
637         xPropSet.setPropertyValue( "CellStyle", new uno.Any( aStyleName ) );
638 
639         xCellRange = xSheet.getCellRangeByName( "A3:G3" );
640         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) xCellRange;
641         xPropSet.setPropertyValue( "CellStyle", new uno.Any( aStyleName ) );
642 
643         // All ranges in one container
644         xCellRange = xSheet.getCellRangeByName( "A1:G3" );
645         Console.WriteLine( "Service CellFormatRanges:" );
646         unoidl.com.sun.star.sheet.XCellFormatRangesSupplier xFormatSupp =
647             (unoidl.com.sun.star.sheet.XCellFormatRangesSupplier) xCellRange;
648         xRangeIA = xFormatSupp.getCellFormatRanges();
649         Console.WriteLine( getCellRangeListString( xRangeIA ) );
650 
651         // Ranges sorted in SheetCellRanges containers
652         Console.WriteLine( "\nService UniqueCellFormatRanges:" );
653         unoidl.com.sun.star.sheet.XUniqueCellFormatRangesSupplier
654             xUniqueFormatSupp =
655             (unoidl.com.sun.star.sheet.XUniqueCellFormatRangesSupplier)
656               xCellRange;
657         unoidl.com.sun.star.container.XIndexAccess xRangesIA =
658             xUniqueFormatSupp.getUniqueCellFormatRanges();
659         int nCount = xRangesIA.getCount();
660         for (int nIndex = 0; nIndex < nCount; ++nIndex)
661         {
662             uno.Any aRangesObj = xRangesIA.getByIndex( nIndex );
663             xRangeIA =
664                 (unoidl.com.sun.star.container.XIndexAccess) aRangesObj.Value;
665             Console.WriteLine(
666                 "Container " + (nIndex + 1) + ": " +
667                 getCellRangeListString( xRangeIA ) );
668         }
669 
670 
671         // --- Table auto formats ---
672         // get the global collection of table auto formats,
673         // use global service manager
674         xServiceManager = getServiceManager();
675         Object aAutoFormatsObj = xServiceManager.createInstance(
676             "com.sun.star.sheet.TableAutoFormats" );
677         unoidl.com.sun.star.container.XNameContainer xAutoFormatsNA =
678             (unoidl.com.sun.star.container.XNameContainer) aAutoFormatsObj;
679 
680         // create a new table auto format and insert into the container
681         String aAutoFormatName =  "Temp_Example";
682         bool bExistsAlready = xAutoFormatsNA.hasByName( aAutoFormatName );
683         uno.Any aAutoFormatObj;
684         if (bExistsAlready)
685             // auto format already exists -> use it
686             aAutoFormatObj = xAutoFormatsNA.getByName( aAutoFormatName );
687         else
688         {
689             // create a new auto format (with document service manager!)
690             xServiceManager =
691                 (unoidl.com.sun.star.lang.XMultiServiceFactory) getDocument();
692             aAutoFormatObj = new uno.Any(
693                 typeof (Object),
694                 xServiceManager.createInstance(
695                     "com.sun.star.sheet.TableAutoFormat" ) );
696             xAutoFormatsNA.insertByName( aAutoFormatName, aAutoFormatObj );
697         }
698         // index access to the auto format fields
699         unoidl.com.sun.star.container.XIndexAccess xAutoFormatIA =
700             (unoidl.com.sun.star.container.XIndexAccess) aAutoFormatObj.Value;
701 
702         // set properties of all auto format fields
703         for (int nRow = 0; nRow < 4; ++nRow)
704         {
705             int nRowColor = 0;
706             switch (nRow)
707             {
708                 case 0:     nRowColor = 0x999999;   break;
709                 case 1:     nRowColor = 0xFFFFCC;   break;
710                 case 2:     nRowColor = 0xEEEEEE;   break;
711                 case 3:     nRowColor = 0x999999;   break;
712             }
713 
714             for (int nColumn = 0; nColumn < 4; ++nColumn)
715             {
716                 int nColor = nRowColor;
717                 if ((nColumn == 0) || (nColumn == 3))
718                     nColor -= 0x333300;
719 
720                 // get the auto format field and apply properties
721                 uno.Any aFieldObj = xAutoFormatIA.getByIndex(
722                     4 * nRow + nColumn );
723                 xPropSet =
724                     (unoidl.com.sun.star.beans.XPropertySet) aFieldObj.Value;
725                 xPropSet.setPropertyValue(
726                     "CellBackColor", new uno.Any( (Int32) nColor ) );
727             }
728         }
729 
730         // set the auto format to the spreadsheet
731         xCellRange = xSheet.getCellRangeByName( "A5:H25" );
732         unoidl.com.sun.star.table.XAutoFormattable xAutoForm =
733             (unoidl.com.sun.star.table.XAutoFormattable) xCellRange;
734         xAutoForm.autoFormat( aAutoFormatName );
735 
736         // remove the auto format
737         if (!bExistsAlready)
738             xAutoFormatsNA.removeByName( aAutoFormatName );
739 
740 
741         // --- Conditional formats ---
742         xSheet = getSpreadsheet( 0 );
743         prepareRange( xSheet, "K20:K23", "Cond. Format" );
744         setValue( xSheet, "K21", 1 );
745         setValue( xSheet, "K22", 2 );
746         setValue( xSheet, "K23", 3 );
747 
748         // get the conditional format object of the cell range
749         xCellRange = xSheet.getCellRangeByName( "K21:K23" );
750         xPropSet = (unoidl.com.sun.star.beans.XPropertySet) xCellRange;
751         unoidl.com.sun.star.sheet.XSheetConditionalEntries xEntries =
752             (unoidl.com.sun.star.sheet.XSheetConditionalEntries)
753               xPropSet.getPropertyValue( "ConditionalFormat" ).Value;
754 
755         // create a condition and apply it to the range
756         unoidl.com.sun.star.beans.PropertyValue[] aCondition =
757             new unoidl.com.sun.star.beans.PropertyValue[3];
758         aCondition[0] = new unoidl.com.sun.star.beans.PropertyValue();
759         aCondition[0].Name  = "Operator";
760         aCondition[0].Value =
761             new uno.Any(
762                 typeof (unoidl.com.sun.star.sheet.ConditionOperator),
763                 unoidl.com.sun.star.sheet.ConditionOperator.GREATER );
764         aCondition[1] = new unoidl.com.sun.star.beans.PropertyValue();
765         aCondition[1].Name  = "Formula1";
766         aCondition[1].Value = new uno.Any( "1" );
767         aCondition[2] = new unoidl.com.sun.star.beans.PropertyValue();
768         aCondition[2].Name  = "StyleName";
769         aCondition[2].Value = new uno.Any( aStyleName );
770         xEntries.addNew( aCondition );
771         xPropSet.setPropertyValue(
772             "ConditionalFormat",
773             new uno.Any(
774                 typeof (unoidl.com.sun.star.sheet.XSheetConditionalEntries),
775                 xEntries ) );
776     }
777 
778 // ________________________________________________________________
779 
780     /** All samples regarding the spreadsheet document. */
781     private void doDocumentSamples()
782     {
783         Console.WriteLine( "\n*** Samples for spreadsheet document ***\n" );
784 
785 
786         // --- Insert a new spreadsheet ---
787         unoidl.com.sun.star.sheet.XSpreadsheet xSheet =
788             insertSpreadsheet( "A new sheet", (short) 0x7FFF );
789 
790 
791         // --- Copy a cell range ---
792         prepareRange( xSheet, "A1:B3", "Copy from" );
793         prepareRange( xSheet, "D1:E3", "To" );
794         setValue( xSheet, "A2", 123 );
795         setValue( xSheet, "B2", 345 );
796         setFormula( xSheet, "A3", "=SUM(A2:B2)" );
797         setFormula( xSheet, "B3", "=FORMULA(A3)" );
798 
799         unoidl.com.sun.star.sheet.XCellRangeMovement xMovement =
800             (unoidl.com.sun.star.sheet.XCellRangeMovement) xSheet;
801         unoidl.com.sun.star.table.CellRangeAddress aSourceRange =
802             createCellRangeAddress( xSheet, "A2:B3" );
803         unoidl.com.sun.star.table.CellAddress aDestCell =
804             createCellAddress( xSheet, "D2" );
805         xMovement.copyRange( aDestCell, aSourceRange );
806 
807 
808         // --- Print automatic column page breaks ---
809         unoidl.com.sun.star.sheet.XSheetPageBreak xPageBreak =
810             (unoidl.com.sun.star.sheet.XSheetPageBreak) xSheet;
811         unoidl.com.sun.star.sheet.TablePageBreakData[] aPageBreakArray =
812             xPageBreak.getColumnPageBreaks();
813 
814         Console.Write( "Automatic column page breaks:" );
815         for (int nIndex = 0; nIndex < aPageBreakArray.Length; ++nIndex)
816             if (!aPageBreakArray[nIndex].ManualBreak)
817                 Console.Write( " " + aPageBreakArray[nIndex].Position );
818         Console.WriteLine();
819 
820 
821         // --- Document properties ---
822         unoidl.com.sun.star.beans.XPropertySet xPropSet =
823             (unoidl.com.sun.star.beans.XPropertySet) getDocument();
824 
825         String aText = "Value of property IsIterationEnabled: ";
826         aText +=
827             (Boolean) xPropSet.getPropertyValue( "IsIterationEnabled" ).Value;
828         Console.WriteLine( aText );
829         aText = "Value of property IterationCount: ";
830         aText += (Int32) xPropSet.getPropertyValue( "IterationCount" ).Value;
831         Console.WriteLine( aText );
832         aText = "Value of property NullDate: ";
833         unoidl.com.sun.star.util.Date aDate = (unoidl.com.sun.star.util.Date)
834             xPropSet.getPropertyValue( "NullDate" ).Value;
835         aText += aDate.Year + "-" + aDate.Month + "-" + aDate.Day;
836         Console.WriteLine( aText );
837 
838 
839         // --- Data validation ---
840         prepareRange( xSheet, "A5:C7", "Validation" );
841         setFormula( xSheet, "A6", "Insert values between 0.0 and 5.0 below:" );
842 
843         unoidl.com.sun.star.table.XCellRange xCellRange =
844             xSheet.getCellRangeByName( "A7:C7" );
845         unoidl.com.sun.star.beans.XPropertySet xCellPropSet =
846             (unoidl.com.sun.star.beans.XPropertySet) xCellRange;
847         // validation properties
848         unoidl.com.sun.star.beans.XPropertySet xValidPropSet =
849             (unoidl.com.sun.star.beans.XPropertySet)
850               xCellPropSet.getPropertyValue( "Validation" ).Value;
851         xValidPropSet.setPropertyValue(
852             "Type",
853             new uno.Any(
854                 typeof (unoidl.com.sun.star.sheet.ValidationType),
855                 unoidl.com.sun.star.sheet.ValidationType.DECIMAL ) );
856         xValidPropSet.setPropertyValue(
857             "ShowErrorMessage", new uno.Any( true ) );
858         xValidPropSet.setPropertyValue(
859             "ErrorMessage", new uno.Any( "This is an invalid value!" ) );
860         xValidPropSet.setPropertyValue(
861             "ErrorAlertStyle",
862             new uno.Any(
863                 typeof (unoidl.com.sun.star.sheet.ValidationAlertStyle),
864                 unoidl.com.sun.star.sheet.ValidationAlertStyle.STOP ) );
865         // condition
866         unoidl.com.sun.star.sheet.XSheetCondition xCondition =
867             (unoidl.com.sun.star.sheet.XSheetCondition) xValidPropSet;
868         xCondition.setOperator(
869             unoidl.com.sun.star.sheet.ConditionOperator.BETWEEN );
870         xCondition.setFormula1( "0.0" );
871         xCondition.setFormula2( "5.0" );
872         // apply on cell range
873         xCellPropSet.setPropertyValue(
874             "Validation",
875             new uno.Any(
876                 typeof (unoidl.com.sun.star.beans.XPropertySet),
877                 xValidPropSet ) );
878 
879 
880         // --- Scenarios ---
881         uno.Any [][] aValues = {
882             new uno.Any [] { uno.Any.VOID, uno.Any.VOID },
883             new uno.Any [] { uno.Any.VOID, uno.Any.VOID }
884         };
885 
886         aValues[ 0 ][ 0 ] = new uno.Any( (Double) 11 );
887         aValues[ 0 ][ 1 ] = new uno.Any( (Double) 12 );
888         aValues[ 1 ][ 0 ] = new uno.Any( "Test13" );
889         aValues[ 1 ][ 1 ] = new uno.Any( "Test14" );
890         insertScenario(
891             xSheet, "B10:C11", aValues,
892             "First Scenario", "The first scenario." );
893 
894         aValues[ 0 ][ 0 ] = new uno.Any( "Test21" );
895         aValues[ 0 ][ 1 ] = new uno.Any( "Test22" );
896         aValues[ 1 ][ 0 ] = new uno.Any( (Double) 23 );
897         aValues[ 1 ][ 1 ] = new uno.Any( (Double) 24 );
898         insertScenario(
899             xSheet, "B10:C11", aValues,
900             "Second Scenario", "The visible scenario." );
901 
902         aValues[ 0 ][ 0 ] = new uno.Any( (Double) 31 );
903         aValues[ 0 ][ 1 ] = new uno.Any( (Double) 32 );
904         aValues[ 1 ][ 0 ] = new uno.Any( "Test33" );
905         aValues[ 1 ][ 1 ] = new uno.Any( "Test34" );
906         insertScenario(
907             xSheet, "B10:C11", aValues,
908             "Third Scenario", "The last scenario." );
909 
910         // show second scenario
911         showScenario( xSheet, "Second Scenario" );
912     }
913 
914     /** Inserts a scenario containing one cell range into a sheet and
915         applies the value array.
916         @param xSheet           The XSpreadsheet interface of the spreadsheet.
917         @param aRange           The range address for the scenario.
918         @param aValueArray      The array of cell contents.
919         @param aScenarioName    The name of the new scenario.
920         @param aScenarioComment The user comment for the scenario. */
921     private void insertScenario(
922             unoidl.com.sun.star.sheet.XSpreadsheet xSheet,
923             String aRange,
924             uno.Any [][] aValueArray,
925             String aScenarioName,
926             String aScenarioComment )
927     {
928         // get the cell range with the given address
929         unoidl.com.sun.star.table.XCellRange xCellRange =
930             xSheet.getCellRangeByName( aRange );
931 
932         // create the range address sequence
933         unoidl.com.sun.star.sheet.XCellRangeAddressable xAddr =
934             (unoidl.com.sun.star.sheet.XCellRangeAddressable) xCellRange;
935         unoidl.com.sun.star.table.CellRangeAddress[] aRangesSeq =
936             new unoidl.com.sun.star.table.CellRangeAddress[1];
937         aRangesSeq[0] = xAddr.getRangeAddress();
938 
939         // create the scenario
940         unoidl.com.sun.star.sheet.XScenariosSupplier xScenSupp =
941             (unoidl.com.sun.star.sheet.XScenariosSupplier) xSheet;
942         unoidl.com.sun.star.sheet.XScenarios xScenarios =
943             xScenSupp.getScenarios();
944         xScenarios.addNewByName( aScenarioName, aRangesSeq, aScenarioComment );
945 
946         // insert the values into the range
947         unoidl.com.sun.star.sheet.XCellRangeData xData =
948             (unoidl.com.sun.star.sheet.XCellRangeData) xCellRange;
949         xData.setDataArray( aValueArray );
950     }
951 
952     /** Activates a scenario.
953         @param xSheet           The XSpreadsheet interface of the spreadsheet.
954         @param aScenarioName    The name of the scenario. */
955     private void showScenario(
956             unoidl.com.sun.star.sheet.XSpreadsheet xSheet,
957             String aScenarioName )
958     {
959         // get the scenario set
960         unoidl.com.sun.star.sheet.XScenariosSupplier xScenSupp =
961             (unoidl.com.sun.star.sheet.XScenariosSupplier) xSheet;
962         unoidl.com.sun.star.sheet.XScenarios xScenarios =
963             xScenSupp.getScenarios();
964 
965         // get the scenario and activate it
966         uno.Any aScenarioObj = xScenarios.getByName( aScenarioName );
967         unoidl.com.sun.star.sheet.XScenario xScenario =
968             (unoidl.com.sun.star.sheet.XScenario) aScenarioObj.Value;
969         xScenario.apply();
970     }
971 
972 // ________________________________________________________________
973 
974     private void doNamedRangesSamples()
975     {
976         Console.WriteLine( "\n*** Samples for named ranges ***\n" );
977         unoidl.com.sun.star.sheet.XSpreadsheetDocument xDocument =
978             getDocument();
979         unoidl.com.sun.star.sheet.XSpreadsheet xSheet =
980             getSpreadsheet( 0 );
981 
982 
983         // --- Named ranges ---
984         prepareRange( xSheet, "G42:H45", "Named ranges" );
985         xSheet.getCellByPosition( 6, 42 ).setValue( 1 );
986         xSheet.getCellByPosition( 6, 43 ).setValue( 2 );
987         xSheet.getCellByPosition( 7, 42 ).setValue( 3 );
988         xSheet.getCellByPosition( 7, 43 ).setValue( 4 );
989 
990         // insert a named range
991         unoidl.com.sun.star.beans.XPropertySet xDocProp =
992             (unoidl.com.sun.star.beans.XPropertySet) xDocument;
993         uno.Any aRangesObj = xDocProp.getPropertyValue( "NamedRanges" );
994         unoidl.com.sun.star.sheet.XNamedRanges xNamedRanges =
995             (unoidl.com.sun.star.sheet.XNamedRanges) aRangesObj.Value;
996         unoidl.com.sun.star.table.CellAddress aRefPos =
997             new unoidl.com.sun.star.table.CellAddress();
998         aRefPos.Sheet  = 0;
999         aRefPos.Column = 6;
1000         aRefPos.Row    = 44;
1001         xNamedRanges.addNewByName( "ExampleName", "SUM(G43:G44)", aRefPos, 0 );
1002 
1003         // use the named range in formulas
1004         xSheet.getCellByPosition( 6, 44 ).setFormula( "=ExampleName" );
1005         xSheet.getCellByPosition( 7, 44 ).setFormula( "=ExampleName" );
1006 
1007 
1008         // --- Label ranges ---
1009         prepareRange( xSheet, "G47:I50", "Label ranges" );
1010         unoidl.com.sun.star.table.XCellRange xRange =
1011             xSheet.getCellRangeByPosition( 6, 47, 7, 49 );
1012         unoidl.com.sun.star.sheet.XCellRangeData xData =
1013             ( unoidl.com.sun.star.sheet.XCellRangeData ) xRange;
1014         uno.Any [][] aValues =
1015         {
1016             new uno.Any [] { new uno.Any( "Apples" ),
1017                              new uno.Any( "Oranges" ) },
1018             new uno.Any [] { new uno.Any( (Double) 5 ),
1019                              new uno.Any( (Double) 7 ) },
1020             new uno.Any [] { new uno.Any( (Double) 6 ),
1021                              new uno.Any( (Double) 8 ) }
1022         };
1023         xData.setDataArray( aValues );
1024 
1025         // insert a column label range
1026         uno.Any aLabelsObj = xDocProp.getPropertyValue( "ColumnLabelRanges" );
1027         unoidl.com.sun.star.sheet.XLabelRanges xLabelRanges =
1028             (unoidl.com.sun.star.sheet.XLabelRanges) aLabelsObj.Value;
1029         unoidl.com.sun.star.table.CellRangeAddress aLabelArea =
1030             new unoidl.com.sun.star.table.CellRangeAddress();
1031         aLabelArea.Sheet       = 0;
1032         aLabelArea.StartColumn = 6;
1033         aLabelArea.StartRow    = 47;
1034         aLabelArea.EndColumn   = 7;
1035         aLabelArea.EndRow      = 47;
1036         unoidl.com.sun.star.table.CellRangeAddress aDataArea =
1037             new unoidl.com.sun.star.table.CellRangeAddress();
1038         aDataArea.Sheet       = 0;
1039         aDataArea.StartColumn = 6;
1040         aDataArea.StartRow    = 48;
1041         aDataArea.EndColumn   = 7;
1042         aDataArea.EndRow      = 49;
1043         xLabelRanges.addNew( aLabelArea, aDataArea );
1044 
1045         // use the label range in formulas
1046         xSheet.getCellByPosition( 8, 48 ).setFormula( "=Apples+Oranges" );
1047         xSheet.getCellByPosition( 8, 49 ).setFormula( "=Apples+Oranges" );
1048     }
1049 
1050 // ________________________________________________________________
1051 
1052     /** Helper for doDatabaseSamples: get name of first database. */
1053     private String getFirstDatabaseName()
1054     {
1055         String aDatabase = null;
1056         unoidl.com.sun.star.lang.XMultiServiceFactory xServiceManager =
1057             getServiceManager();
1058         unoidl.com.sun.star.container.XNameAccess xContext =
1059             (unoidl.com.sun.star.container.XNameAccess)
1060             xServiceManager.createInstance(
1061                 "com.sun.star.sdb.DatabaseContext" );
1062         String[] aNames = xContext.getElementNames();
1063         if ( aNames.Length > 0 )
1064             aDatabase = aNames[0];
1065         return aDatabase;
1066     }
1067 
1068     /** Helper for doDatabaseSamples: get name of first table in a database. */
1069     private String getFirstTableName( String aDatabase )
1070     {
1071         if ( aDatabase == null )
1072             return null;
1073 
1074         String aTable = null;
1075         unoidl.com.sun.star.lang.XMultiServiceFactory xServiceManager =
1076             getServiceManager();
1077         unoidl.com.sun.star.container.XNameAccess xContext =
1078             (unoidl.com.sun.star.container.XNameAccess)
1079             xServiceManager.createInstance(
1080                 "com.sun.star.sdb.DatabaseContext" );
1081         unoidl.com.sun.star.sdb.XCompletedConnection xSource =
1082             (unoidl.com.sun.star.sdb.XCompletedConnection)
1083               xContext.getByName( aDatabase ).Value;
1084         unoidl.com.sun.star.task.XInteractionHandler xHandler =
1085             (unoidl.com.sun.star.task.XInteractionHandler)
1086               xServiceManager.createInstance(
1087                   "com.sun.star.task.InteractionHandler" );
1088          unoidl.com.sun.star.sdbcx.XTablesSupplier xSupplier =
1089             (unoidl.com.sun.star.sdbcx.XTablesSupplier)
1090               xSource.connectWithCompletion( xHandler );
1091         unoidl.com.sun.star.container.XNameAccess xTables =
1092             xSupplier.getTables();
1093         String[] aNames = xTables.getElementNames();
1094         if ( aNames.Length > 0 )
1095             aTable = aNames[0];
1096         return aTable;
1097     }
1098 
1099     private void doDatabaseSamples()
1100     {
1101         Console.WriteLine( "\n*** Samples for database operations ***\n" );
1102         unoidl.com.sun.star.sheet.XSpreadsheet xSheet = getSpreadsheet( 2 );
1103 
1104 
1105         // --- put some example data into the sheet ---
1106         unoidl.com.sun.star.table.XCellRange xRange =
1107             xSheet.getCellRangeByName( "B3:D24" );
1108         unoidl.com.sun.star.sheet.XCellRangeData xData =
1109             (unoidl.com.sun.star.sheet.XCellRangeData) xRange;
1110         uno.Any [][] aValues =
1111         {
1112             new uno.Any [] { new uno.Any( "Name" ),
1113                              new uno.Any( "Year" ),
1114                              new uno.Any( "Sales" ) },
1115             new uno.Any [] { new uno.Any( "Alice" ),
1116                              new uno.Any( (Double) 2001 ),
1117                              new uno.Any( (Double) 4.0 ) },
1118             new uno.Any [] { new uno.Any( "Carol" ),
1119                              new uno.Any( (Double) 1997 ),
1120                              new uno.Any( (Double) 3.0 ) },
1121             new uno.Any [] { new uno.Any( "Carol" ),
1122                              new uno.Any( (Double) 1998 ),
1123                              new uno.Any( (Double) 8.0 ) },
1124             new uno.Any [] { new uno.Any( "Bob" ),
1125                              new uno.Any( (Double) 1997 ),
1126                              new uno.Any( (Double) 8.0 ) },
1127             new uno.Any [] { new uno.Any( "Alice" ),
1128                              new uno.Any( (Double) 2002 ),
1129                              new uno.Any( (Double) 9.0 ) },
1130             new uno.Any [] { new uno.Any( "Alice" ),
1131                              new uno.Any( (Double) 1999 ),
1132                              new uno.Any( (Double) 7.0 ) },
1133             new uno.Any [] { new uno.Any( "Alice" ),
1134                              new uno.Any( (Double) 1996 ),
1135                              new uno.Any( (Double) 3.0 ) },
1136             new uno.Any [] { new uno.Any( "Bob" ),
1137                              new uno.Any( (Double) 2000 ),
1138                              new uno.Any( (Double) 1.0 ) },
1139             new uno.Any [] { new uno.Any( "Carol" ),
1140                              new uno.Any( (Double) 1999 ),
1141                              new uno.Any( (Double) 5.0 ) },
1142             new uno.Any [] { new uno.Any( "Bob" ),
1143                              new uno.Any( (Double) 2002 ),
1144                              new uno.Any( (Double) 1.0 ) },
1145             new uno.Any [] { new uno.Any( "Carol" ),
1146               new uno.Any( (Double) 2001 ),
1147               new uno.Any( (Double) 5.0 ) },
1148             new uno.Any [] { new uno.Any( "Carol" ),
1149               new uno.Any( (Double) 2000 ),
1150               new uno.Any( (Double) 1.0 ) },
1151             new uno.Any [] { new uno.Any( "Carol" ),
1152               new uno.Any( (Double) 1996 ),
1153               new uno.Any( (Double) 8.0 ) },
1154             new uno.Any [] { new uno.Any( "Bob" ),
1155               new uno.Any( (Double) 1996 ),
1156               new uno.Any( (Double) 7.0 ) },
1157             new uno.Any [] { new uno.Any( "Alice" ),
1158               new uno.Any( (Double) 1997 ),
1159               new uno.Any( (Double) 3.0 ) },
1160             new uno.Any [] { new uno.Any( "Alice" ),
1161               new uno.Any( (Double) 2000 ),
1162               new uno.Any( (Double) 9.0 ) },
1163             new uno.Any [] { new uno.Any( "Bob" ),
1164               new uno.Any( (Double) 1998 ),
1165               new uno.Any( (Double) 1.0 ) },
1166             new uno.Any [] { new uno.Any( "Bob" ),
1167               new uno.Any( (Double) 1999 ),
1168               new uno.Any( (Double) 6.0 ) },
1169             new uno.Any [] { new uno.Any( "Carol" ),
1170               new uno.Any( (Double) 2002 ),
1171               new uno.Any( (Double) 8.0 ) },
1172             new uno.Any [] { new uno.Any( "Alice" ),
1173               new uno.Any( (Double) 1998 ),
1174               new uno.Any( (Double) 5.0 ) },
1175             new uno.Any [] { new uno.Any( "Bob" ),
1176               new uno.Any( (Double) 2001 ),
1177               new uno.Any( (Double) 6.0 ) }
1178         };
1179         xData.setDataArray( aValues );
1180 
1181 
1182         // --- filter for second column >= 1998 ---
1183         unoidl.com.sun.star.sheet.XSheetFilterable xFilter =
1184             (unoidl.com.sun.star.sheet.XSheetFilterable) xRange;
1185         unoidl.com.sun.star.sheet.XSheetFilterDescriptor xFilterDesc =
1186             xFilter.createFilterDescriptor( true );
1187         unoidl.com.sun.star.sheet.TableFilterField[] aFilterFields =
1188             new unoidl.com.sun.star.sheet.TableFilterField[1];
1189         aFilterFields[0] = new unoidl.com.sun.star.sheet.TableFilterField();
1190         aFilterFields[0].Field        = 1;
1191         aFilterFields[0].IsNumeric    = true;
1192         aFilterFields[0].Operator =
1193             unoidl.com.sun.star.sheet.FilterOperator.GREATER_EQUAL;
1194         aFilterFields[0].NumericValue = 1998;
1195         xFilterDesc.setFilterFields( aFilterFields );
1196         unoidl.com.sun.star.beans.XPropertySet xFilterProp =
1197             (unoidl.com.sun.star.beans.XPropertySet) xFilterDesc;
1198         xFilterProp.setPropertyValue(
1199             "ContainsHeader", new uno.Any( true ) );
1200         xFilter.filter( xFilterDesc );
1201 
1202 
1203         // --- do the same filter as above, using criteria from a cell range ---
1204         unoidl.com.sun.star.table.XCellRange xCritRange =
1205             xSheet.getCellRangeByName( "B27:B28" );
1206         unoidl.com.sun.star.sheet.XCellRangeData xCritData =
1207             (unoidl.com.sun.star.sheet.XCellRangeData) xCritRange;
1208         uno.Any [][] aCritValues =
1209         {
1210             new uno.Any [] { new uno.Any( "Year" ) },
1211             new uno.Any [] { new uno.Any( ">= 1998" ) }
1212         };
1213         xCritData.setDataArray( aCritValues );
1214         unoidl.com.sun.star.sheet.XSheetFilterableEx xCriteria =
1215             (unoidl.com.sun.star.sheet.XSheetFilterableEx) xCritRange;
1216         xFilterDesc = xCriteria.createFilterDescriptorByObject( xFilter );
1217         if ( xFilterDesc != null )
1218             xFilter.filter( xFilterDesc );
1219 
1220 
1221         // --- sort by second column, ascending ---
1222         unoidl.com.sun.star.util.SortField[] aSortFields =
1223             new unoidl.com.sun.star.util.SortField[1];
1224         aSortFields[0] = new unoidl.com.sun.star.util.SortField();
1225         aSortFields[0].Field         = 1;
1226         aSortFields[0].SortAscending = true;
1227 
1228         unoidl.com.sun.star.beans.PropertyValue[] aSortDesc =
1229             new unoidl.com.sun.star.beans.PropertyValue[2];
1230         aSortDesc[0] = new unoidl.com.sun.star.beans.PropertyValue();
1231         aSortDesc[0].Name   = "SortFields";
1232         aSortDesc[0].Value  =
1233             new uno.Any(
1234                 typeof (unoidl.com.sun.star.util.SortField []),
1235                 aSortFields );
1236         aSortDesc[1] = new unoidl.com.sun.star.beans.PropertyValue();
1237         aSortDesc[1].Name   = "ContainsHeader";
1238         aSortDesc[1].Value  = new uno.Any( true );
1239 
1240         unoidl.com.sun.star.util.XSortable xSort =
1241             (unoidl.com.sun.star.util.XSortable) xRange;
1242         xSort.sort( aSortDesc );
1243 
1244 
1245         // --- insert subtotals ---
1246         unoidl.com.sun.star.sheet.XSubTotalCalculatable xSub =
1247             (unoidl.com.sun.star.sheet.XSubTotalCalculatable) xRange;
1248         unoidl.com.sun.star.sheet.XSubTotalDescriptor xSubDesc =
1249             xSub.createSubTotalDescriptor( true );
1250         unoidl.com.sun.star.sheet.SubTotalColumn[] aColumns =
1251             new unoidl.com.sun.star.sheet.SubTotalColumn[1];
1252         // calculate sum of third column
1253         aColumns[0] = new unoidl.com.sun.star.sheet.SubTotalColumn();
1254         aColumns[0].Column   = 2;
1255         aColumns[0].Function = unoidl.com.sun.star.sheet.GeneralFunction.SUM;
1256         // group by first column
1257         xSubDesc.addNew( aColumns, 0 );
1258         xSub.applySubTotals( xSubDesc, true );
1259 
1260         String aDatabase = getFirstDatabaseName();
1261         String aTableName = getFirstTableName( aDatabase );
1262         if ( aDatabase != null && aTableName != null )
1263         {
1264             // --- import from database ---
1265             unoidl.com.sun.star.beans.PropertyValue[] aImportDesc =
1266                 new unoidl.com.sun.star.beans.PropertyValue[3];
1267             aImportDesc[0] = new unoidl.com.sun.star.beans.PropertyValue();
1268             aImportDesc[0].Name     = "DatabaseName";
1269             aImportDesc[0].Value    = new uno.Any( aDatabase );
1270             aImportDesc[1] = new unoidl.com.sun.star.beans.PropertyValue();
1271             aImportDesc[1].Name     = "SourceType";
1272             aImportDesc[1].Value    =
1273                 new uno.Any(
1274                     typeof (unoidl.com.sun.star.sheet.DataImportMode),
1275                     unoidl.com.sun.star.sheet.DataImportMode.TABLE );
1276             aImportDesc[2] = new unoidl.com.sun.star.beans.PropertyValue();
1277             aImportDesc[2].Name     = "SourceObject";
1278             aImportDesc[2].Value    = new uno.Any( aTableName );
1279 
1280             unoidl.com.sun.star.table.XCellRange xImportRange =
1281                 xSheet.getCellRangeByName( "B35:B35" );
1282             unoidl.com.sun.star.util.XImportable xImport =
1283                 (unoidl.com.sun.star.util.XImportable) xImportRange;
1284             xImport.doImport( aImportDesc );
1285 
1286 
1287             // --- use the temporary database range to find the
1288             // imported data's size ---
1289             unoidl.com.sun.star.beans.XPropertySet xDocProp =
1290                 (unoidl.com.sun.star.beans.XPropertySet) getDocument();
1291             uno.Any aRangesObj = xDocProp.getPropertyValue( "DatabaseRanges" );
1292             unoidl.com.sun.star.container.XNameAccess xRanges =
1293                 (unoidl.com.sun.star.container.XNameAccess) aRangesObj.Value;
1294             String[] aNames = xRanges.getElementNames();
1295             for ( int i=0; i<aNames.Length; i++ )
1296             {
1297                 uno.Any aRangeObj = xRanges.getByName( aNames[i] );
1298                 unoidl.com.sun.star.beans.XPropertySet xRangeProp =
1299                     (unoidl.com.sun.star.beans.XPropertySet) aRangeObj.Value;
1300                 bool bUser = (Boolean)
1301                     xRangeProp.getPropertyValue( "IsUserDefined" ).Value;
1302                 if ( !bUser )
1303                 {
1304                     // this is the temporary database range -
1305                     // get the cell range and format it
1306                     unoidl.com.sun.star.sheet.XCellRangeReferrer xRef =
1307                         (unoidl.com.sun.star.sheet.XCellRangeReferrer)
1308                           aRangeObj.Value;
1309                     unoidl.com.sun.star.table.XCellRange xResultRange =
1310                         xRef.getReferredCells();
1311                     unoidl.com.sun.star.beans.XPropertySet xResultProp =
1312                         (unoidl.com.sun.star.beans.XPropertySet) xResultRange;
1313                     xResultProp.setPropertyValue(
1314                         "IsCellBackgroundTransparent", new uno.Any( false ) );
1315                     xResultProp.setPropertyValue(
1316                         "CellBackColor", new uno.Any( (Int32) 0xFFFFCC ) );
1317                 }
1318             }
1319         }
1320         else
1321             Console.WriteLine("can't get database");
1322     }
1323 
1324 // ________________________________________________________________
1325 
1326     private void doDataPilotSamples()
1327     {
1328         Console.WriteLine( "\n*** Samples for Data Pilot ***\n" );
1329         unoidl.com.sun.star.sheet.XSpreadsheet xSheet = getSpreadsheet( 0 );
1330 
1331 
1332         // --- Create a new DataPilot table ---
1333         prepareRange( xSheet, "A38:C38", "Data Pilot" );
1334         unoidl.com.sun.star.sheet.XDataPilotTablesSupplier xDPSupp =
1335             (unoidl.com.sun.star.sheet.XDataPilotTablesSupplier) xSheet;
1336         unoidl.com.sun.star.sheet.XDataPilotTables xDPTables =
1337             xDPSupp.getDataPilotTables();
1338         unoidl.com.sun.star.sheet.XDataPilotDescriptor xDPDesc =
1339             xDPTables.createDataPilotDescriptor();
1340         // set source range (use data range from CellRange test)
1341         unoidl.com.sun.star.table.CellRangeAddress aSourceAddress =
1342             createCellRangeAddress( xSheet, "A10:C30" );
1343         xDPDesc.setSourceRange( aSourceAddress );
1344         // settings for fields
1345         unoidl.com.sun.star.container.XIndexAccess xFields =
1346             xDPDesc.getDataPilotFields();
1347         uno.Any aFieldObj;
1348         unoidl.com.sun.star.beans.XPropertySet xFieldProp;
1349         // use first column as column field
1350         aFieldObj = xFields.getByIndex(0);
1351         xFieldProp = (unoidl.com.sun.star.beans.XPropertySet) aFieldObj.Value;
1352         xFieldProp.setPropertyValue(
1353             "Orientation",
1354             new uno.Any(
1355                 typeof (unoidl.com.sun.star.sheet.DataPilotFieldOrientation),
1356                 unoidl.com.sun.star.sheet.DataPilotFieldOrientation.COLUMN ) );
1357         // use second column as row field
1358         aFieldObj = xFields.getByIndex(1);
1359         xFieldProp = (unoidl.com.sun.star.beans.XPropertySet) aFieldObj.Value;
1360         xFieldProp.setPropertyValue(
1361             "Orientation",
1362             new uno.Any(
1363                 typeof (unoidl.com.sun.star.sheet.DataPilotFieldOrientation),
1364                 unoidl.com.sun.star.sheet.DataPilotFieldOrientation.ROW ) );
1365         // use third column as data field, calculating the sum
1366         aFieldObj = xFields.getByIndex(2);
1367         xFieldProp = (unoidl.com.sun.star.beans.XPropertySet) aFieldObj.Value;
1368         xFieldProp.setPropertyValue(
1369             "Orientation",
1370             new uno.Any(
1371                 typeof (unoidl.com.sun.star.sheet.DataPilotFieldOrientation),
1372                 unoidl.com.sun.star.sheet.DataPilotFieldOrientation.DATA ) );
1373         xFieldProp.setPropertyValue(
1374             "Function",
1375             new uno.Any(
1376                 typeof (unoidl.com.sun.star.sheet.GeneralFunction),
1377                 unoidl.com.sun.star.sheet.GeneralFunction.SUM ) );
1378         // select output position
1379         unoidl.com.sun.star.table.CellAddress aDestAddress =
1380             createCellAddress( xSheet, "A40" );
1381         xDPTables.insertNewByName( "DataPilotExample", aDestAddress, xDPDesc );
1382 
1383 
1384         // --- Modify the DataPilot table ---
1385         uno.Any aDPTableObj = xDPTables.getByName( "DataPilotExample" );
1386         xDPDesc =
1387             (unoidl.com.sun.star.sheet.XDataPilotDescriptor) aDPTableObj.Value;
1388         xFields = xDPDesc.getDataPilotFields();
1389         // add a second data field from the third column,
1390         // calculating the average
1391         aFieldObj = xFields.getByIndex(2);
1392         xFieldProp = (unoidl.com.sun.star.beans.XPropertySet) aFieldObj.Value;
1393         xFieldProp.setPropertyValue(
1394             "Orientation",
1395             new uno.Any(
1396                 typeof (unoidl.com.sun.star.sheet.DataPilotFieldOrientation),
1397                 unoidl.com.sun.star.sheet.DataPilotFieldOrientation.DATA ) );
1398         xFieldProp.setPropertyValue(
1399             "Function",
1400             new uno.Any(
1401                 typeof (unoidl.com.sun.star.sheet.GeneralFunction),
1402                 unoidl.com.sun.star.sheet.GeneralFunction.AVERAGE ) );
1403     }
1404 
1405 // ________________________________________________________________
1406 
1407     private void doFunctionAccessSamples()
1408     {
1409         Console.WriteLine( "\n*** Samples for function handling ***\n" );
1410         unoidl.com.sun.star.lang.XMultiServiceFactory xServiceManager =
1411             getServiceManager();
1412 
1413 
1414         // --- Calculate a function ---
1415         Object aFuncInst = xServiceManager.createInstance(
1416             "com.sun.star.sheet.FunctionAccess" );
1417         unoidl.com.sun.star.sheet.XFunctionAccess xFuncAcc =
1418             (unoidl.com.sun.star.sheet.XFunctionAccess) aFuncInst;
1419         // put the data in a two-dimensional array
1420         Double [][] aData = { new Double [] { 1.0, 2.0, 3.0 } };
1421         // construct the array of function arguments
1422         uno.Any [] aArgs = new uno.Any [2];
1423         aArgs[0] = new uno.Any( typeof (Double [][]), aData );
1424         aArgs[1] = new uno.Any( (Double) 2.0 );
1425         uno.Any aResult = xFuncAcc.callFunction( "ZTEST", aArgs );
1426         Console.WriteLine(
1427             "ZTEST result for data {1,2,3} and value 2 is " + aResult.Value );
1428 
1429 
1430         // --- Get the list of recently used functions ---
1431         Object aRecInst = xServiceManager.createInstance(
1432             "com.sun.star.sheet.RecentFunctions" );
1433         unoidl.com.sun.star.sheet.XRecentFunctions xRecFunc =
1434             (unoidl.com.sun.star.sheet.XRecentFunctions) aRecInst;
1435         int[] nRecentIds = xRecFunc.getRecentFunctionIds();
1436 
1437 
1438         // --- Get the names for these functions ---
1439         Object aDescInst = xServiceManager.createInstance(
1440             "com.sun.star.sheet.FunctionDescriptions" );
1441         unoidl.com.sun.star.sheet.XFunctionDescriptions xFuncDesc =
1442             (unoidl.com.sun.star.sheet.XFunctionDescriptions) aDescInst;
1443         Console.Write("Recently used functions: ");
1444         for (int nFunction=0; nFunction<nRecentIds.Length; nFunction++)
1445         {
1446             unoidl.com.sun.star.beans.PropertyValue[] aProperties =
1447                 xFuncDesc.getById( nRecentIds[nFunction] );
1448             for (int nProp=0; nProp<aProperties.Length; nProp++)
1449                 if ( aProperties[nProp].Name.Equals( "Name" ) )
1450                     Console.Write( aProperties[nProp].Value + " " );
1451         }
1452         Console.WriteLine();
1453     }
1454 
1455 // ________________________________________________________________
1456 
1457     private void doApplicationSettingsSamples()
1458     {
1459         Console.WriteLine( "\n*** Samples for application settings ***\n" );
1460         unoidl.com.sun.star.lang.XMultiServiceFactory xServiceManager =
1461             getServiceManager();
1462 
1463 
1464         // --- Get the user defined sort lists ---
1465         Object aSettings = xServiceManager.createInstance(
1466             "com.sun.star.sheet.GlobalSheetSettings" );
1467         unoidl.com.sun.star.beans.XPropertySet xPropSet =
1468             (unoidl.com.sun.star.beans.XPropertySet) aSettings;
1469         String[] aEntries = (String [])
1470             xPropSet.getPropertyValue( "UserLists" ).Value;
1471         Console.WriteLine("User defined sort lists:");
1472         for ( int i=0; i<aEntries.Length; i++ )
1473             Console.WriteLine( aEntries[i] );
1474     }
1475 
1476 // ________________________________________________________________
1477 
1478 }
1479