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 #include "AccessibleCellBase.hxx"
29 #include "attrib.hxx"
30 #include "scitems.hxx"
31 #include "miscuno.hxx"
32 #include "document.hxx"
33 #include "docfunc.hxx"
34 #include "cell.hxx"
35 #include "unoguard.hxx"
36 #include "scresid.hxx"
37 #ifndef SC_SC_HRC
38 #include "sc.hrc"
39 #endif
40 #include "unonames.hxx"
41 #include "detfunc.hxx"
42 #include "chgtrack.hxx"
43 #ifndef _COM_SUN_STAR_ACCESSIBILITY_XACCESSIBLEROLE_HPP_
44 #include <com/sun/star/accessibility/AccessibleRole.hpp>
45 #endif
46 #ifndef _COM_SUN_STAR_ACCESSIBILITY_XACCESSIBLESTATETYPE_HPP_
47 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
48 #endif
49 #include <com/sun/star/sheet/XSpreadsheetDocument.hpp>
50 #include <com/sun/star/sheet/XSpreadsheet.hpp>
51 #include <tools/debug.hxx>
52 #include <editeng/brshitem.hxx>
53 #include <rtl/uuid.h>
54 #include <comphelper/sequence.hxx>
55 #include <sfx2/objsh.hxx>
56 #include <com/sun/star/sheet/XSheetAnnotation.hpp>
57 #include <com/sun/star/sheet/XSheetAnnotationAnchor.hpp>
58 #include <com/sun/star/text/XSimpleText.hpp>
59 
60 #include <float.h>
61 
62 using namespace	::com::sun::star;
63 using namespace	::com::sun::star::accessibility;
64 
65 //=====  internal  ============================================================
66 
ScAccessibleCellBase(const uno::Reference<XAccessible> & rxParent,ScDocument * pDoc,const ScAddress & rCellAddress,sal_Int32 nIndex)67 ScAccessibleCellBase::ScAccessibleCellBase(
68         const uno::Reference<XAccessible>& rxParent,
69 		ScDocument* pDoc,
70 		const ScAddress& rCellAddress,
71 		sal_Int32 nIndex)
72 	:
73 	ScAccessibleContextBase(rxParent, AccessibleRole::TABLE_CELL),
74 	maCellAddress(rCellAddress),
75 	mpDoc(pDoc),
76 	mnIndex(nIndex)
77 {
78 }
79 
~ScAccessibleCellBase()80 ScAccessibleCellBase::~ScAccessibleCellBase()
81 {
82 }
83 
84 	//=====  XAccessibleComponent  ============================================
85 
isVisible()86 sal_Bool SAL_CALL ScAccessibleCellBase::isVisible(  )
87 		throw (uno::RuntimeException)
88 {
89  	ScUnoGuard aGuard;
90     IsObjectValid();
91 	// test whether the cell is hidden (column/row - hidden/filtered)
92 	sal_Bool bVisible(sal_True);
93 	if (mpDoc)
94 	{
95         bool bColHidden = mpDoc->ColHidden(maCellAddress.Col(), maCellAddress.Tab());
96         bool bRowHidden = mpDoc->RowHidden(maCellAddress.Row(), maCellAddress.Tab());
97         bool bColFiltered = mpDoc->ColFiltered(maCellAddress.Col(), maCellAddress.Tab());
98         bool bRowFiltered = mpDoc->RowFiltered(maCellAddress.Row(), maCellAddress.Tab());
99 
100         if (bColHidden || bColFiltered || bRowHidden || bRowFiltered)
101 			bVisible = sal_False;
102 	}
103 	return bVisible;
104 }
105 
getForeground()106 sal_Int32 SAL_CALL ScAccessibleCellBase::getForeground()
107     throw (uno::RuntimeException)
108 {
109     ScUnoGuard aGuard;
110     IsObjectValid();
111     sal_Int32 nColor(0);
112     if (mpDoc)
113     {
114         SfxObjectShell* pObjSh = mpDoc->GetDocumentShell();
115         if ( pObjSh )
116         {
117             uno::Reference <sheet::XSpreadsheetDocument> xSpreadDoc( pObjSh->GetModel(), uno::UNO_QUERY );
118             if ( xSpreadDoc.is() )
119             {
120                 uno::Reference<sheet::XSpreadsheets> xSheets = xSpreadDoc->getSheets();
121                 uno::Reference<container::XIndexAccess> xIndex( xSheets, uno::UNO_QUERY );
122                 if ( xIndex.is() )
123                 {
124                     uno::Any aTable = xIndex->getByIndex(maCellAddress.Tab());
125                     uno::Reference<sheet::XSpreadsheet> xTable;
126                     if (aTable>>=xTable)
127                     {
128                         uno::Reference<table::XCell> xCell = xTable->getCellByPosition(maCellAddress.Col(), maCellAddress.Row());
129                         if (xCell.is())
130                         {
131                             uno::Reference<beans::XPropertySet> xCellProps(xCell, uno::UNO_QUERY);
132                             if (xCellProps.is())
133                             {
134                                 uno::Any aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_CCOLOR)));
135                                 aAny >>= nColor;
136                             }
137                         }
138                     }
139                 }
140             }
141         }
142     }
143     return nColor;
144 }
145 
getBackground()146 sal_Int32 SAL_CALL ScAccessibleCellBase::getBackground()
147     throw (uno::RuntimeException)
148 {
149     ScUnoGuard aGuard;
150     IsObjectValid();
151     sal_Int32 nColor(0);
152 
153     if (mpDoc)
154     {
155         SfxObjectShell* pObjSh = mpDoc->GetDocumentShell();
156         if ( pObjSh )
157         {
158             uno::Reference <sheet::XSpreadsheetDocument> xSpreadDoc( pObjSh->GetModel(), uno::UNO_QUERY );
159             if ( xSpreadDoc.is() )
160             {
161                 uno::Reference<sheet::XSpreadsheets> xSheets = xSpreadDoc->getSheets();
162                 uno::Reference<container::XIndexAccess> xIndex( xSheets, uno::UNO_QUERY );
163                 if ( xIndex.is() )
164                 {
165                     uno::Any aTable = xIndex->getByIndex(maCellAddress.Tab());
166                     uno::Reference<sheet::XSpreadsheet> xTable;
167                     if (aTable>>=xTable)
168                     {
169                         uno::Reference<table::XCell> xCell = xTable->getCellByPosition(maCellAddress.Col(), maCellAddress.Row());
170                         if (xCell.is())
171                         {
172                             uno::Reference<beans::XPropertySet> xCellProps(xCell, uno::UNO_QUERY);
173                             if (xCellProps.is())
174                             {
175                                 uno::Any aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_CELLBACK)));
176                                 aAny >>= nColor;
177                             }
178                         }
179                     }
180                 }
181             }
182         }
183     }
184 
185     return nColor;
186 }
187 
188 	//=====  XInterface  =====================================================
189 
queryInterface(uno::Type const & rType)190 uno::Any SAL_CALL ScAccessibleCellBase::queryInterface( uno::Type const & rType )
191 	throw (uno::RuntimeException)
192 {
193 	uno::Any aAny (ScAccessibleCellBaseImpl::queryInterface(rType));
194 	return aAny.hasValue() ? aAny : ScAccessibleContextBase::queryInterface(rType);
195 }
196 
acquire()197 void SAL_CALL ScAccessibleCellBase::acquire()
198 	throw ()
199 {
200 	ScAccessibleContextBase::acquire();
201 }
202 
release()203 void SAL_CALL ScAccessibleCellBase::release()
204 	throw ()
205 {
206 	ScAccessibleContextBase::release();
207 }
208 
209 	//=====  XAccessibleContext  ==============================================
210 
211 sal_Int32
getAccessibleIndexInParent(void)212 	ScAccessibleCellBase::getAccessibleIndexInParent(void)
213         throw (uno::RuntimeException)
214 {
215 	ScUnoGuard aGuard;
216     IsObjectValid();
217 	return mnIndex;
218 }
219 
220 ::rtl::OUString SAL_CALL
createAccessibleDescription(void)221     ScAccessibleCellBase::createAccessibleDescription(void)
222     throw (uno::RuntimeException)
223 {
224 	rtl::OUString sDescription = String(ScResId(STR_ACC_CELL_DESCR));
225 
226 	return sDescription;
227 }
228 
229 ::rtl::OUString SAL_CALL
createAccessibleName(void)230     ScAccessibleCellBase::createAccessibleName(void)
231     throw (uno::RuntimeException)
232 {
233 	String sAddress;
234 	// Document not needed, because only the cell address, but not the tablename is needed
235 	// always us OOO notation
236 	maCellAddress.Format( sAddress, SCA_VALID, NULL );
237 	//sName.SearchAndReplaceAscii("%1", sAddress);
238     /*  #i65103# ZoomText merges cell address and contents, e.g. if value 2 is
239         contained in cell A1, ZT reads "cell A twelve" instead of "cell A1 - 2".
240         Simple solution: Append a space character to the cell address. */
241     return rtl::OUString(sAddress);
242 }
243 
244 	//=====  XAccessibleValue  ================================================
245 
246 uno::Any SAL_CALL
getCurrentValue()247 	ScAccessibleCellBase::getCurrentValue(  )
248 	throw (uno::RuntimeException)
249 {
250  	ScUnoGuard aGuard;
251     IsObjectValid();
252 	uno::Any aAny;
253 	if (mpDoc)
254 	{
255 		String valStr;
256 		mpDoc->GetString(maCellAddress.Col(),maCellAddress.Row(),maCellAddress.Tab(), valStr);
257 		aAny <<= rtl::OUString(valStr);
258 	}
259 	return aAny;
260 }
261 
262 sal_Bool SAL_CALL
setCurrentValue(const uno::Any & aNumber)263 	ScAccessibleCellBase::setCurrentValue( const uno::Any& aNumber )
264 	throw (uno::RuntimeException)
265 {
266  	ScUnoGuard aGuard;
267     IsObjectValid();
268 	double fValue = 0;
269 	sal_Bool bResult(sal_False);
270 	if((aNumber >>= fValue) && mpDoc && mpDoc->GetDocumentShell())
271 	{
272 		uno::Reference<XAccessibleStateSet> xParentStates;
273 		if (getAccessibleParent().is())
274 		{
275 			uno::Reference<XAccessibleContext> xParentContext = getAccessibleParent()->getAccessibleContext();
276 			xParentStates = xParentContext->getAccessibleStateSet();
277 		}
278 		if (IsEditable(xParentStates))
279 		{
280 			ScDocShell* pDocShell = (ScDocShell*) mpDoc->GetDocumentShell();
281 			ScDocFunc aFunc(*pDocShell);
282 			bResult = aFunc.PutCell( maCellAddress, new ScValueCell(fValue), sal_True );
283 		}
284 	}
285 	return bResult;
286 }
287 
288 uno::Any SAL_CALL
getMaximumValue()289 	ScAccessibleCellBase::getMaximumValue(  )
290 	throw (uno::RuntimeException)
291 {
292 	uno::Any aAny;
293 	aAny <<= DBL_MAX;
294 
295 	return aAny;
296 }
297 
298 uno::Any SAL_CALL
getMinimumValue()299 	ScAccessibleCellBase::getMinimumValue(  )
300 	throw (uno::RuntimeException)
301 {
302 	uno::Any aAny;
303 	aAny <<= -DBL_MAX;
304 
305 	return aAny;
306 }
307 
308 	//=====  XServiceInfo  ====================================================
309 
getImplementationName(void)310 ::rtl::OUString SAL_CALL ScAccessibleCellBase::getImplementationName(void)
311         throw (uno::RuntimeException)
312 {
313 	return rtl::OUString(RTL_CONSTASCII_USTRINGPARAM ("ScAccessibleCellBase"));
314 }
315 
316 	//=====  XTypeProvider  ===================================================
317 
getTypes()318 uno::Sequence< uno::Type > SAL_CALL ScAccessibleCellBase::getTypes()
319 		throw (uno::RuntimeException)
320 {
321 	return comphelper::concatSequences(ScAccessibleCellBaseImpl::getTypes(), ScAccessibleContextBase::getTypes());
322 }
323 
324 uno::Sequence<sal_Int8> SAL_CALL
getImplementationId(void)325 	ScAccessibleCellBase::getImplementationId(void)
326     throw (uno::RuntimeException)
327 {
328     ScUnoGuard aGuard;
329     IsObjectValid();
330 	static uno::Sequence<sal_Int8> aId;
331 	if (aId.getLength() == 0)
332 	{
333 		aId.realloc (16);
334 		rtl_createUuid (reinterpret_cast<sal_uInt8 *>(aId.getArray()), 0, sal_True);
335 	}
336 	return aId;
337 }
338 
IsEditable(const uno::Reference<XAccessibleStateSet> & rxParentStates)339 sal_Bool ScAccessibleCellBase::IsEditable(
340 	const uno::Reference<XAccessibleStateSet>& rxParentStates)
341 {
342 	sal_Bool bEditable(sal_False);
343 	if (rxParentStates.is() && rxParentStates->contains(AccessibleStateType::EDITABLE))
344 		bEditable = sal_True;
345 	return bEditable;
346 }
GetNote(void)347 ::rtl::OUString SAL_CALL ScAccessibleCellBase::GetNote(void)
348 								throw (::com::sun::star::uno::RuntimeException)
349 {
350 	ScUnoGuard aGuard;
351     IsObjectValid();
352     rtl::OUString msNote;
353     if (mpDoc)
354     {
355         SfxObjectShell* pObjSh = mpDoc->GetDocumentShell();
356         if ( pObjSh )
357         {
358             uno::Reference <sheet::XSpreadsheetDocument> xSpreadDoc( pObjSh->GetModel(), uno::UNO_QUERY );
359             if ( xSpreadDoc.is() )
360             {
361                 uno::Reference<sheet::XSpreadsheets> xSheets = xSpreadDoc->getSheets();
362                 uno::Reference<container::XIndexAccess> xIndex( xSheets, uno::UNO_QUERY );
363                 if ( xIndex.is() )
364                 {
365                     uno::Any aTable = xIndex->getByIndex(maCellAddress.Tab());
366                     uno::Reference<sheet::XSpreadsheet> xTable;
367                     if (aTable>>=xTable)
368                     {
369                         uno::Reference<table::XCell> xCell = xTable->getCellByPosition(maCellAddress.Col(), maCellAddress.Row());
370                         if (xCell.is())
371                         {
372 							uno::Reference <sheet::XSheetAnnotationAnchor> xAnnotationAnchor ( xCell, uno::UNO_QUERY);
373 							if(xAnnotationAnchor.is())
374 							{
375 								uno::Reference <sheet::XSheetAnnotation> xSheetAnnotation = xAnnotationAnchor->getAnnotation();
376 								if (xSheetAnnotation.is())
377 								{
378 									uno::Reference <text::XSimpleText> xText (xSheetAnnotation, uno::UNO_QUERY);
379 									if (xText.is())
380 									{
381 										msNote = xText->getString();
382 									}
383 								}
384 							}
385                         }
386                     }
387                 }
388             }
389         }
390     }
391 	return msNote;
392 }
393 #ifndef _COM_SUN_STAR_TABLE_SHADOWFORMAT_HPP_
394 #include <com/sun/star/table/ShadowFormat.hpp>
395 #endif
getShadowAttrs(void)396 ::rtl::OUString SAL_CALL ScAccessibleCellBase::getShadowAttrs(void)
397 										throw (::com::sun::star::uno::RuntimeException)
398 {
399 	ScUnoGuard aGuard;
400 	IsObjectValid();
401 	table::ShadowFormat aShadowFmt;
402 	if (mpDoc)
403 	{
404 		SfxObjectShell* pObjSh = mpDoc->GetDocumentShell();
405 		if ( pObjSh )
406 		{
407 			uno::Reference <sheet::XSpreadsheetDocument> xSpreadDoc( pObjSh->GetModel(), uno::UNO_QUERY );
408 			if ( xSpreadDoc.is() )
409 			{
410 				uno::Reference<sheet::XSpreadsheets> xSheets = xSpreadDoc->getSheets();
411 				uno::Reference<container::XIndexAccess> xIndex( xSheets, uno::UNO_QUERY );
412 				if ( xIndex.is() )
413 				{
414 					uno::Any aTable = xIndex->getByIndex(maCellAddress.Tab());
415 					uno::Reference<sheet::XSpreadsheet> xTable;
416 					if (aTable>>=xTable)
417 					{
418 						uno::Reference<table::XCell> xCell = xTable->getCellByPosition(maCellAddress.Col(), maCellAddress.Row());
419 						if (xCell.is())
420 						{
421 							uno::Reference<beans::XPropertySet> xCellProps(xCell, uno::UNO_QUERY);
422 							if (xCellProps.is())
423 							{
424 								uno::Any aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_SHADOW)));
425 								aAny >>= aShadowFmt;
426 							}
427 						}
428 					}
429 				}
430 			}
431 		}
432 	}
433 	//construct shadow attributes string
434 	rtl::OUString sShadowAttrs( RTL_CONSTASCII_USTRINGPARAM("Shadow:") );
435 	rtl::OUString sInnerSplit( RTL_CONSTASCII_USTRINGPARAM(",") );
436 	rtl::OUString sOuterSplit( RTL_CONSTASCII_USTRINGPARAM(";") );
437 	sal_Int32 nLocationVal = 0;
438 	switch( aShadowFmt.Location )
439 	{
440 	case table::ShadowLocation_TOP_LEFT:
441 		nLocationVal = 1;
442 		break;
443 	case table::ShadowLocation_TOP_RIGHT:
444 		nLocationVal = 2;
445 		break;
446 	case table::ShadowLocation_BOTTOM_LEFT:
447 		nLocationVal = 3;
448 		break;
449 	case table::ShadowLocation_BOTTOM_RIGHT:
450 		nLocationVal = 4;
451 		break;
452 	default:
453 		break;
454 	}
455 	//if there is no shadow property for the cell
456 	if ( nLocationVal == 0 )
457 	{
458 		sShadowAttrs += sOuterSplit;
459 		return sShadowAttrs;
460 	}
461 	//else return all the shadow properties
462 	sShadowAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Location=") );
463 	sShadowAttrs += rtl::OUString::valueOf( (sal_Int32)nLocationVal );
464 	sShadowAttrs += sInnerSplit;
465 	sShadowAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("ShadowWidth=") );
466 	sShadowAttrs += rtl::OUString::valueOf( (sal_Int32)aShadowFmt.ShadowWidth ) ;
467 	sShadowAttrs += sInnerSplit;
468 	sShadowAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("IsTransparent=") );
469 	sShadowAttrs += rtl::OUString::valueOf( (sal_Bool)aShadowFmt.IsTransparent ) ;
470 	sShadowAttrs += sInnerSplit;
471 	sShadowAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Color=") );
472 	sShadowAttrs += rtl::OUString::valueOf( (sal_Int32)aShadowFmt.Color );
473 	sShadowAttrs += sOuterSplit;
474 	return sShadowAttrs;
475 }
476 #ifndef _COM_SUN_STAR_TABLE_BORDERLINE_HPP_
477 #include <com/sun/star/table/BorderLine.hpp>
478 #endif
getBorderAttrs(void)479 ::rtl::OUString SAL_CALL ScAccessibleCellBase::getBorderAttrs(void)
480 										throw (::com::sun::star::uno::RuntimeException)
481 {
482 	ScUnoGuard aGuard;
483 	IsObjectValid();
484 	table::BorderLine aTopBorder;
485 	table::BorderLine aBottomBorder;
486 	table::BorderLine aLeftBorder;
487 	table::BorderLine aRightBorder;
488 	if (mpDoc)
489 	{
490 		SfxObjectShell* pObjSh = mpDoc->GetDocumentShell();
491 		if ( pObjSh )
492 		{
493 			uno::Reference <sheet::XSpreadsheetDocument> xSpreadDoc( pObjSh->GetModel(), uno::UNO_QUERY );
494 			if ( xSpreadDoc.is() )
495 			{
496 				uno::Reference<sheet::XSpreadsheets> xSheets = xSpreadDoc->getSheets();
497 				uno::Reference<container::XIndexAccess> xIndex( xSheets, uno::UNO_QUERY );
498 				if ( xIndex.is() )
499 				{
500 					uno::Any aTable = xIndex->getByIndex(maCellAddress.Tab());
501 					uno::Reference<sheet::XSpreadsheet> xTable;
502 					if (aTable>>=xTable)
503 					{
504 						uno::Reference<table::XCell> xCell = xTable->getCellByPosition(maCellAddress.Col(), maCellAddress.Row());
505 						if (xCell.is())
506 						{
507 							uno::Reference<beans::XPropertySet> xCellProps(xCell, uno::UNO_QUERY);
508 							if (xCellProps.is())
509 							{
510 								uno::Any aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_TOPBORDER)));
511 								aAny >>= aTopBorder;
512 								aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_BOTTBORDER)));
513 								aAny >>= aBottomBorder;
514 								aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_LEFTBORDER)));
515 								aAny >>= aLeftBorder;
516 								aAny = xCellProps->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_RIGHTBORDER)));
517 								aAny >>= aRightBorder;
518 							}
519 						}
520 					}
521 				}
522 			}
523 		}
524 	}
525 
526 	Color aColor;
527 	sal_Bool bIn = mpDoc ? mpDoc->IsCellInChangeTrack(maCellAddress,&aColor) : sal_False;
528 	if (bIn)
529 	{
530 		aTopBorder.Color = aColor.GetColor();
531 		aBottomBorder.Color = aColor.GetColor();
532 		aLeftBorder.Color = aColor.GetColor();
533 		aRightBorder.Color = aColor.GetColor();
534 		aTopBorder.OuterLineWidth =2;
535 		aBottomBorder.OuterLineWidth =2;
536 		aLeftBorder.OuterLineWidth =2;
537 		aRightBorder.OuterLineWidth =2;
538 	}
539 
540 	//construct border attributes string
541 	rtl::OUString sBorderAttrs;
542 	rtl::OUString sInnerSplit( RTL_CONSTASCII_USTRINGPARAM(",") );
543 	rtl::OUString sOuterSplit( RTL_CONSTASCII_USTRINGPARAM(";") );
544 	//top border
545 	//if top of the cell has no border
546 	if ( aTopBorder.InnerLineWidth == 0 && aTopBorder.OuterLineWidth == 0 )
547 	{
548 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("TopBorder:;") );
549 	}
550 	else//add all the border properties to the return string.
551 	{
552 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("TopBorder:Color=") );
553 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aTopBorder.Color );
554 		sBorderAttrs += sInnerSplit;
555 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("InnerLineWidth=") );
556 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aTopBorder.InnerLineWidth );
557 		sBorderAttrs += sInnerSplit;
558 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("OuterLineWidth=") );
559 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aTopBorder.OuterLineWidth );
560 		sBorderAttrs += sInnerSplit;
561 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("LineDistance=") );
562 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aTopBorder.LineDistance );
563 		sBorderAttrs += sOuterSplit;
564 	}
565 	//bottom border
566 	if ( aBottomBorder.InnerLineWidth == 0 && aBottomBorder.OuterLineWidth == 0 )
567 	{
568 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("BottomBorde:;") );
569 	}
570 	else
571 	{
572 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("BottomBorder:Color=") );
573 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aBottomBorder.Color );
574 		sBorderAttrs += sInnerSplit;
575 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("InnerLineWidth=") );
576 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aBottomBorder.InnerLineWidth );
577 		sBorderAttrs += sInnerSplit;
578 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("OuterLineWidth=") );
579 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aBottomBorder.OuterLineWidth );
580 		sBorderAttrs += sInnerSplit;
581 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("LineDistance=") );
582 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aBottomBorder.LineDistance );
583 		sBorderAttrs += sOuterSplit;
584 	}
585 	//left border
586 	if ( aLeftBorder.InnerLineWidth == 0 && aLeftBorder.OuterLineWidth == 0 )
587 	{
588 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("LeftBorder:;") );
589 	}
590 	else
591 	{
592 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("LeftBorder:Color=") );
593 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aLeftBorder.Color );
594 		sBorderAttrs += sInnerSplit;
595 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("InnerLineWidth=") );
596 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aLeftBorder.InnerLineWidth );
597 		sBorderAttrs += sInnerSplit;
598 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("OuterLineWidth=") );
599 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aLeftBorder.OuterLineWidth );
600 		sBorderAttrs += sInnerSplit;
601 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("LineDistance=") );
602 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aLeftBorder.LineDistance );
603 		sBorderAttrs += sOuterSplit;
604 	}
605 	//right border
606 	if ( aRightBorder.InnerLineWidth == 0 && aRightBorder.OuterLineWidth == 0 )
607 	{
608 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("RightBorder:;") );
609 	}
610 	else
611 	{
612 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("RightBorder:Color=") );
613 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aRightBorder.Color );
614 		sBorderAttrs += sInnerSplit;
615 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("InnerLineWidth=") );
616 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aRightBorder.InnerLineWidth );
617 		sBorderAttrs += sInnerSplit;
618 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("OuterLineWidth=") );
619 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aRightBorder.OuterLineWidth );
620 		sBorderAttrs += sInnerSplit;
621 		sBorderAttrs += rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("LineDistance=") );
622 		sBorderAttrs += rtl::OUString::valueOf( (sal_Int32)aRightBorder.LineDistance );
623 		sBorderAttrs += sOuterSplit;
624 	}
625 	return sBorderAttrs;
626 }
627 //end of cell attributes
628 
GetAllDisplayNote(void)629 ::rtl::OUString SAL_CALL ScAccessibleCellBase::GetAllDisplayNote(void)
630 	throw (::com::sun::star::uno::RuntimeException)
631 {
632 	::rtl::OUString strNote;
633 	String strTrackText;
634 	if (mpDoc)
635 	{
636 		sal_Bool bLeftedge=sal_False;
637 		mpDoc->GetCellChangeTrackNote(maCellAddress,strTrackText,bLeftedge);
638 	}
639 	if (strTrackText.Len() > 0 )
640 	{
641 		ScDetectiveFunc::AppendChangTrackNoteSeparator(strTrackText);
642 		strNote = strTrackText;
643 	}
644 	strNote += GetNote();
645 	return strNote;
646 }
647