1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: trvltbl.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_sw.hxx"
33 #include <hintids.hxx>
35 #include <vcl/svapp.hxx>
36 #include <svx/protitem.hxx>
40 #include <editsh.hxx> //EndAllAction gibts nur an der EditShell
42 #include <swtable.hxx>
50 #include <shellres.hxx>
51 #include <cellatr.hxx>
52 #include <cellfrm.hxx>
56 // setze Crsr in die naechsten/vorherigen Celle
57 BOOL
SwCrsrShell::GoNextCell( BOOL bAppendLine
)
60 const SwTableNode
* pTblNd
= 0;
62 if( IsTableMode() || 0 != ( pTblNd
= IsCrsrInTbl() ))
64 SwCursor
* pCrsr
= pTblCrsr
? pTblCrsr
: pCurCrsr
;
65 SwCallLink
aLk( *this ); // Crsr-Moves ueberwachen,
68 // Check if we have to move the cursor to a covered cell before
70 const SwNode
* pTableBoxStartNode
= pCrsr
->GetNode()->FindTableBoxStartNode();
71 const SwTableBox
* pTableBox
= 0;
73 if ( pCrsr
->GetCrsrRowSpanOffset() )
75 pTableBox
= pTableBoxStartNode
->GetTblBox();
76 if ( pTableBox
->getRowSpan() > 1 )
79 pTblNd
= IsCrsrInTbl();
80 pTableBox
= & pTableBox
->FindEndOfRowSpan( pTblNd
->GetTable(),
81 (USHORT
)(pTableBox
->getRowSpan() + pCrsr
->GetCrsrRowSpanOffset() ) );
82 pTableBoxStartNode
= pTableBox
->GetSttNd();
86 SwNodeIndex
aCellStt( *pTableBoxStartNode
->EndOfSectionNode(), 1 );
88 // folgt nach dem EndNode der Cell ein weiterer StartNode, dann
89 // gibt es auch eine naechste Celle
91 if( !aCellStt
.GetNode().IsStartNode() )
93 if( pCrsr
->HasMark() || !bAppendLine
)
97 // auf besonderen Wunsch: keine Line mehr vorhanden, dann
98 // mache doch eine neue:
100 pTableBox
= pTblNd
->GetTable().GetTblBox(
101 pCrsr
->GetPoint()->nNode
.GetNode().
102 StartOfSectionIndex() );
104 ASSERT( pTableBox
, "Box steht nicht in dieser Tabelle" );
107 //Das Dokument veraendert sich evtl. ohne Action wuerden die Sichten
108 //nichts mitbekommen.
109 ((SwEditShell
*)this)->StartAllAction();
110 bRet
= pDoc
->InsertRow( pTblNd
->GetTable().
111 SelLineFromBox( pTableBox
, aBoxes
, FALSE
));
112 ((SwEditShell
*)this)->EndAllAction();
115 if( bRet
&& 0 != ( bRet
= pCrsr
->GoNextCell() ))
116 UpdateCrsr(); // und den akt. Updaten
122 BOOL
SwCrsrShell::GoPrevCell()
125 const SwTableNode
* pTblNd
;
126 if( IsTableMode() || 0 != ( pTblNd
= IsCrsrInTbl() ))
128 SwCursor
* pCrsr
= pTblCrsr
? pTblCrsr
: pCurCrsr
;
129 SwCallLink
aLk( *this ); // Crsr-Moves ueberwachen,
130 bRet
= pCrsr
->GoPrevCell();
132 UpdateCrsr(); // und den akt. Updaten
137 const SwFrm
* lcl_FindMostUpperCellFrm( const SwFrm
* pFrm
)
140 ( !pFrm
->IsCellFrm() ||
141 !pFrm
->GetUpper()->GetUpper()->IsTabFrm() ||
142 pFrm
->GetUpper()->GetUpper()->GetUpper()->IsInTab() ) )
144 pFrm
= pFrm
->GetUpper();
149 BOOL
SwCrsrShell::_SelTblRowOrCol( bool bRow
, bool bRowSimple
)
151 // pruefe ob vom aktuellen Crsr der SPoint/Mark in einer Tabelle stehen
152 SwFrm
*pFrm
= GetCurrFrm();
153 if( !pFrm
->IsInTab() )
156 const SwTabFrm
* pTabFrm
= pFrm
->FindTabFrm();
157 const SwTabFrm
* pMasterTabFrm
= pTabFrm
->IsFollow() ? pTabFrm
->FindMaster( true ) : pTabFrm
;
158 const SwTable
* pTable
= pTabFrm
->GetTable();
160 SET_CURR_SHELL( this );
162 const SwTableBox
* pStt
= 0;
163 const SwTableBox
* pEnd
= 0;
165 // lasse ueber das Layout die Boxen suchen
167 SwTblSearchType eType
= bRow
? nsSwTblSearchType::TBLSEARCH_ROW
: nsSwTblSearchType::TBLSEARCH_COL
;
168 const bool bCheckProtected
= !IsReadOnlyAvailable();
170 if( bCheckProtected
)
171 eType
= (SwTblSearchType
)(eType
| nsSwTblSearchType::TBLSEARCH_PROTECT
);
175 GetTblSel( *this, aBoxes
, eType
);
177 if( !aBoxes
.Count() )
181 pEnd
= aBoxes
[aBoxes
.Count() - 1];
183 // --> FME 2004-07-30 #i32329# Enhanced table selection
184 else if ( pTable
->IsNewModel() )
186 const SwShellCrsr
*pCrsr
= _GetCrsr();
187 SwTable::SearchType eSearchType
= bRow
? SwTable::SEARCH_ROW
: SwTable::SEARCH_COL
;
188 pTable
->CreateSelection( *pCrsr
, aBoxes
, eSearchType
, bCheckProtected
);
189 if( !aBoxes
.Count() )
193 pEnd
= aBoxes
[aBoxes
.Count() - 1];
197 const SwShellCrsr
*pCrsr
= _GetCrsr();
198 const SwFrm
* pStartFrm
= pFrm
;
199 const SwCntntNode
*pCNd
= pCrsr
->GetCntntNode( FALSE
);
200 const SwFrm
* pEndFrm
= pCNd
? pCNd
->GetFrm( &pCrsr
->GetMkPos() ) : 0;
204 pStartFrm
= lcl_FindMostUpperCellFrm( pStartFrm
);
205 pEndFrm
= lcl_FindMostUpperCellFrm( pEndFrm
);
208 if ( !pStartFrm
|| !pEndFrm
)
211 const bool bVert
= pFrm
->ImplFindTabFrm()->IsVertical();
213 // If we select upwards it is sufficient to set pStt and pEnd
214 // to the first resp. last box of the selection obtained from
215 // GetTblSel. However, selecting downwards requires the frames
216 // located at the corners of the selection. This does not work
217 // for column selections in vertical tables:
218 const bool bSelectUp
= ( bVert
&& !bRow
) ||
219 *pCrsr
->GetPoint() <= *pCrsr
->GetMark();
221 GetTblSel( static_cast<const SwCellFrm
*>(pStartFrm
),
222 static_cast<const SwCellFrm
*>(pEndFrm
),
223 aBoxes
, bSelectUp
? 0 : &aCells
, eType
);
225 if( !aBoxes
.Count() || ( !bSelectUp
&& 4 != aCells
.Count() ) )
231 pEnd
= aBoxes
[aBoxes
.Count() - 1];
235 pStt
= aCells
[ bVert
? (bRow
? 0 : 3) : (bRow
? 2 : 1) ]->GetTabBox(); // will become point of table cursor
236 pEnd
= aCells
[ bVert
? (bRow
? 3 : 0) : (bRow
? 1 : 2) ]->GetTabBox(); // will become mark of table cursor
241 // noch kein Tabellen-Cursor vorhanden, dann erzeuge einen
244 pTblCrsr
= new SwShellTableCrsr( *this, *pCurCrsr
->GetPoint() );
245 pCurCrsr
->DeleteMark();
246 pCurCrsr
->SwSelPaintRects::Hide();
249 pTblCrsr
->DeleteMark();
251 // dann setze mal Anfang und Ende der Spalte
252 pTblCrsr
->GetPoint()->nNode
= *pEnd
->GetSttNd();
253 pTblCrsr
->Move( fnMoveForward
, fnGoCntnt
);
255 pTblCrsr
->GetPoint()->nNode
= *pStt
->GetSttNd()->EndOfSectionNode();
256 pTblCrsr
->Move( fnMoveBackward
, fnGoCntnt
);
258 // set PtPos 'close' to the reference table, otherwise we might get problems with the
259 // repeated headlines check in UpdateCrsr():
261 pTblCrsr
->GetPtPos() = pMasterTabFrm
->IsVertical() ? pMasterTabFrm
->Frm().TopRight() : pMasterTabFrm
->Frm().TopLeft();
263 UpdateCrsr(); // und den akt. Updaten
267 BOOL
SwCrsrShell::SelTbl()
269 // pruefe ob vom aktuellen Crsr der SPoint/Mark in einer Tabelle stehen
270 SwFrm
*pFrm
= GetCurrFrm();
271 if( !pFrm
->IsInTab() )
274 const SwTabFrm
*pTblFrm
= pFrm
->ImplFindTabFrm();
275 const SwTabFrm
* pMasterTabFrm
= pTblFrm
->IsFollow() ? pTblFrm
->FindMaster( true ) : pTblFrm
;
276 const SwTableNode
* pTblNd
= pTblFrm
->GetTable()->GetTableNode();
278 SET_CURR_SHELL( this );
282 pTblCrsr
= new SwShellTableCrsr( *this, *pCurCrsr
->GetPoint() );
283 pCurCrsr
->DeleteMark();
284 pCurCrsr
->SwSelPaintRects::Hide();
287 pTblCrsr
->DeleteMark();
288 pTblCrsr
->GetPoint()->nNode
= *pTblNd
;
289 pTblCrsr
->Move( fnMoveForward
, fnGoCntnt
);
291 // set MkPos 'close' to the master table, otherwise we might get problems with the
292 // repeated headlines check in UpdateCrsr():
293 pTblCrsr
->GetMkPos() = pMasterTabFrm
->IsVertical() ? pMasterTabFrm
->Frm().TopRight() : pMasterTabFrm
->Frm().TopLeft();
294 pTblCrsr
->GetPoint()->nNode
= *pTblNd
->EndOfSectionNode();
295 pTblCrsr
->Move( fnMoveBackward
, fnGoCntnt
);
296 UpdateCrsr(); // und den akt. Updaten
301 BOOL
SwCrsrShell::SelTblBox()
303 // if we're in a table, create a table cursor, and select the cell
304 // that the current cursor's point resides in
306 // search for start node of our table box. If not found, exit realy
307 const SwStartNode
* pStartNode
=
308 pCurCrsr
->GetPoint()->nNode
.GetNode().FindTableBoxStartNode();
311 // the old code checks whether we're in a table by asking the
312 // frame. This should yield the same result as searching for the
313 // table box start node, right?
314 SwFrm
*pFrm
= GetCurrFrm();
315 DBG_ASSERT( !pFrm
->IsInTab() == !(pStartNode
!= NULL
),
316 "Schroedinger's table: We're in a box, and also we aren't." );
319 if( pStartNode
== NULL
)
323 SET_CURR_SHELL( this );
325 // create a table cursor, if there isn't one already
328 pTblCrsr
= new SwShellTableCrsr( *this, *pCurCrsr
->GetPoint() );
329 pCurCrsr
->DeleteMark();
330 pCurCrsr
->SwSelPaintRects::Hide();
333 // select the complete box with our shiny new pTblCrsr
334 // 1. delete mark, and move point to first content node in box
335 // 2. set mark, and move point to last content node in box
338 pTblCrsr
->DeleteMark();
339 *(pTblCrsr
->GetPoint()) = SwPosition( *pStartNode
);
340 pTblCrsr
->Move( fnMoveForward
, fnGoNode
);
343 *(pTblCrsr
->GetPoint()) = SwPosition( *(pStartNode
->EndOfSectionNode()) );
344 pTblCrsr
->Move( fnMoveBackward
, fnGoNode
);
346 pTblCrsr
->Exchange();
348 // with some luck, UpdateCrsr() will now update everything that
355 // return the next non-protected cell inside a table
356 // rIdx - is on a table node
358 // true - Idx points to content in a suitable cell
359 // false - could not find a suitable cell
360 bool lcl_FindNextCell( SwNodeIndex
& rIdx
, BOOL bInReadOnly
)
362 // ueberpruefe geschuetzte Zellen
363 SwNodeIndex
aTmp( rIdx
, 2 ); // TableNode + StartNode
365 // the resulting cell should be in that table:
366 const SwTableNode
* pTblNd
= rIdx
.GetNode().GetTableNode();
370 ASSERT( false, "lcl_FindNextCell not celled with table start node!" )
374 const SwNode
* pTableEndNode
= pTblNd
->EndOfSectionNode();
376 SwNodes
& rNds
= aTmp
.GetNode().GetNodes();
377 SwCntntNode
* pCNd
= aTmp
.GetNode().GetCntntNode();
379 // no content node => go to next content node
381 pCNd
= rNds
.GoNext( &aTmp
);
387 SwCntntFrm
* pFrm
= pCNd
->GetFrm();
389 if ( 0 == pFrm
|| pCNd
->FindTableNode() != pTblNd
||
390 (!bInReadOnly
&& pFrm
->IsProtected() ) )
392 // we are not located inside a 'valid' cell. We have to continue searching...
394 // skip behind current section. This might be the end of the table cell
395 // or behind a inner section or or or...
396 aTmp
.Assign( *pCNd
->EndOfSectionNode(), 1 );
398 // loop to find a suitable cell...
401 SwNode
* pNd
= &aTmp
.GetNode();
403 // we break this loop if we reached the end of the table.
404 // to make this code even more robust, we also break if we are
405 // already behind the table end node:
406 if( pNd
== pTableEndNode
|| /*robust: */ pNd
->GetIndex() > pTableEndNode
->GetIndex() )
409 // ok, get the next content node:
410 pCNd
= aTmp
.GetNode().GetCntntNode();
412 pCNd
= rNds
.GoNext( &aTmp
);
418 // check if we have found a suitable table cell:
419 pFrm
= pCNd
->GetFrm();
421 if ( 0 != pFrm
&& pCNd
->FindTableNode() == pTblNd
&&
422 (bInReadOnly
|| !pFrm
->IsProtected() ) )
424 // finally, we have found a suitable table cell => set index and return
429 // continue behind the current section:
430 aTmp
.Assign( *pCNd
->EndOfSectionNode(), +1 );
438 // comments see lcl_FindNextCell
439 bool lcl_FindPrevCell( SwNodeIndex
& rIdx
, BOOL bInReadOnly
)
441 SwNodeIndex
aTmp( rIdx
, -2 ); // TableNode + EndNode
443 const SwNode
* pTableEndNode
= &rIdx
.GetNode();
444 const SwTableNode
* pTblNd
= pTableEndNode
->StartOfSectionNode()->GetTableNode();
448 ASSERT( false, "lcl_FindPrevCell not celled with table start node!" )
452 SwNodes
& rNds
= aTmp
.GetNode().GetNodes();
453 SwCntntNode
* pCNd
= aTmp
.GetNode().GetCntntNode();
456 pCNd
= rNds
.GoPrevious( &aTmp
);
461 SwCntntFrm
* pFrm
= pCNd
->GetFrm();
463 if( 0 == pFrm
|| pCNd
->FindTableNode() != pTblNd
||
464 (!bInReadOnly
&& pFrm
->IsProtected() ))
466 // skip before current section
467 aTmp
.Assign( *pCNd
->StartOfSectionNode(), -1 );
470 SwNode
* pNd
= &aTmp
.GetNode();
472 if( pNd
== pTblNd
|| pNd
->GetIndex() < pTblNd
->GetIndex() )
475 pCNd
= aTmp
.GetNode().GetCntntNode();
477 pCNd
= rNds
.GoPrevious( &aTmp
);
482 pFrm
= pCNd
->GetFrm();
484 if( 0 != pFrm
&& pCNd
->FindTableNode() == pTblNd
&&
485 (bInReadOnly
|| !pFrm
->IsProtected() ) )
488 return true; // Ok, nicht geschuetzt
490 aTmp
.Assign( *pCNd
->StartOfSectionNode(), - 1 );
499 BOOL
GotoPrevTable( SwPaM
& rCurCrsr
, SwPosTable fnPosTbl
,
502 SwNodeIndex
aIdx( rCurCrsr
.GetPoint()->nNode
);
504 SwTableNode
* pTblNd
= aIdx
.GetNode().FindTableNode();
507 // #i26532#: If we are inside a table, we may not go backward
508 // to the table start node, because we would miss any tables
509 // inside this table.
510 SwTableNode
* pInnerTblNd
= 0;
511 SwNodeIndex
aTmpIdx( aIdx
);
512 while( aTmpIdx
.GetIndex() &&
513 0 == ( pInnerTblNd
= aTmpIdx
.GetNode().StartOfSectionNode()->GetTableNode()) )
516 if( pInnerTblNd
== pTblNd
)
517 aIdx
.Assign( *pTblNd
, - 1 );
521 while( aIdx
.GetIndex() &&
522 0 == ( pTblNd
= aIdx
.GetNode().StartOfSectionNode()->GetTableNode()) )
525 if( pTblNd
) // gibt einen weiteren TableNode ?
527 if( fnPosTbl
== fnMoveForward
) // an Anfang ?
529 aIdx
= *aIdx
.GetNode().StartOfSectionNode();
530 if( !lcl_FindNextCell( aIdx
, bInReadOnly
))
532 // Tabelle ueberspringen
533 aIdx
.Assign( *pTblNd
, -1 );
539 // ueberpruefe geschuetzte Zellen
540 if( !lcl_FindNextCell( aIdx
, bInReadOnly
))
542 // Tabelle ueberspringen
543 aIdx
.Assign( *pTblNd
, -1 );
548 SwTxtNode
* pTxtNode
= aIdx
.GetNode().GetTxtNode();
551 rCurCrsr
.GetPoint()->nNode
= *pTxtNode
;
552 rCurCrsr
.GetPoint()->nContent
.Assign( pTxtNode
, fnPosTbl
== fnMoveBackward
?
564 BOOL
GotoNextTable( SwPaM
& rCurCrsr
, SwPosTable fnPosTbl
,
567 SwNodeIndex
aIdx( rCurCrsr
.GetPoint()->nNode
);
568 SwTableNode
* pTblNd
= aIdx
.GetNode().FindTableNode();
571 aIdx
.Assign( *pTblNd
->EndOfSectionNode(), 1 );
573 ULONG nLastNd
= rCurCrsr
.GetDoc()->GetNodes().Count() - 1;
575 while( aIdx
.GetIndex() < nLastNd
&&
576 0 == ( pTblNd
= aIdx
.GetNode().GetTableNode()) )
578 if( pTblNd
) // gibt einen weiteren TableNode ?
580 if( fnPosTbl
== fnMoveForward
) // an Anfang ?
582 if( !lcl_FindNextCell( aIdx
, bInReadOnly
))
584 // Tabelle ueberspringen
585 aIdx
.Assign( *pTblNd
->EndOfSectionNode(), + 1 );
591 aIdx
= *aIdx
.GetNode().EndOfSectionNode();
592 // ueberpruefe geschuetzte Zellen
593 if( !lcl_FindNextCell( aIdx
, bInReadOnly
))
595 // Tabelle ueberspringen
596 aIdx
.Assign( *pTblNd
->EndOfSectionNode(), + 1 );
601 SwTxtNode
* pTxtNode
= aIdx
.GetNode().GetTxtNode();
604 rCurCrsr
.GetPoint()->nNode
= *pTxtNode
;
605 rCurCrsr
.GetPoint()->nContent
.Assign( pTxtNode
, fnPosTbl
== fnMoveBackward
?
617 BOOL
GotoCurrTable( SwPaM
& rCurCrsr
, SwPosTable fnPosTbl
,
620 SwTableNode
* pTblNd
= rCurCrsr
.GetPoint()->nNode
.GetNode().FindTableNode();
624 SwTxtNode
* pTxtNode
= 0;
625 if( fnPosTbl
== fnMoveBackward
) // ans Ende der Tabelle
627 SwNodeIndex
aIdx( *pTblNd
->EndOfSectionNode() );
628 if( !lcl_FindPrevCell( aIdx
, bInReadOnly
))
630 pTxtNode
= aIdx
.GetNode().GetTxtNode();
634 SwNodeIndex
aIdx( *pTblNd
);
635 if( !lcl_FindNextCell( aIdx
, bInReadOnly
))
637 pTxtNode
= aIdx
.GetNode().GetTxtNode();
642 rCurCrsr
.GetPoint()->nNode
= *pTxtNode
;
643 rCurCrsr
.GetPoint()->nContent
.Assign( pTxtNode
, fnPosTbl
== fnMoveBackward
?
652 BOOL
SwCursor::MoveTable( SwWhichTable fnWhichTbl
, SwPosTable fnPosTbl
)
655 SwTableCursor
* pTblCrsr
= dynamic_cast<SwTableCursor
*>(this);
657 if( pTblCrsr
|| !HasMark() ) // nur wenn kein Mark oder ein TblCrsr
659 SwCrsrSaveState
aSaveState( *this );
660 bRet
= (*fnWhichTbl
)( *this, fnPosTbl
, IsReadOnlyAvailable() ) &&
661 !IsSelOvr( nsSwCursorSelOverFlags::SELOVER_CHECKNODESSECTION
|
662 nsSwCursorSelOverFlags::SELOVER_TOGGLE
);
667 BOOL
SwCrsrShell::MoveTable( SwWhichTable fnWhichTbl
, SwPosTable fnPosTbl
)
669 SwCallLink
aLk( *this ); // Crsr-Moves ueberwachen, evt. Link callen
671 SwShellCrsr
* pCrsr
= pTblCrsr
? pTblCrsr
: pCurCrsr
;
672 BOOL bCheckPos
, bRet
;
674 xub_StrLen nPtCnt
= 0;
676 if( !pTblCrsr
&& pCurCrsr
->HasMark() ) // wenn Mark und kein TblCrsr,
678 // dann auf jedenfall in den Tabellen-Modus schalten
679 pTblCrsr
= new SwShellTableCrsr( *this, *pCurCrsr
->GetPoint() );
680 pCurCrsr
->DeleteMark();
681 pCurCrsr
->SwSelPaintRects::Hide();
689 nPtNd
= pCrsr
->GetPoint()->nNode
.GetIndex();
690 nPtCnt
= pCrsr
->GetPoint()->nContent
.GetIndex();
693 bRet
= pCrsr
->MoveTable( fnWhichTbl
, fnPosTbl
);
697 //JP 28.10.97: Bug 45028 - die "oberste" Position setzen fuer
698 // wiederholte Kopfzeilen
699 pCrsr
->GetPtPos() = Point();
701 UpdateCrsr(SwCrsrShell::SCROLLWIN
|SwCrsrShell::CHKRANGE
|SwCrsrShell::READONLY
);
704 pCrsr
->GetPoint()->nNode
.GetIndex() == nPtNd
&&
705 pCrsr
->GetPoint()->nContent
.GetIndex() == nPtCnt
)
712 BOOL
SwCrsrShell::IsTblComplex() const
714 SwFrm
*pFrm
= GetCurrFrm( FALSE
);
715 if ( pFrm
&& pFrm
->IsInTab() )
716 return pFrm
->FindTabFrm()->GetTable()->IsTblComplex();
721 BOOL
SwCrsrShell::IsTblComplexForChart()
725 StartAction(); // IsTblComplexForChart() may trigger table formatting
726 // we better do that inside an action
728 const SwTableNode
* pTNd
= pCurCrsr
->GetPoint()->nNode
.GetNode().FindTableNode();
731 // wir stehen in der Tabelle, dann teste mal, ob die Tabelle oder die
732 // Selektion ausgeglichen ist.
736 bRet
= pTNd
->GetTable().IsTblComplexForChart( sSel
);
744 String
SwCrsrShell::GetBoxNms() const
747 const SwPosition
* pPos
;
752 SwCntntNode
*pCNd
= pTblCrsr
->Start()->nNode
.GetNode().GetCntntNode();
753 pFrm
= pCNd
? pCNd
->GetFrm() : 0;
758 pFrm
= pFrm
->GetUpper();
759 } while ( pFrm
&& !pFrm
->IsCellFrm() );
761 ASSERT( pFrm
, "kein Frame zur Box" );
762 sNm
= ((SwCellFrm
*)pFrm
)->GetTabBox()->GetName();
764 pPos
= pTblCrsr
->End();
768 const SwTableNode
* pTblNd
= IsCrsrInTbl();
771 pPos
= GetCrsr()->GetPoint();
774 SwCntntNode
* pCNd
= pPos
->nNode
.GetNode().GetCntntNode();
775 pFrm
= pCNd
? pCNd
->GetFrm() : 0;
780 pFrm
= pFrm
->GetUpper();
781 } while ( pFrm
&& !pFrm
->IsCellFrm() );
784 sNm
+= ((SwCellFrm
*)pFrm
)->GetTabBox()->GetName();
790 BOOL
SwCrsrShell::GotoTable( const String
& rName
)
792 SwCallLink
aLk( *this ); // Crsr-Moves ueberwachen,
793 BOOL bRet
= !pTblCrsr
&& pCurCrsr
->GotoTable( rName
);
796 pCurCrsr
->GetPtPos() = Point();
797 UpdateCrsr( SwCrsrShell::SCROLLWIN
| SwCrsrShell::CHKRANGE
|
798 SwCrsrShell::READONLY
); // und den akt. Updaten
804 BOOL
SwCrsrShell::CheckTblBoxCntnt( const SwPosition
* pPos
)
806 if( !pBoxIdx
|| !pBoxPtr
|| IsSelTblCells() || !IsAutoUpdateCells() )
809 // ueberpruefe, ob der Box Inhalt mit dem angegebenen Format der Box
810 // ueber einstimmt. Wenn nicht, setze neu
811 SwTableBox
* pChkBox
= 0;
812 SwStartNode
* pSttNd
= 0;
815 // gesicherte Position heraus holen.
816 if( pBoxIdx
&& pBoxPtr
&&
817 0 != ( pSttNd
= pBoxIdx
->GetNode().GetStartNode() ) &&
818 SwTableBoxStartNode
== pSttNd
->GetStartNodeType() &&
819 pBoxPtr
== pSttNd
->FindTableNode()->GetTable().
820 GetTblBox( pBoxIdx
->GetIndex() ) )
823 else if( 0 != ( pSttNd
= pPos
->nNode
.GetNode().
824 FindSttNodeByType( SwTableBoxStartNode
)) )
826 pChkBox
= pSttNd
->FindTableNode()->GetTable().GetTblBox( pSttNd
->GetIndex() );
830 // Box mehr als 1 Absatz?
831 if( pChkBox
&& pSttNd
->GetIndex() + 2 != pSttNd
->EndOfSectionIndex() )
834 // jetzt sollten wir mal die Pointer zerstoeren, bevor eine erneute
835 // Actionklammerung kommt.
836 if( !pPos
&& !pChkBox
)
839 // liegt der Cursor nicht mehr in dem Bereich ?
840 if( pChkBox
&& !pPos
&&
841 ( pCurCrsr
->HasMark() || pCurCrsr
->GetNext() != pCurCrsr
||
842 pSttNd
->GetIndex() + 1 == pCurCrsr
->GetPoint()->nNode
.GetIndex() ))
845 //JP 12.01.99: hat sich der Inhalt der Box ueberhaupt veraendert?
846 // Ist wichtig, wenn z.B. Undo nicht den richtigen Inhalt wieder
847 // herstellen konnte.
850 const SwTxtNode
* pNd
= GetDoc()->GetNodes()[
851 pSttNd
->GetIndex() + 1 ]->GetTxtNode();
853 ( pNd
->GetTxt() == ViewShell::GetShellRes()->aCalc_Error
&&
854 SFX_ITEM_SET
== pChkBox
->GetFrmFmt()->
855 GetItemState( RES_BOXATR_FORMULA
)) )
861 // jetzt sollten wir mal die Pointer zerstoeren, bevor ein weiterer
865 GetDoc()->ChkBoxNumFmt( *pChkBox
, TRUE
);
873 void SwCrsrShell::SaveTblBoxCntnt( const SwPosition
* pPos
)
875 if( IsSelTblCells() || !IsAutoUpdateCells() )
879 pPos
= pCurCrsr
->GetPoint();
881 SwStartNode
* pSttNd
= pPos
->nNode
.GetNode().FindSttNodeByType( SwTableBoxStartNode
);
883 BOOL bCheckBox
= FALSE
;
884 if( pSttNd
&& pBoxIdx
)
886 if( pSttNd
== &pBoxIdx
->GetNode() )
887 pSttNd
= 0; // die haben wir schon
892 bCheckBox
= 0 != pBoxIdx
;
897 SwPosition
aPos( *pBoxIdx
);
898 CheckTblBoxCntnt( &aPos
);
903 pBoxPtr
= pSttNd
->FindTableNode()->GetTable().GetTblBox( pSttNd
->GetIndex() );
908 pBoxIdx
= new SwNodeIndex( *pSttNd
);
913 void SwCrsrShell::ClearTblBoxCntnt()
915 delete pBoxIdx
, pBoxIdx
= 0;
919 BOOL
SwCrsrShell::EndAllTblBoxEdit()
922 ViewShell
*pSh
= this;
924 if( pSh
->IsA( TYPE( SwCrsrShell
) ) )
925 bRet
|= ((SwCrsrShell
*)pSh
)->CheckTblBoxCntnt(
926 ((SwCrsrShell
*)pSh
)->pCurCrsr
->GetPoint() );
928 } while( this != (pSh
= (ViewShell
*)pSh
->GetNext()) );