1f6e50924SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3f6e50924SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4f6e50924SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5f6e50924SAndrew Rist  * distributed with this work for additional information
6f6e50924SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7f6e50924SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8f6e50924SAndrew Rist  * "License"); you may not use this file except in compliance
9f6e50924SAndrew Rist  * with the License.  You may obtain a copy of the License at
10f6e50924SAndrew Rist  *
11f6e50924SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12f6e50924SAndrew Rist  *
13f6e50924SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14f6e50924SAndrew Rist  * software distributed under the License is distributed on an
15f6e50924SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16f6e50924SAndrew Rist  * KIND, either express or implied.  See the License for the
17f6e50924SAndrew Rist  * specific language governing permissions and limitations
18f6e50924SAndrew Rist  * under the License.
19f6e50924SAndrew Rist  *
20f6e50924SAndrew Rist  *************************************************************/
21f6e50924SAndrew Rist 
22f6e50924SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_svx.hxx"
26cdf0e10cSrcweir 
27766ce4d0SZheng Fan #include <svx/sdr/table/tablecontroller.hxx>
28766ce4d0SZheng Fan #include <tablemodel.hxx>
29cdf0e10cSrcweir 
30cdf0e10cSrcweir #include <com/sun/star/style/XStyleFamiliesSupplier.hpp>
31cdf0e10cSrcweir #include <com/sun/star/container/XIndexAccess.hpp>
32cdf0e10cSrcweir 
33cdf0e10cSrcweir #include <com/sun/star/beans/XPropertySet.hpp>
34cdf0e10cSrcweir #include <com/sun/star/table/XMergeableCellRange.hpp>
35cdf0e10cSrcweir #include <com/sun/star/table/XMergeableCell.hpp>
36cdf0e10cSrcweir 
37cdf0e10cSrcweir #include <sal/config.h>
38cdf0e10cSrcweir 
39cdf0e10cSrcweir #include <vcl/svapp.hxx>
40cdf0e10cSrcweir #include <svl/whiter.hxx>
41cdf0e10cSrcweir 
42cdf0e10cSrcweir #include <sfx2/request.hxx>
43cdf0e10cSrcweir 
44cdf0e10cSrcweir #include <editeng/scripttypeitem.hxx>
45cdf0e10cSrcweir #include <svx/svdotable.hxx>
46cdf0e10cSrcweir #include <svx/sdr/overlay/overlayobjectcell.hxx>
47cdf0e10cSrcweir #include <svx/sdr/overlay/overlaymanager.hxx>
48cdf0e10cSrcweir #include <svx/svxids.hrc>
49cdf0e10cSrcweir #include <editeng/outlobj.hxx>
50cdf0e10cSrcweir #include <svx/svdoutl.hxx>
51cdf0e10cSrcweir #include <svx/svdpagv.hxx>
52cdf0e10cSrcweir #include <svx/svdetc.hxx>
53cdf0e10cSrcweir #include <editeng/editobj.hxx>
54cdf0e10cSrcweir #include "editeng/editstat.hxx"
55cdf0e10cSrcweir #include "editeng/unolingu.hxx"
56cdf0e10cSrcweir #include "svx/sdrpagewindow.hxx"
57cdf0e10cSrcweir #include <svx/selectioncontroller.hxx>
58cdf0e10cSrcweir #include <svx/svdmodel.hxx>
59cdf0e10cSrcweir #include "svx/sdrpaintwindow.hxx"
60cdf0e10cSrcweir #include <svx/svxdlg.hxx>
61cdf0e10cSrcweir #include <editeng/boxitem.hxx>
62cdf0e10cSrcweir #include "cell.hxx"
63cdf0e10cSrcweir #include <editeng/borderline.hxx>
64cdf0e10cSrcweir #include <editeng/colritem.hxx>
65cdf0e10cSrcweir #include "editeng/bolnitem.hxx"
66cdf0e10cSrcweir #include "svx/svdstr.hrc"
67cdf0e10cSrcweir #include "svx/svdglob.hxx"
68cdf0e10cSrcweir #include "svx/svdpage.hxx"
69cdf0e10cSrcweir #include "tableundo.hxx"
70cdf0e10cSrcweir #include "tablelayouter.hxx"
71cdf0e10cSrcweir 
72cdf0e10cSrcweir using ::rtl::OUString;
73cdf0e10cSrcweir using namespace ::sdr::table;
74cdf0e10cSrcweir using namespace ::com::sun::star;
75cdf0e10cSrcweir using namespace ::com::sun::star::uno;
76cdf0e10cSrcweir using namespace ::com::sun::star::table;
77cdf0e10cSrcweir using namespace ::com::sun::star::beans;
78cdf0e10cSrcweir using namespace ::com::sun::star::container;
79cdf0e10cSrcweir using namespace ::com::sun::star::text;
80cdf0e10cSrcweir using namespace ::com::sun::star::style;
81cdf0e10cSrcweir 
82cdf0e10cSrcweir namespace sdr { namespace table {
83cdf0e10cSrcweir 
84cdf0e10cSrcweir // --------------------------------------------------------------------
85cdf0e10cSrcweir // class SvxTableControllerModifyListener
86cdf0e10cSrcweir // --------------------------------------------------------------------
87cdf0e10cSrcweir 
88cdf0e10cSrcweir class SvxTableControllerModifyListener : public ::cppu::WeakImplHelper1< ::com::sun::star::util::XModifyListener >
89cdf0e10cSrcweir {
90cdf0e10cSrcweir public:
SvxTableControllerModifyListener(SvxTableController * pController)91cdf0e10cSrcweir 	SvxTableControllerModifyListener( SvxTableController* pController )
92cdf0e10cSrcweir 		: mpController( pController ) {}
93cdf0e10cSrcweir 
94cdf0e10cSrcweir 	// XModifyListener
95cdf0e10cSrcweir     virtual void SAL_CALL modified( const ::com::sun::star::lang::EventObject& aEvent ) throw (::com::sun::star::uno::RuntimeException);
96cdf0e10cSrcweir 
97cdf0e10cSrcweir     // XEventListener
98cdf0e10cSrcweir     virtual void SAL_CALL disposing( const ::com::sun::star::lang::EventObject& Source ) throw (::com::sun::star::uno::RuntimeException);
99cdf0e10cSrcweir 
100cdf0e10cSrcweir 	SvxTableController* mpController;
101cdf0e10cSrcweir };
102cdf0e10cSrcweir 
103cdf0e10cSrcweir // --------------------------------------------------------------------
104cdf0e10cSrcweir // XModifyListener
105cdf0e10cSrcweir // --------------------------------------------------------------------
106cdf0e10cSrcweir 
modified(const::com::sun::star::lang::EventObject &)107cdf0e10cSrcweir void SAL_CALL SvxTableControllerModifyListener::modified( const ::com::sun::star::lang::EventObject&  ) throw (::com::sun::star::uno::RuntimeException)
108cdf0e10cSrcweir {
109cdf0e10cSrcweir 	if( mpController )
110cdf0e10cSrcweir 		mpController->onTableModified();
111cdf0e10cSrcweir }
112cdf0e10cSrcweir 
113cdf0e10cSrcweir // --------------------------------------------------------------------
114cdf0e10cSrcweir // XEventListener
115cdf0e10cSrcweir // --------------------------------------------------------------------
116cdf0e10cSrcweir 
disposing(const::com::sun::star::lang::EventObject &)117cdf0e10cSrcweir void SAL_CALL SvxTableControllerModifyListener::disposing( const ::com::sun::star::lang::EventObject&  ) throw (::com::sun::star::uno::RuntimeException)
118cdf0e10cSrcweir {
119cdf0e10cSrcweir 	mpController = 0;
120cdf0e10cSrcweir }
121cdf0e10cSrcweir 
122cdf0e10cSrcweir // --------------------------------------------------------------------
123cdf0e10cSrcweir // class SvxTableController
124cdf0e10cSrcweir // --------------------------------------------------------------------
125cdf0e10cSrcweir 
CreateTableController(SdrObjEditView * pView,const SdrObject * pObj,const rtl::Reference<sdr::SelectionController> & xRefController)126cdf0e10cSrcweir rtl::Reference< sdr::SelectionController > CreateTableController( SdrObjEditView* pView, const SdrObject* pObj, const rtl::Reference< sdr::SelectionController >& xRefController )
127cdf0e10cSrcweir {
128cdf0e10cSrcweir 	return SvxTableController::create( pView, pObj, xRefController );
129cdf0e10cSrcweir }
130cdf0e10cSrcweir 
131cdf0e10cSrcweir // --------------------------------------------------------------------
132cdf0e10cSrcweir 
create(SdrObjEditView * pView,const SdrObject * pObj,const rtl::Reference<sdr::SelectionController> & xRefController)133cdf0e10cSrcweir rtl::Reference< sdr::SelectionController > SvxTableController::create( SdrObjEditView* pView, const SdrObject* pObj, const rtl::Reference< sdr::SelectionController >& xRefController )
134cdf0e10cSrcweir {
135cdf0e10cSrcweir 	if( xRefController.is() )
136cdf0e10cSrcweir 	{
137cdf0e10cSrcweir 		SvxTableController* pController = dynamic_cast< SvxTableController* >( xRefController.get() );
138cdf0e10cSrcweir 		if( pController && (pController->mxTableObj.get() == pObj) && (pController->mpView == pView)  )
139cdf0e10cSrcweir 			return xRefController;
140cdf0e10cSrcweir 	}
141cdf0e10cSrcweir 	return new SvxTableController( pView, pObj );
142cdf0e10cSrcweir }
143cdf0e10cSrcweir 
144cdf0e10cSrcweir // --------------------------------------------------------------------
145cdf0e10cSrcweir 
SvxTableController(SdrObjEditView * pView,const SdrObject * pObj)146cdf0e10cSrcweir SvxTableController::SvxTableController( SdrObjEditView* pView, const SdrObject* pObj )
147cdf0e10cSrcweir : mbCellSelectionMode(false)
148cdf0e10cSrcweir , mbLeftButtonDown(false)
149cdf0e10cSrcweir , mpSelectionOverlay(0)
150cdf0e10cSrcweir , mpView( dynamic_cast< SdrView* >( pView ) )
151cdf0e10cSrcweir , mxTableObj( dynamic_cast< SdrTableObj* >( const_cast< SdrObject* >( pObj ) ) )
152cdf0e10cSrcweir , mpModel( 0 )
153cdf0e10cSrcweir , mnUpdateEvent( 0 )
154cdf0e10cSrcweir {
155cdf0e10cSrcweir 	if( pObj )
156cdf0e10cSrcweir 		mpModel = pObj->GetModel();
157cdf0e10cSrcweir 
158cdf0e10cSrcweir 	if( mxTableObj.is() )
159cdf0e10cSrcweir 	{
160cdf0e10cSrcweir 		static_cast< const SdrTableObj* >( pObj )->getActiveCellPos( maCursorFirstPos );
161cdf0e10cSrcweir 		maCursorLastPos = maCursorFirstPos;
162cdf0e10cSrcweir 
163cdf0e10cSrcweir 		Reference< XTable > xTable( static_cast< const SdrTableObj* >( pObj )->getTable() );
164cdf0e10cSrcweir 		if( xTable.is() )
165cdf0e10cSrcweir 		{
166cdf0e10cSrcweir 			mxModifyListener = new SvxTableControllerModifyListener( this );
167cdf0e10cSrcweir 			xTable->addModifyListener( mxModifyListener );
168cdf0e10cSrcweir 
169cdf0e10cSrcweir 			mxTable.set( dynamic_cast< TableModel* >( xTable.get() ) );
170cdf0e10cSrcweir 		}
171cdf0e10cSrcweir 	}
172cdf0e10cSrcweir }
173cdf0e10cSrcweir 
174cdf0e10cSrcweir // --------------------------------------------------------------------
175cdf0e10cSrcweir 
~SvxTableController()176cdf0e10cSrcweir SvxTableController::~SvxTableController()
177cdf0e10cSrcweir {
178cdf0e10cSrcweir 	if( mnUpdateEvent )
179cdf0e10cSrcweir 	{
180cdf0e10cSrcweir 		Application::RemoveUserEvent( mnUpdateEvent );
181cdf0e10cSrcweir 	}
182cdf0e10cSrcweir 
183cdf0e10cSrcweir 	if( mxModifyListener.is() && mxTableObj.get() )
184cdf0e10cSrcweir 	{
185cdf0e10cSrcweir 		Reference< XTable > xTable( static_cast< SdrTableObj* >( mxTableObj.get() )->getTable() );
186cdf0e10cSrcweir 		if( xTable.is() )
187cdf0e10cSrcweir 		{
188cdf0e10cSrcweir 			xTable->removeModifyListener( mxModifyListener );
189cdf0e10cSrcweir 			mxModifyListener.clear();
190cdf0e10cSrcweir 		}
191cdf0e10cSrcweir 	}
192cdf0e10cSrcweir }
193cdf0e10cSrcweir 
194cdf0e10cSrcweir // --------------------------------------------------------------------
195cdf0e10cSrcweir 
196cdf0e10cSrcweir const sal_uInt16 ACTION_NONE = 0;
197cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_FIRST_CELL = 1;
198cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_FIRST_COLUMN = 2;
199cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_FIRST_ROW = 3;
200cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_LEFT_CELL = 4;
201cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_UP_CELL = 5;
202cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_RIGHT_CELL = 6;
203cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_DOWN_CELL = 7;
204cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_LAST_CELL = 8;
205cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_LAST_COLUMN = 9;
206cdf0e10cSrcweir const sal_uInt16 ACTION_GOTO_LAST_ROW = 10;
207cdf0e10cSrcweir const sal_uInt16 ACTION_EDIT_CELL = 11;
208cdf0e10cSrcweir const sal_uInt16 ACTION_STOP_TEXT_EDIT = 12;
209cdf0e10cSrcweir const sal_uInt16 ACTION_REMOVE_SELECTION = 13;
210cdf0e10cSrcweir const sal_uInt16 ACTION_START_SELECTION = 14;
211cdf0e10cSrcweir const sal_uInt16 ACTION_HANDLED_BY_VIEW = 15;
212cdf0e10cSrcweir const sal_uInt16 ACTION_TAB = 18;
213cdf0e10cSrcweir 
onKeyInput(const KeyEvent & rKEvt,Window * pWindow)214cdf0e10cSrcweir bool SvxTableController::onKeyInput(const KeyEvent& rKEvt, Window* pWindow )
215cdf0e10cSrcweir {
216cdf0e10cSrcweir 	if( !checkTableObject() )
217cdf0e10cSrcweir 		return false;
218cdf0e10cSrcweir 
219cdf0e10cSrcweir 	// check if we are read only
220cdf0e10cSrcweir 	if( mpModel && mpModel->IsReadOnly())
221cdf0e10cSrcweir 	{
222cdf0e10cSrcweir 		switch( rKEvt.GetKeyCode().GetCode() )
223cdf0e10cSrcweir 		{
224cdf0e10cSrcweir 		case awt::Key::DOWN:
225cdf0e10cSrcweir 		case awt::Key::UP:
226cdf0e10cSrcweir 		case awt::Key::LEFT:
227cdf0e10cSrcweir 		case awt::Key::RIGHT:
228cdf0e10cSrcweir 		case awt::Key::TAB:
229cdf0e10cSrcweir 		case awt::Key::HOME:
230cdf0e10cSrcweir 		case awt::Key::END:
231cdf0e10cSrcweir 		case awt::Key::NUM2:
232cdf0e10cSrcweir 		case awt::Key::NUM4:
233cdf0e10cSrcweir 		case awt::Key::NUM6:
234cdf0e10cSrcweir 		case awt::Key::NUM8:
235cdf0e10cSrcweir 		case awt::Key::ESCAPE:
236cdf0e10cSrcweir 		case awt::Key::F2:
237cdf0e10cSrcweir 			break;
238cdf0e10cSrcweir 		default:
239cdf0e10cSrcweir 			// tell the view we eat the event, no further processing needed
240cdf0e10cSrcweir 			return true;
241cdf0e10cSrcweir 		}
242cdf0e10cSrcweir 	}
243cdf0e10cSrcweir 
244cdf0e10cSrcweir 	sal_uInt16 nAction = getKeyboardAction( rKEvt, pWindow );
245cdf0e10cSrcweir 
246cdf0e10cSrcweir 	return executeAction( nAction, ( rKEvt.GetKeyCode().IsShift() ) ? sal_True : sal_False, pWindow );
247cdf0e10cSrcweir }
248cdf0e10cSrcweir 
249cdf0e10cSrcweir // --------------------------------------------------------------------
250cdf0e10cSrcweir // ::com::sun::star::awt::XMouseClickHandler:
251cdf0e10cSrcweir // --------------------------------------------------------------------
252cdf0e10cSrcweir 
onMouseButtonDown(const MouseEvent & rMEvt,Window * pWindow)253cdf0e10cSrcweir bool SvxTableController::onMouseButtonDown(const MouseEvent& rMEvt, Window* pWindow )
254cdf0e10cSrcweir {
255cdf0e10cSrcweir 	if( !pWindow || !checkTableObject() )
256cdf0e10cSrcweir 		return false;
257cdf0e10cSrcweir 
258cdf0e10cSrcweir 	SdrViewEvent aVEvt;
259cdf0e10cSrcweir 	if( !rMEvt.IsRight() && mpView->PickAnything(rMEvt,SDRMOUSEBUTTONDOWN, aVEvt) == SDRHIT_HANDLE )
260cdf0e10cSrcweir 		return false;
261cdf0e10cSrcweir 
262cdf0e10cSrcweir 	TableHitKind eHit = static_cast< SdrTableObj* >(mxTableObj.get())->CheckTableHit( pWindow->PixelToLogic(rMEvt.GetPosPixel()), maMouseDownPos.mnCol, maMouseDownPos.mnRow, 0 );
263cdf0e10cSrcweir 
264cdf0e10cSrcweir 	mbLeftButtonDown = (rMEvt.GetClicks() == 1) && rMEvt.IsLeft();
265cdf0e10cSrcweir 
266cdf0e10cSrcweir 	if( eHit == SDRTABLEHIT_CELL )
267cdf0e10cSrcweir 	{
268cdf0e10cSrcweir 		StartSelection( maMouseDownPos );
269cdf0e10cSrcweir 		return true;
270cdf0e10cSrcweir 	}
271cdf0e10cSrcweir 
272cdf0e10cSrcweir 	if( rMEvt.IsRight() && eHit != SDRTABLEHIT_NONE )
273cdf0e10cSrcweir 		return true; // right click will become context menu
274cdf0e10cSrcweir 
275cdf0e10cSrcweir 	// for cell selektion with the mouse remember our first hit
276cdf0e10cSrcweir 	if( mbLeftButtonDown )
277cdf0e10cSrcweir 	{
278cdf0e10cSrcweir 		RemoveSelection();
279cdf0e10cSrcweir 
280cdf0e10cSrcweir 		Point aPnt(rMEvt.GetPosPixel());
281cdf0e10cSrcweir 		if (pWindow!=NULL)
282cdf0e10cSrcweir 			aPnt=pWindow->PixelToLogic(aPnt);
283cdf0e10cSrcweir 
284cdf0e10cSrcweir 		SdrHdl* pHdl = mpView->PickHandle(aPnt);
285cdf0e10cSrcweir 
286cdf0e10cSrcweir 		if( pHdl )
287cdf0e10cSrcweir 		{
288cdf0e10cSrcweir 			mbLeftButtonDown = false;
289cdf0e10cSrcweir 		}
290cdf0e10cSrcweir 		else
291cdf0e10cSrcweir 		{
292cdf0e10cSrcweir 			::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
293cdf0e10cSrcweir 
294cdf0e10cSrcweir 			if( !pWindow || !pTableObj || eHit  == SDRTABLEHIT_NONE)
295cdf0e10cSrcweir 			{
296cdf0e10cSrcweir 				mbLeftButtonDown = false;
297cdf0e10cSrcweir 			}
298cdf0e10cSrcweir 		}
299cdf0e10cSrcweir 	}
300cdf0e10cSrcweir 
301cdf0e10cSrcweir 	return false;
302cdf0e10cSrcweir }
303cdf0e10cSrcweir 
304cdf0e10cSrcweir // --------------------------------------------------------------------
305cdf0e10cSrcweir 
onMouseButtonUp(const MouseEvent & rMEvt,Window *)306cdf0e10cSrcweir bool SvxTableController::onMouseButtonUp(const MouseEvent& rMEvt, Window* /*pWin*/)
307cdf0e10cSrcweir {
308cdf0e10cSrcweir 	if( !checkTableObject() )
309cdf0e10cSrcweir 		return false;
310cdf0e10cSrcweir 
311cdf0e10cSrcweir 	mbLeftButtonDown = false;
312cdf0e10cSrcweir 
313cdf0e10cSrcweir 	if( rMEvt.GetClicks() == 2 )
314cdf0e10cSrcweir 		return true;
315cdf0e10cSrcweir 
316cdf0e10cSrcweir 	return false;
317cdf0e10cSrcweir }
318cdf0e10cSrcweir 
319cdf0e10cSrcweir // --------------------------------------------------------------------
320cdf0e10cSrcweir 
onMouseMove(const MouseEvent & rMEvt,Window * pWindow)321cdf0e10cSrcweir bool SvxTableController::onMouseMove(const MouseEvent& rMEvt, Window* pWindow )
322cdf0e10cSrcweir {
323cdf0e10cSrcweir 	if( !checkTableObject() )
324cdf0e10cSrcweir 		return false;
325cdf0e10cSrcweir 
326cdf0e10cSrcweir 	if( rMEvt.IsLeft() )
327cdf0e10cSrcweir 	{
328cdf0e10cSrcweir 		int i = 0;
329cdf0e10cSrcweir 		i++;
330cdf0e10cSrcweir 	}
331cdf0e10cSrcweir 
332cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< SdrTableObj* >( mxTableObj.get() );
333cdf0e10cSrcweir 	CellPos aPos;
334cdf0e10cSrcweir 	if( mbLeftButtonDown && pTableObj && pTableObj->CheckTableHit( pWindow->PixelToLogic(rMEvt.GetPosPixel()), aPos.mnCol, aPos.mnRow, 0 ) != SDRTABLEHIT_NONE )
335cdf0e10cSrcweir 	{
336cdf0e10cSrcweir 		if(aPos != maMouseDownPos)
337cdf0e10cSrcweir 		{
338cdf0e10cSrcweir 			if( mbCellSelectionMode )
339cdf0e10cSrcweir 			{
340cdf0e10cSrcweir 				setSelectedCells( maMouseDownPos, aPos );
341cdf0e10cSrcweir 				return true;
342cdf0e10cSrcweir 			}
343cdf0e10cSrcweir 			else
344cdf0e10cSrcweir 			{
345cdf0e10cSrcweir 				StartSelection( maMouseDownPos );
346cdf0e10cSrcweir 			}
347cdf0e10cSrcweir 		}
348cdf0e10cSrcweir 		else if( mbCellSelectionMode )
349cdf0e10cSrcweir 		{
350cdf0e10cSrcweir 			UpdateSelection( aPos );
351cdf0e10cSrcweir 			return true;
352cdf0e10cSrcweir 		}
353cdf0e10cSrcweir 	}
354cdf0e10cSrcweir     return false;
355cdf0e10cSrcweir }
356cdf0e10cSrcweir 
357cdf0e10cSrcweir // --------------------------------------------------------------------
358cdf0e10cSrcweir 
onSelectionHasChanged()359cdf0e10cSrcweir void SvxTableController::onSelectionHasChanged()
360cdf0e10cSrcweir {
361cdf0e10cSrcweir 	bool bSelected = false;
362cdf0e10cSrcweir 
363cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< SdrTableObj* >( mxTableObj.get() );
364cdf0e10cSrcweir 	if( pTableObj && pTableObj->IsTextEditActive() )
365cdf0e10cSrcweir 	{
366cdf0e10cSrcweir 		pTableObj->getActiveCellPos( maCursorFirstPos );
367cdf0e10cSrcweir 		maCursorLastPos = maCursorFirstPos;
368cdf0e10cSrcweir 		mbCellSelectionMode = false;
369cdf0e10cSrcweir 	}
370cdf0e10cSrcweir 	else
371cdf0e10cSrcweir 	{
372cdf0e10cSrcweir 		const SdrMarkList& rMarkList= mpView->GetMarkedObjectList();
373cdf0e10cSrcweir 		if( rMarkList.GetMarkCount() == 1 )
374cdf0e10cSrcweir 			bSelected = mxTableObj.get() == rMarkList.GetMark(0)->GetMarkedSdrObj();
375cdf0e10cSrcweir 	}
376cdf0e10cSrcweir 
377cdf0e10cSrcweir 	if( bSelected )
378cdf0e10cSrcweir 	{
379cdf0e10cSrcweir 		updateSelectionOverlay();
380cdf0e10cSrcweir 	}
381cdf0e10cSrcweir 	else
382cdf0e10cSrcweir 	{
383cdf0e10cSrcweir 		destroySelectionOverlay();
384cdf0e10cSrcweir 	}
385cdf0e10cSrcweir }
386cdf0e10cSrcweir 
387cdf0e10cSrcweir // --------------------------------------------------------------------
388cdf0e10cSrcweir 
GetState(SfxItemSet & rSet)389cdf0e10cSrcweir void SvxTableController::GetState( SfxItemSet& rSet )
390cdf0e10cSrcweir {
391cdf0e10cSrcweir 	if( !mxTable.is() || !mxTableObj.is() || !mxTableObj->GetModel() )
392cdf0e10cSrcweir 		return;
393cdf0e10cSrcweir 
394cdf0e10cSrcweir 	SfxItemSet* pSet = 0;
395cdf0e10cSrcweir 
396cdf0e10cSrcweir 	bool bVertDone = false;
397cdf0e10cSrcweir 
398cdf0e10cSrcweir     // Iterate over all requested items in the set.
399cdf0e10cSrcweir 	SfxWhichIter aIter( rSet );
400cdf0e10cSrcweir 	sal_uInt16 nWhich = aIter.FirstWhich();
401cdf0e10cSrcweir 	while (nWhich)
402cdf0e10cSrcweir 	{
403cdf0e10cSrcweir 		switch (nWhich)
404cdf0e10cSrcweir 		{
405cdf0e10cSrcweir 			case SID_TABLE_VERT_BOTTOM:
406cdf0e10cSrcweir 			case SID_TABLE_VERT_CENTER:
407cdf0e10cSrcweir 			case SID_TABLE_VERT_NONE:
408cdf0e10cSrcweir 				{
409cdf0e10cSrcweir 					if( !mxTable.is() || !mxTableObj->GetModel() )
410cdf0e10cSrcweir 					{
411cdf0e10cSrcweir 						rSet.DisableItem(nWhich);
412cdf0e10cSrcweir 					}
413cdf0e10cSrcweir 					else if(!bVertDone)
414cdf0e10cSrcweir 					{
415cdf0e10cSrcweir 						if( !pSet )
416cdf0e10cSrcweir 						{
417cdf0e10cSrcweir 							pSet = new SfxItemSet( mxTableObj->GetModel()->GetItemPool() );
418cdf0e10cSrcweir 							MergeAttrFromSelectedCells(*pSet, sal_False);
419cdf0e10cSrcweir 						}
420cdf0e10cSrcweir 
421cdf0e10cSrcweir 						SdrTextVertAdjust eAdj = SDRTEXTVERTADJUST_BLOCK;
422cdf0e10cSrcweir 
423cdf0e10cSrcweir 						if( pSet->GetItemState( SDRATTR_TEXT_VERTADJUST ) != SFX_ITEM_DONTCARE )
424cdf0e10cSrcweir 							eAdj = ((SdrTextVertAdjustItem&)(pSet->Get(SDRATTR_TEXT_VERTADJUST))).GetValue();
425cdf0e10cSrcweir 
426cdf0e10cSrcweir 						rSet.Put(SfxBoolItem(SID_TABLE_VERT_BOTTOM, eAdj == SDRTEXTVERTADJUST_BOTTOM));
427cdf0e10cSrcweir 						rSet.Put(SfxBoolItem(SID_TABLE_VERT_CENTER, eAdj == SDRTEXTVERTADJUST_CENTER));
428cdf0e10cSrcweir 						rSet.Put(SfxBoolItem(SID_TABLE_VERT_NONE, eAdj == SDRTEXTVERTADJUST_TOP));
429cdf0e10cSrcweir 						bVertDone = true;
430cdf0e10cSrcweir 					}
431cdf0e10cSrcweir 					break;
432cdf0e10cSrcweir 				}
433cdf0e10cSrcweir 			case SID_TABLE_DELETE_ROW:
434cdf0e10cSrcweir 				if( !mxTable.is() || !hasSelectedCells() || (mxTable->getRowCount() <= 1) )
435cdf0e10cSrcweir 					rSet.DisableItem(SID_TABLE_DELETE_ROW);
436cdf0e10cSrcweir 				break;
437cdf0e10cSrcweir 			case SID_TABLE_DELETE_COL:
438cdf0e10cSrcweir 				if( !mxTable.is() || !hasSelectedCells() || (mxTable->getColumnCount() <= 1) )
439cdf0e10cSrcweir 					rSet.DisableItem(SID_TABLE_DELETE_COL);
440cdf0e10cSrcweir 				break;
441cdf0e10cSrcweir 			case SID_TABLE_MERGE_CELLS:
442cdf0e10cSrcweir 				if( !mxTable.is() || !hasSelectedCells() )
443cdf0e10cSrcweir 					rSet.DisableItem(SID_TABLE_MERGE_CELLS);
444cdf0e10cSrcweir 				break;
445cdf0e10cSrcweir 			case SID_TABLE_SPLIT_CELLS:
446cdf0e10cSrcweir 				if( !hasSelectedCells() || !mxTable.is() )
447cdf0e10cSrcweir 					rSet.DisableItem(SID_TABLE_SPLIT_CELLS);
448cdf0e10cSrcweir 				break;
449cdf0e10cSrcweir 
450cdf0e10cSrcweir 			case SID_OPTIMIZE_TABLE:
451cdf0e10cSrcweir 			case SID_TABLE_DISTRIBUTE_COLUMNS:
452cdf0e10cSrcweir 			case SID_TABLE_DISTRIBUTE_ROWS:
453cdf0e10cSrcweir 			{
454cdf0e10cSrcweir 				bool bDistributeColumns = false;
455cdf0e10cSrcweir 				bool bDistributeRows = false;
456cdf0e10cSrcweir 				if( mxTable.is() )
457cdf0e10cSrcweir 				{
458cdf0e10cSrcweir 					CellPos aStart, aEnd;
459cdf0e10cSrcweir 					getSelectedCells( aStart, aEnd );
460cdf0e10cSrcweir 
461cdf0e10cSrcweir 					bDistributeColumns = aStart.mnCol != aEnd.mnCol;
462cdf0e10cSrcweir 					bDistributeRows = aStart.mnRow != aEnd.mnRow;
463cdf0e10cSrcweir 				}
464cdf0e10cSrcweir 				if( !bDistributeColumns && !bDistributeRows )
465cdf0e10cSrcweir 					rSet.DisableItem(SID_OPTIMIZE_TABLE);
466cdf0e10cSrcweir 				if( !bDistributeColumns )
467cdf0e10cSrcweir 					rSet.DisableItem(SID_TABLE_DISTRIBUTE_COLUMNS);
468cdf0e10cSrcweir 				if( !bDistributeRows )
469cdf0e10cSrcweir 					rSet.DisableItem(SID_TABLE_DISTRIBUTE_ROWS);
470cdf0e10cSrcweir 				break;
471cdf0e10cSrcweir 			}
472cdf0e10cSrcweir 
473cdf0e10cSrcweir 			case SID_AUTOFORMAT:
474cdf0e10cSrcweir 			case SID_TABLE_SORT_DIALOG:
475cdf0e10cSrcweir 			case SID_TABLE_AUTOSUM:
476cdf0e10cSrcweir //				if( !mxTable.is() )
477cdf0e10cSrcweir //					rSet.DisableItem( nWhich );
478cdf0e10cSrcweir 				break;
479cdf0e10cSrcweir 			default:
480cdf0e10cSrcweir 				break;
481cdf0e10cSrcweir         }
482cdf0e10cSrcweir 		nWhich = aIter.NextWhich();
483cdf0e10cSrcweir 	}
484cdf0e10cSrcweir 	if( pSet )
485cdf0e10cSrcweir 		delete pSet;
486cdf0e10cSrcweir }
487cdf0e10cSrcweir 
488cdf0e10cSrcweir // --------------------------------------------------------------------
489cdf0e10cSrcweir 
onInsert(sal_uInt16 nSId,const SfxItemSet * pArgs)490cdf0e10cSrcweir void SvxTableController::onInsert( sal_uInt16 nSId, const SfxItemSet* pArgs )
491cdf0e10cSrcweir {
492cdf0e10cSrcweir 	::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
493cdf0e10cSrcweir 	if( !pTableObj )
494cdf0e10cSrcweir 		return;
495cdf0e10cSrcweir 
496cdf0e10cSrcweir 	if( mxTable.is() ) try
497cdf0e10cSrcweir 	{
498cdf0e10cSrcweir 		//
499cdf0e10cSrcweir 		bool bInsertAfter = true;
500cdf0e10cSrcweir 		sal_uInt16 nCount = 0;
501cdf0e10cSrcweir     	if( pArgs )
502cdf0e10cSrcweir     	{
503cdf0e10cSrcweir     	    const SfxPoolItem* pItem = 0;
504cdf0e10cSrcweir     	    pArgs->GetItemState(nSId, sal_False, &pItem);
505cdf0e10cSrcweir 			if (pItem)
506cdf0e10cSrcweir 			{
507cdf0e10cSrcweir 				nCount = ((const SfxInt16Item* )pItem)->GetValue();
508cdf0e10cSrcweir 				if(SFX_ITEM_SET == pArgs->GetItemState(SID_TABLE_PARAM_INSERT_AFTER, sal_True, &pItem))
509cdf0e10cSrcweir 					bInsertAfter = ((const SfxBoolItem* )pItem)->GetValue();
510cdf0e10cSrcweir 			}
511cdf0e10cSrcweir     	}
512cdf0e10cSrcweir 
513cdf0e10cSrcweir 		CellPos aStart, aEnd;
514cdf0e10cSrcweir 		if( hasSelectedCells() )
515cdf0e10cSrcweir 		{
516cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
517cdf0e10cSrcweir 		}
518cdf0e10cSrcweir 		else
519cdf0e10cSrcweir 		{
520cdf0e10cSrcweir 		    if( bInsertAfter )
521cdf0e10cSrcweir 		    {
522cdf0e10cSrcweir 			    aStart.mnCol = mxTable->getColumnCount() - 1;
523cdf0e10cSrcweir 			    aStart.mnRow = mxTable->getRowCount() - 1;
524cdf0e10cSrcweir 			    aEnd = aStart;
525cdf0e10cSrcweir 		    }
526cdf0e10cSrcweir 		}
527cdf0e10cSrcweir 
528cdf0e10cSrcweir 		if( pTableObj->IsTextEditActive() )
529cdf0e10cSrcweir 			mpView->SdrEndTextEdit(sal_True);
530cdf0e10cSrcweir 
531cdf0e10cSrcweir 		RemoveSelection();
532cdf0e10cSrcweir 
533cdf0e10cSrcweir 		const OUString sSize( RTL_CONSTASCII_USTRINGPARAM( "Size" ) );
534cdf0e10cSrcweir 
535cdf0e10cSrcweir 		const bool bUndo = mpModel && mpModel->IsUndoEnabled();
536cdf0e10cSrcweir 
537cdf0e10cSrcweir 		switch( nSId )
538cdf0e10cSrcweir 		{
539cdf0e10cSrcweir 		case SID_TABLE_INSERT_COL:
540cdf0e10cSrcweir 		{
541cdf0e10cSrcweir 			TableModelNotifyGuard aGuard( mxTable.get() );
542cdf0e10cSrcweir 
543cdf0e10cSrcweir 			if( bUndo )
544cdf0e10cSrcweir 			{
545cdf0e10cSrcweir 				mpModel->BegUndo( ImpGetResStr(STR_TABLE_INSCOL) );
546cdf0e10cSrcweir 				mpModel->AddUndo( mpModel->GetSdrUndoFactory().CreateUndoGeoObject(*pTableObj) );
547cdf0e10cSrcweir 			}
548cdf0e10cSrcweir 
549cdf0e10cSrcweir 			Reference< XTableColumns > xCols( mxTable->getColumns() );
550cdf0e10cSrcweir 			const sal_Int32 nNewColumns = (nCount == 0) ? (aEnd.mnCol - aStart.mnCol + 1) : nCount;
551cdf0e10cSrcweir 			const sal_Int32 nNewStartColumn = aEnd.mnCol + (bInsertAfter ? 1 : 0);
552cdf0e10cSrcweir 			xCols->insertByIndex( nNewStartColumn, nNewColumns );
553cdf0e10cSrcweir 
554cdf0e10cSrcweir 			for( sal_Int32 nOffset = 0; nOffset < nNewColumns; nOffset++ )
555cdf0e10cSrcweir 			{
556cdf0e10cSrcweir 				Reference< XPropertySet >( xCols->getByIndex( aEnd.mnCol + nOffset + 1 ), UNO_QUERY_THROW )->
557cdf0e10cSrcweir 					setPropertyValue( sSize,
558cdf0e10cSrcweir 						Reference< XPropertySet >( xCols->getByIndex( aStart.mnCol + nOffset ), UNO_QUERY_THROW )->
559cdf0e10cSrcweir 							getPropertyValue( sSize ) );
560cdf0e10cSrcweir 			}
561cdf0e10cSrcweir 
562cdf0e10cSrcweir 			if( bUndo )
563cdf0e10cSrcweir 				mpModel->EndUndo();
564cdf0e10cSrcweir 
565cdf0e10cSrcweir 			aStart.mnCol = nNewStartColumn;
566cdf0e10cSrcweir 			aStart.mnRow = 0;
567cdf0e10cSrcweir 			aEnd.mnCol = aStart.mnCol + nNewColumns - 1;
568cdf0e10cSrcweir 			aEnd.mnRow = mxTable->getRowCount() - 1;
569cdf0e10cSrcweir 			break;
570cdf0e10cSrcweir 		}
571cdf0e10cSrcweir 
572cdf0e10cSrcweir 		case SID_TABLE_INSERT_ROW:
573cdf0e10cSrcweir 		{
574cdf0e10cSrcweir 			TableModelNotifyGuard aGuard( mxTable.get() );
575cdf0e10cSrcweir 
576cdf0e10cSrcweir 			if( bUndo )
577cdf0e10cSrcweir 			{
578cdf0e10cSrcweir 				mpModel->BegUndo( ImpGetResStr(STR_TABLE_INSROW ) );
579cdf0e10cSrcweir 				mpModel->AddUndo( mpModel->GetSdrUndoFactory().CreateUndoGeoObject(*pTableObj) );
580cdf0e10cSrcweir 			}
581cdf0e10cSrcweir 
582cdf0e10cSrcweir 			Reference< XTableRows > xRows( mxTable->getRows() );
583cdf0e10cSrcweir 			const sal_Int32 nNewRows = (nCount == 0) ? (aEnd.mnRow - aStart.mnRow + 1) : nCount;
584cdf0e10cSrcweir 			const sal_Int32 nNewRowStart = aEnd.mnRow + (bInsertAfter ? 1 : 0);
585cdf0e10cSrcweir 			xRows->insertByIndex( nNewRowStart, nNewRows );
586cdf0e10cSrcweir 
587cdf0e10cSrcweir 			for( sal_Int32 nOffset = 0; nOffset < nNewRows; nOffset++ )
588cdf0e10cSrcweir 			{
589cdf0e10cSrcweir 				Reference< XPropertySet >( xRows->getByIndex( aEnd.mnRow + nOffset + 1 ), UNO_QUERY_THROW )->
590cdf0e10cSrcweir 					setPropertyValue( sSize,
591cdf0e10cSrcweir 						Reference< XPropertySet >( xRows->getByIndex( aStart.mnRow + nOffset ), UNO_QUERY_THROW )->
592cdf0e10cSrcweir 							getPropertyValue( sSize ) );
593cdf0e10cSrcweir 			}
594cdf0e10cSrcweir 
595cdf0e10cSrcweir 			if( bUndo )
596cdf0e10cSrcweir 				mpModel->EndUndo();
597cdf0e10cSrcweir 
598cdf0e10cSrcweir 			aStart.mnCol = 0;
599cdf0e10cSrcweir 			aStart.mnRow = nNewRowStart;
600cdf0e10cSrcweir 			aEnd.mnCol = mxTable->getColumnCount() - 1;
601cdf0e10cSrcweir 			aEnd.mnRow = aStart.mnRow + nNewRows - 1;
602cdf0e10cSrcweir 			break;
603cdf0e10cSrcweir 		}
604cdf0e10cSrcweir 		}
605cdf0e10cSrcweir 
606cdf0e10cSrcweir 		StartSelection( aStart );
607cdf0e10cSrcweir 		UpdateSelection( aEnd );
608cdf0e10cSrcweir 	}
609cdf0e10cSrcweir 	catch( Exception& e )
610cdf0e10cSrcweir 	{
611cdf0e10cSrcweir 		(void)e;
612cdf0e10cSrcweir 		DBG_ERROR("svx::SvxTableController::onInsert(), exception caught!");
613cdf0e10cSrcweir 	}
614cdf0e10cSrcweir }
615cdf0e10cSrcweir 
616cdf0e10cSrcweir // --------------------------------------------------------------------
617cdf0e10cSrcweir 
onDelete(sal_uInt16 nSId)618cdf0e10cSrcweir void SvxTableController::onDelete( sal_uInt16 nSId )
619cdf0e10cSrcweir {
620cdf0e10cSrcweir 	::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
621cdf0e10cSrcweir 	if( !pTableObj )
622cdf0e10cSrcweir 		return;
623cdf0e10cSrcweir 
624cdf0e10cSrcweir 	if( mxTable.is() && hasSelectedCells() )
625cdf0e10cSrcweir 	{
626cdf0e10cSrcweir 		CellPos aStart, aEnd;
627cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
628cdf0e10cSrcweir 
629cdf0e10cSrcweir 		if( pTableObj->IsTextEditActive() )
630cdf0e10cSrcweir 			mpView->SdrEndTextEdit(sal_True);
631cdf0e10cSrcweir 
632cdf0e10cSrcweir 		RemoveSelection();
633cdf0e10cSrcweir 
634cdf0e10cSrcweir 		bool bDeleteTable = false;
635cdf0e10cSrcweir 		switch( nSId )
636cdf0e10cSrcweir 		{
637cdf0e10cSrcweir 		case SID_TABLE_DELETE_COL:
638cdf0e10cSrcweir 		{
639cdf0e10cSrcweir 			const sal_Int32 nRemovedColumns = aEnd.mnCol - aStart.mnCol + 1;
640cdf0e10cSrcweir 			if( nRemovedColumns == mxTable->getColumnCount() )
641cdf0e10cSrcweir 			{
642cdf0e10cSrcweir 				bDeleteTable = true;
643cdf0e10cSrcweir 			}
644cdf0e10cSrcweir 			else
645cdf0e10cSrcweir 			{
646cdf0e10cSrcweir 				Reference< XTableColumns > xCols( mxTable->getColumns() );
647cdf0e10cSrcweir 				xCols->removeByIndex( aStart.mnCol, nRemovedColumns );
648cdf0e10cSrcweir 			}
649cdf0e10cSrcweir 			break;
650cdf0e10cSrcweir 		}
651cdf0e10cSrcweir 
652cdf0e10cSrcweir 		case SID_TABLE_DELETE_ROW:
653cdf0e10cSrcweir 		{
654cdf0e10cSrcweir 			const sal_Int32 nRemovedRows = aEnd.mnRow - aStart.mnRow + 1;
655cdf0e10cSrcweir 			if( nRemovedRows == mxTable->getRowCount() )
656cdf0e10cSrcweir 			{
657cdf0e10cSrcweir 				bDeleteTable = true;
658cdf0e10cSrcweir 			}
659cdf0e10cSrcweir 			else
660cdf0e10cSrcweir 			{
661cdf0e10cSrcweir 				Reference< XTableRows > xRows( mxTable->getRows() );
662cdf0e10cSrcweir 				xRows->removeByIndex( aStart.mnRow, nRemovedRows );
663cdf0e10cSrcweir 			}
664cdf0e10cSrcweir 			break;
665cdf0e10cSrcweir 		}
666cdf0e10cSrcweir 		}
667cdf0e10cSrcweir 
668cdf0e10cSrcweir 		if( bDeleteTable )
669cdf0e10cSrcweir 			mpView->DeleteMarkedObj();
670cdf0e10cSrcweir 		else
671cdf0e10cSrcweir 			UpdateTableShape();
672cdf0e10cSrcweir 	}
673cdf0e10cSrcweir }
674cdf0e10cSrcweir 
675cdf0e10cSrcweir // --------------------------------------------------------------------
676cdf0e10cSrcweir 
onSelect(sal_uInt16 nSId)677cdf0e10cSrcweir void SvxTableController::onSelect( sal_uInt16 nSId )
678cdf0e10cSrcweir {
679cdf0e10cSrcweir 	if( mxTable.is() )
680cdf0e10cSrcweir 	{
681cdf0e10cSrcweir 		const sal_Int32 nRowCount = mxTable->getRowCount();
682cdf0e10cSrcweir 		const sal_Int32 nColCount = mxTable->getColumnCount();
683cdf0e10cSrcweir 		if( nRowCount && nColCount )
684cdf0e10cSrcweir 		{
685cdf0e10cSrcweir 			CellPos aStart, aEnd;
686cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
687cdf0e10cSrcweir 
688cdf0e10cSrcweir 			switch( nSId )
689cdf0e10cSrcweir 			{
690cdf0e10cSrcweir 			case SID_TABLE_SELECT_ALL:
691cdf0e10cSrcweir 				aEnd.mnCol = 0; aEnd.mnRow = 0;
692cdf0e10cSrcweir 				aStart.mnCol = nColCount - 1; aStart.mnRow = nRowCount - 1;
693cdf0e10cSrcweir 				break;
694cdf0e10cSrcweir 			case SID_TABLE_SELECT_COL:
695cdf0e10cSrcweir 				aEnd.mnRow = nRowCount - 1;
696cdf0e10cSrcweir 				aStart.mnRow = 0;
697cdf0e10cSrcweir 				break;
698cdf0e10cSrcweir 			case SID_TABLE_SELECT_ROW:
699cdf0e10cSrcweir 				aEnd.mnCol = nColCount - 1;
700cdf0e10cSrcweir 				aStart.mnCol = 0;
701cdf0e10cSrcweir 				break;
702cdf0e10cSrcweir 			}
703cdf0e10cSrcweir 
704cdf0e10cSrcweir 			StartSelection( aEnd );
705cdf0e10cSrcweir 			gotoCell( aStart, true, 0 );
706cdf0e10cSrcweir 		}
707cdf0e10cSrcweir 	}
708cdf0e10cSrcweir }
709cdf0e10cSrcweir 
710cdf0e10cSrcweir // --------------------------------------------------------------------
onFormatTable(SfxRequest & rReq)711cdf0e10cSrcweir void SvxTableController::onFormatTable( SfxRequest& rReq )
712cdf0e10cSrcweir {
713cdf0e10cSrcweir 	::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
714cdf0e10cSrcweir 	if( !pTableObj )
715cdf0e10cSrcweir 		return;
716cdf0e10cSrcweir 
717cdf0e10cSrcweir 	const SfxItemSet* pArgs = rReq.GetArgs();
718cdf0e10cSrcweir 
719cdf0e10cSrcweir 	if( !pArgs && pTableObj->GetModel() )
720cdf0e10cSrcweir 	{
721cdf0e10cSrcweir 		SfxItemSet aNewAttr( pTableObj->GetModel()->GetItemPool() );
722cdf0e10cSrcweir 		MergeAttrFromSelectedCells(aNewAttr, sal_False);
723cdf0e10cSrcweir 
724cdf0e10cSrcweir 		// merge drawing layer text distance items into SvxBoxItem used by the dialog
725cdf0e10cSrcweir 		SvxBoxItem aBoxItem( static_cast< const SvxBoxItem& >( aNewAttr.Get( SDRATTR_TABLE_BORDER ) ) );
726cdf0e10cSrcweir 		aBoxItem.SetDistance( sal::static_int_cast< sal_uInt16 >( ((SdrTextLeftDistItem&)(aNewAttr.Get(SDRATTR_TEXT_LEFTDIST))).GetValue()), BOX_LINE_LEFT );
727cdf0e10cSrcweir 		aBoxItem.SetDistance( sal::static_int_cast< sal_uInt16 >( ((SdrTextRightDistItem&)(aNewAttr.Get(SDRATTR_TEXT_RIGHTDIST))).GetValue()), BOX_LINE_RIGHT );
728cdf0e10cSrcweir 		aBoxItem.SetDistance( sal::static_int_cast< sal_uInt16 >( ((SdrTextUpperDistItem&)(aNewAttr.Get(SDRATTR_TEXT_UPPERDIST))).GetValue()), BOX_LINE_TOP );
729cdf0e10cSrcweir 		aBoxItem.SetDistance( sal::static_int_cast< sal_uInt16 >( ((SdrTextLowerDistItem&)(aNewAttr.Get(SDRATTR_TEXT_LOWERDIST))).GetValue()), BOX_LINE_BOTTOM );
730cdf0e10cSrcweir 		aNewAttr.Put( aBoxItem );
731cdf0e10cSrcweir 
732cdf0e10cSrcweir 		SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
733cdf0e10cSrcweir 		std::auto_ptr< SfxAbstractTabDialog > pDlg( pFact ? pFact->CreateSvxFormatCellsDialog( NULL, &aNewAttr, pTableObj->GetModel(), pTableObj) : 0 );
734cdf0e10cSrcweir 		if( pDlg.get() && pDlg->Execute() )
735cdf0e10cSrcweir 		{
736cdf0e10cSrcweir 			SfxItemSet aNewSet( *(pDlg->GetOutputItemSet ()) );
737cdf0e10cSrcweir 
738cdf0e10cSrcweir 			SvxBoxItem aNewBoxItem( static_cast< const SvxBoxItem& >( aNewSet.Get( SDRATTR_TABLE_BORDER ) ) );
739cdf0e10cSrcweir 
740cdf0e10cSrcweir 			if( aNewBoxItem.GetDistance( BOX_LINE_LEFT ) != aBoxItem.GetDistance( BOX_LINE_LEFT ) )
741cdf0e10cSrcweir 				aNewSet.Put(SdrTextLeftDistItem( aNewBoxItem.GetDistance( BOX_LINE_LEFT ) ) );
742cdf0e10cSrcweir 
743cdf0e10cSrcweir 			if( aNewBoxItem.GetDistance( BOX_LINE_RIGHT ) != aBoxItem.GetDistance( BOX_LINE_RIGHT ) )
744cdf0e10cSrcweir 				aNewSet.Put(SdrTextRightDistItem( aNewBoxItem.GetDistance( BOX_LINE_RIGHT ) ) );
745cdf0e10cSrcweir 
746cdf0e10cSrcweir 			if( aNewBoxItem.GetDistance( BOX_LINE_TOP ) != aBoxItem.GetDistance( BOX_LINE_TOP ) )
747cdf0e10cSrcweir 				aNewSet.Put(SdrTextUpperDistItem( aNewBoxItem.GetDistance( BOX_LINE_TOP ) ) );
748cdf0e10cSrcweir 
749cdf0e10cSrcweir 			if( aNewBoxItem.GetDistance( BOX_LINE_BOTTOM ) != aBoxItem.GetDistance( BOX_LINE_BOTTOM ) )
750cdf0e10cSrcweir 				aNewSet.Put(SdrTextLowerDistItem( aNewBoxItem.GetDistance( BOX_LINE_BOTTOM ) ) );
751cdf0e10cSrcweir 
752cdf0e10cSrcweir 			SetAttrToSelectedCells(aNewSet, sal_False);
753cdf0e10cSrcweir 		}
754cdf0e10cSrcweir 		UpdateTableShape();
755cdf0e10cSrcweir 	}
756cdf0e10cSrcweir }
757cdf0e10cSrcweir 
758cdf0e10cSrcweir // --------------------------------------------------------------------
759cdf0e10cSrcweir 
Execute(SfxRequest & rReq)760cdf0e10cSrcweir void SvxTableController::Execute( SfxRequest& rReq )
761cdf0e10cSrcweir {
762cdf0e10cSrcweir 	const sal_uInt16 nSId = rReq.GetSlot();
763cdf0e10cSrcweir 	switch( nSId )
764cdf0e10cSrcweir 	{
765cdf0e10cSrcweir 	case SID_TABLE_INSERT_ROW:
766cdf0e10cSrcweir 	case SID_TABLE_INSERT_COL:
767cdf0e10cSrcweir 		onInsert( nSId, rReq.GetArgs() );
768cdf0e10cSrcweir 		break;
769cdf0e10cSrcweir 	case SID_TABLE_DELETE_ROW:
770cdf0e10cSrcweir 	case SID_TABLE_DELETE_COL:
771cdf0e10cSrcweir 		onDelete( nSId );
772cdf0e10cSrcweir 		break;
773cdf0e10cSrcweir 	case SID_TABLE_SELECT_ALL:
774cdf0e10cSrcweir 	case SID_TABLE_SELECT_COL:
775cdf0e10cSrcweir 	case SID_TABLE_SELECT_ROW:
776cdf0e10cSrcweir 		onSelect( nSId );
777cdf0e10cSrcweir 		break;
778cdf0e10cSrcweir 	case SID_FORMAT_TABLE_DLG:
779cdf0e10cSrcweir 		onFormatTable( rReq );
780cdf0e10cSrcweir 		break;
781cdf0e10cSrcweir 
782cdf0e10cSrcweir 	case SID_FRAME_LINESTYLE:
783cdf0e10cSrcweir 	case SID_FRAME_LINECOLOR:
784cdf0e10cSrcweir 	case SID_ATTR_BORDER:
785cdf0e10cSrcweir 		{
786cdf0e10cSrcweir 			const SfxItemSet* pArgs = rReq.GetArgs();
787cdf0e10cSrcweir 			if( pArgs )
788cdf0e10cSrcweir 				ApplyBorderAttr( *pArgs );
789cdf0e10cSrcweir 		}
790cdf0e10cSrcweir 		break;
791cdf0e10cSrcweir 
792cdf0e10cSrcweir 	case SID_ATTR_FILL_STYLE:
793cdf0e10cSrcweir 		{
794cdf0e10cSrcweir 			const SfxItemSet* pArgs = rReq.GetArgs();
795cdf0e10cSrcweir 			if( pArgs )
796cdf0e10cSrcweir 				SetAttributes( *pArgs, false );
797cdf0e10cSrcweir 		}
798cdf0e10cSrcweir 		break;
799cdf0e10cSrcweir 
800cdf0e10cSrcweir 	case SID_TABLE_MERGE_CELLS:
801cdf0e10cSrcweir 		MergeMarkedCells();
802cdf0e10cSrcweir 		break;
803cdf0e10cSrcweir 
804cdf0e10cSrcweir 	case SID_TABLE_SPLIT_CELLS:
805cdf0e10cSrcweir 		SplitMarkedCells();
806cdf0e10cSrcweir 		break;
807cdf0e10cSrcweir 
808cdf0e10cSrcweir 	case SID_TABLE_DISTRIBUTE_COLUMNS:
809cdf0e10cSrcweir 		DistributeColumns();
810cdf0e10cSrcweir 		break;
811cdf0e10cSrcweir 
812cdf0e10cSrcweir 	case SID_TABLE_DISTRIBUTE_ROWS:
813cdf0e10cSrcweir 		DistributeRows();
814cdf0e10cSrcweir 		break;
815cdf0e10cSrcweir 
816cdf0e10cSrcweir 	case SID_TABLE_VERT_BOTTOM:
817cdf0e10cSrcweir 	case SID_TABLE_VERT_CENTER:
818cdf0e10cSrcweir 	case SID_TABLE_VERT_NONE:
819cdf0e10cSrcweir 		SetVertical( nSId );
820cdf0e10cSrcweir 		break;
821cdf0e10cSrcweir 
822cdf0e10cSrcweir 	case SID_AUTOFORMAT:
823cdf0e10cSrcweir 	case SID_TABLE_SORT_DIALOG:
824cdf0e10cSrcweir 	case SID_TABLE_AUTOSUM:
825cdf0e10cSrcweir 	default:
826cdf0e10cSrcweir 		break;
827cdf0e10cSrcweir 
828cdf0e10cSrcweir 	case SID_TABLE_STYLE:
829cdf0e10cSrcweir 		SetTableStyle( rReq.GetArgs() );
830cdf0e10cSrcweir 		break;
831cdf0e10cSrcweir 
832cdf0e10cSrcweir 	case SID_TABLE_STYLE_SETTINGS:
833cdf0e10cSrcweir 		SetTableStyleSettings( rReq.GetArgs() );
834cdf0e10cSrcweir 		break;
835cdf0e10cSrcweir 	}
836cdf0e10cSrcweir }
837cdf0e10cSrcweir 
SetTableStyle(const SfxItemSet * pArgs)838cdf0e10cSrcweir void SvxTableController::SetTableStyle( const SfxItemSet* pArgs )
839cdf0e10cSrcweir {
840cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
841cdf0e10cSrcweir 	SdrModel* pModel = pTableObj ? pTableObj->GetModel() : 0;
842cdf0e10cSrcweir 
843cdf0e10cSrcweir 	if( !pTableObj || !pModel || !pArgs || (SFX_ITEM_SET != pArgs->GetItemState(SID_TABLE_STYLE, sal_False)) )
844cdf0e10cSrcweir 		return;
845cdf0e10cSrcweir 
846cdf0e10cSrcweir 	const SfxStringItem* pArg = dynamic_cast< const SfxStringItem* >( &pArgs->Get( SID_TABLE_STYLE ) );
847cdf0e10cSrcweir 	if( pArg && mxTable.is() ) try
848cdf0e10cSrcweir 	{
849cdf0e10cSrcweir 		Reference< XStyleFamiliesSupplier > xSFS( pModel->getUnoModel(), UNO_QUERY_THROW );
850cdf0e10cSrcweir 		Reference< XNameAccess > xFamilyNameAccess( xSFS->getStyleFamilies(), UNO_QUERY_THROW );
851cdf0e10cSrcweir 		const OUString sFamilyName( RTL_CONSTASCII_USTRINGPARAM( "table" ) );
852cdf0e10cSrcweir 		Reference< XNameAccess > xTableFamilyAccess( xFamilyNameAccess->getByName( sFamilyName ), UNO_QUERY_THROW );
853cdf0e10cSrcweir 
854cdf0e10cSrcweir 		if( xTableFamilyAccess->hasByName( pArg->GetValue() ) )
855cdf0e10cSrcweir 		{
856cdf0e10cSrcweir 			// found table style with the same name
857cdf0e10cSrcweir 			Reference< XIndexAccess > xNewTableStyle( xTableFamilyAccess->getByName( pArg->GetValue() ), UNO_QUERY_THROW );
858cdf0e10cSrcweir 
859cdf0e10cSrcweir 			const bool bUndo = pModel->IsUndoEnabled();
860cdf0e10cSrcweir 
861cdf0e10cSrcweir 			if( bUndo )
862cdf0e10cSrcweir 			{
863cdf0e10cSrcweir 				pModel->BegUndo( ImpGetResStr(STR_TABLE_STYLE) );
864cdf0e10cSrcweir 				pModel->AddUndo( new TableStyleUndo( *pTableObj ) );
865cdf0e10cSrcweir 			}
866cdf0e10cSrcweir 
867cdf0e10cSrcweir 			pTableObj->setTableStyle( xNewTableStyle );
868cdf0e10cSrcweir 
869cdf0e10cSrcweir 			const sal_Int32 nRowCount = mxTable->getRowCount();
870cdf0e10cSrcweir 			const sal_Int32 nColCount = mxTable->getColumnCount();
871cdf0e10cSrcweir 			for( sal_Int32 nRow = 0; nRow < nRowCount; nRow++ )
872cdf0e10cSrcweir 			{
873cdf0e10cSrcweir 				for( sal_Int32 nCol = 0; nCol < nColCount; nCol++ ) try
874cdf0e10cSrcweir 				{
875cdf0e10cSrcweir 					CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
876cdf0e10cSrcweir 					if( xCell.is() )
877cdf0e10cSrcweir 					{
878cdf0e10cSrcweir                         SfxItemSet aSet( xCell->GetItemSet() );
879cdf0e10cSrcweir                         bool bChanges = false;
880cdf0e10cSrcweir 	                    const SfxItemSet& rStyleAttribs = xCell->GetStyleSheet()->GetItemSet();
881cdf0e10cSrcweir 
882cdf0e10cSrcweir 	                    for ( sal_uInt16 nWhich = SDRATTR_START; nWhich <= SDRATTR_TABLE_LAST; nWhich++ )
883cdf0e10cSrcweir 	                    {
884cdf0e10cSrcweir 		                    if( (rStyleAttribs.GetItemState( nWhich ) == SFX_ITEM_ON) && (aSet.GetItemState( nWhich ) == SFX_ITEM_ON) )
885cdf0e10cSrcweir 		                    {
886cdf0e10cSrcweir 			                    aSet.ClearItem( nWhich );
887cdf0e10cSrcweir 			                    bChanges = true;
888cdf0e10cSrcweir 			                }
889cdf0e10cSrcweir 	                    }
890cdf0e10cSrcweir 
891cdf0e10cSrcweir 	                    if( bChanges )
892cdf0e10cSrcweir 	                    {
893cdf0e10cSrcweir 						    if( bUndo )
894cdf0e10cSrcweir 							    xCell->AddUndo();
895cdf0e10cSrcweir 
896cdf0e10cSrcweir 							xCell->SetMergedItemSetAndBroadcast( aSet, sal_True );
897cdf0e10cSrcweir 	                    }
898cdf0e10cSrcweir                     }
899cdf0e10cSrcweir 				}
900cdf0e10cSrcweir 				catch( Exception& e )
901cdf0e10cSrcweir 				{
902cdf0e10cSrcweir 					(void)e;
903cdf0e10cSrcweir 					DBG_ERROR( "svx::SvxTableController::SetTableStyle(), exception caught!" );
904cdf0e10cSrcweir 				}
905cdf0e10cSrcweir 			}
906cdf0e10cSrcweir 
907cdf0e10cSrcweir 			if( bUndo )
908cdf0e10cSrcweir 				pModel->EndUndo();
909cdf0e10cSrcweir 		}
910cdf0e10cSrcweir 	}
911cdf0e10cSrcweir 	catch( Exception& e )
912cdf0e10cSrcweir 	{
913cdf0e10cSrcweir 		(void)e;
914cdf0e10cSrcweir 		DBG_ERROR( "svx::SvxTableController::SetTableStyle(), exception caught!" );
915cdf0e10cSrcweir 	}
916cdf0e10cSrcweir }
917cdf0e10cSrcweir 
SetTableStyleSettings(const SfxItemSet * pArgs)918cdf0e10cSrcweir void SvxTableController::SetTableStyleSettings( const SfxItemSet* pArgs )
919cdf0e10cSrcweir {
920cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
921cdf0e10cSrcweir 	SdrModel* pModel = pTableObj ? pTableObj->GetModel() : 0;
922cdf0e10cSrcweir 
923cdf0e10cSrcweir 	if( !pTableObj || !pModel )
924cdf0e10cSrcweir 		return;
925cdf0e10cSrcweir 
926cdf0e10cSrcweir 	TableStyleSettings aSettings( pTableObj->getTableStyleSettings() );
927cdf0e10cSrcweir 
928cdf0e10cSrcweir 	const SfxPoolItem *pPoolItem=NULL;
929cdf0e10cSrcweir 
930cdf0e10cSrcweir 	if( (SFX_ITEM_SET == pArgs->GetItemState(ID_VAL_USEFIRSTROWSTYLE, sal_False,&pPoolItem)) )
931cdf0e10cSrcweir 		aSettings.mbUseFirstRow = static_cast< const SfxBoolItem* >(pPoolItem)->GetValue();
932cdf0e10cSrcweir 
933cdf0e10cSrcweir 	if( (SFX_ITEM_SET == pArgs->GetItemState(ID_VAL_USELASTROWSTYLE, sal_False,&pPoolItem)) )
934cdf0e10cSrcweir 		aSettings.mbUseLastRow = static_cast< const SfxBoolItem* >(pPoolItem)->GetValue();
935cdf0e10cSrcweir 
936cdf0e10cSrcweir 	if( (SFX_ITEM_SET == pArgs->GetItemState(ID_VAL_USEBANDINGROWSTYLE, sal_False,&pPoolItem)) )
937cdf0e10cSrcweir 		aSettings.mbUseRowBanding = static_cast< const SfxBoolItem* >(pPoolItem)->GetValue();
938cdf0e10cSrcweir 
939cdf0e10cSrcweir 	if( (SFX_ITEM_SET == pArgs->GetItemState(ID_VAL_USEFIRSTCOLUMNSTYLE, sal_False,&pPoolItem)) )
940cdf0e10cSrcweir 		aSettings.mbUseFirstColumn = static_cast< const SfxBoolItem* >(pPoolItem)->GetValue();
941cdf0e10cSrcweir 
942cdf0e10cSrcweir 	if( (SFX_ITEM_SET == pArgs->GetItemState(ID_VAL_USELASTCOLUMNSTYLE, sal_False,&pPoolItem)) )
943cdf0e10cSrcweir 		aSettings.mbUseLastColumn = static_cast< const SfxBoolItem* >(pPoolItem)->GetValue();
944cdf0e10cSrcweir 
945cdf0e10cSrcweir 	if( (SFX_ITEM_SET == pArgs->GetItemState(ID_VAL_USEBANDINGCOLUMNSTYLE, sal_False,&pPoolItem)) )
946cdf0e10cSrcweir 		aSettings.mbUseColumnBanding = static_cast< const SfxBoolItem* >(pPoolItem)->GetValue();
947cdf0e10cSrcweir 
948cdf0e10cSrcweir 	if( aSettings == pTableObj->getTableStyleSettings() )
949cdf0e10cSrcweir 		return;
950cdf0e10cSrcweir 
951cdf0e10cSrcweir 	const bool bUndo = pModel->IsUndoEnabled();
952cdf0e10cSrcweir 
953cdf0e10cSrcweir 	if( bUndo )
954cdf0e10cSrcweir 	{
955cdf0e10cSrcweir 		pModel->BegUndo( ImpGetResStr(STR_TABLE_STYLE_SETTINGS) );
956cdf0e10cSrcweir 		pModel->AddUndo( new TableStyleUndo( *pTableObj ) );
957cdf0e10cSrcweir 	}
958cdf0e10cSrcweir 
959cdf0e10cSrcweir 	pTableObj->setTableStyleSettings( aSettings );
960cdf0e10cSrcweir 
961cdf0e10cSrcweir 	if( bUndo )
962cdf0e10cSrcweir 		pModel->EndUndo();
963cdf0e10cSrcweir }
964cdf0e10cSrcweir 
SetVertical(sal_uInt16 nSId)965cdf0e10cSrcweir void SvxTableController::SetVertical( sal_uInt16 nSId )
966cdf0e10cSrcweir {
967cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
968cdf0e10cSrcweir 	if( mxTable.is() && pTableObj )
969cdf0e10cSrcweir 	{
970cdf0e10cSrcweir 		TableModelNotifyGuard aGuard( mxTable.get() );
971cdf0e10cSrcweir 
972cdf0e10cSrcweir 		CellPos aStart, aEnd;
973cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
974cdf0e10cSrcweir 
975cdf0e10cSrcweir 		SdrTextVertAdjust eAdj = SDRTEXTVERTADJUST_TOP;
976cdf0e10cSrcweir 
977cdf0e10cSrcweir 		switch( nSId )
978cdf0e10cSrcweir 		{
979cdf0e10cSrcweir 			case SID_TABLE_VERT_BOTTOM:
980cdf0e10cSrcweir 				eAdj = SDRTEXTVERTADJUST_BOTTOM;
981cdf0e10cSrcweir 				break;
982cdf0e10cSrcweir 			case SID_TABLE_VERT_CENTER:
983cdf0e10cSrcweir 				eAdj = SDRTEXTVERTADJUST_CENTER;
984cdf0e10cSrcweir 				break;
985cdf0e10cSrcweir 			//case SID_TABLE_VERT_NONE:
986cdf0e10cSrcweir 			default:
987cdf0e10cSrcweir 				break;
988cdf0e10cSrcweir 		}
989cdf0e10cSrcweir 
990cdf0e10cSrcweir 		SdrTextVertAdjustItem aItem( eAdj );
991cdf0e10cSrcweir 
992cdf0e10cSrcweir 		for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
993cdf0e10cSrcweir 		{
994cdf0e10cSrcweir 			for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
995cdf0e10cSrcweir 			{
996cdf0e10cSrcweir 				CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
997cdf0e10cSrcweir 				if( xCell.is() )
998cdf0e10cSrcweir 					xCell->SetMergedItem(aItem);
999cdf0e10cSrcweir 			}
1000cdf0e10cSrcweir 		}
1001cdf0e10cSrcweir 
1002cdf0e10cSrcweir 		UpdateTableShape();
1003cdf0e10cSrcweir 	}
1004cdf0e10cSrcweir }
1005cdf0e10cSrcweir 
MergeMarkedCells()1006cdf0e10cSrcweir void SvxTableController::MergeMarkedCells()
1007cdf0e10cSrcweir {
1008cdf0e10cSrcweir 	CellPos aStart, aEnd;
1009cdf0e10cSrcweir 	getSelectedCells( aStart, aEnd );
1010cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
1011cdf0e10cSrcweir 	if( pTableObj )
1012cdf0e10cSrcweir 	{
1013cdf0e10cSrcweir 	    if( pTableObj->IsTextEditActive() )
1014cdf0e10cSrcweir 		    mpView->SdrEndTextEdit(sal_True);
1015cdf0e10cSrcweir 
1016cdf0e10cSrcweir         TableModelNotifyGuard aGuard( mxTable.get() );
1017cdf0e10cSrcweir 		MergeRange( aStart.mnCol, aStart.mnRow, aEnd.mnCol, aEnd.mnRow );
1018cdf0e10cSrcweir 	}
1019cdf0e10cSrcweir }
1020cdf0e10cSrcweir 
SplitMarkedCells()1021cdf0e10cSrcweir void SvxTableController::SplitMarkedCells()
1022cdf0e10cSrcweir {
1023cdf0e10cSrcweir 	if( mxTable.is() )
1024cdf0e10cSrcweir 	{
1025cdf0e10cSrcweir 		CellPos aStart, aEnd;
1026cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
1027cdf0e10cSrcweir 
1028cdf0e10cSrcweir 		SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
1029cdf0e10cSrcweir 		std::auto_ptr< SvxAbstractSplittTableDialog > xDlg( pFact ? pFact->CreateSvxSplittTableDialog( NULL, false, 99, 99 ) : 0 );
1030cdf0e10cSrcweir 		if( xDlg.get() && xDlg->Execute() )
1031cdf0e10cSrcweir 		{
1032cdf0e10cSrcweir 			const sal_Int32 nCount = xDlg->GetCount() - 1;
1033cdf0e10cSrcweir 			if( nCount < 1 )
1034cdf0e10cSrcweir 				return;
1035cdf0e10cSrcweir 
1036cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
1037cdf0e10cSrcweir 
1038cdf0e10cSrcweir 			Reference< XMergeableCellRange > xRange( mxTable->createCursorByRange( mxTable->getCellRangeByPosition( aStart.mnCol, aStart.mnRow, aEnd.mnCol, aEnd.mnRow ) ), UNO_QUERY_THROW );
1039cdf0e10cSrcweir 
1040cdf0e10cSrcweir 			const sal_Int32 nRowCount = mxTable->getRowCount();
1041cdf0e10cSrcweir 			const sal_Int32 nColCount = mxTable->getColumnCount();
1042cdf0e10cSrcweir 
1043cdf0e10cSrcweir 
1044cdf0e10cSrcweir 			SdrTableObj* pTableObj = dynamic_cast< SdrTableObj* >( mxTableObj.get() );
1045cdf0e10cSrcweir 			if( pTableObj )
1046cdf0e10cSrcweir 			{
1047cdf0e10cSrcweir         	    if( pTableObj->IsTextEditActive() )
1048cdf0e10cSrcweir 		            mpView->SdrEndTextEdit(sal_True);
1049cdf0e10cSrcweir 
1050cdf0e10cSrcweir                 TableModelNotifyGuard aGuard( mxTable.get() );
1051cdf0e10cSrcweir 
1052cdf0e10cSrcweir 				const bool bUndo = mpModel && mpModel->IsUndoEnabled();
1053cdf0e10cSrcweir 				if( bUndo )
1054cdf0e10cSrcweir 				{
1055cdf0e10cSrcweir 					mpModel->BegUndo( ImpGetResStr(STR_TABLE_SPLIT) );
1056cdf0e10cSrcweir 					mpModel->AddUndo( mpModel->GetSdrUndoFactory().CreateUndoGeoObject(*pTableObj) );
1057cdf0e10cSrcweir 				}
1058cdf0e10cSrcweir 
1059cdf0e10cSrcweir 				if( xDlg->IsHorizontal() )
1060cdf0e10cSrcweir 				{
1061cdf0e10cSrcweir 					xRange->split( 0, nCount );
1062cdf0e10cSrcweir 				}
1063cdf0e10cSrcweir 				else
1064cdf0e10cSrcweir 				{
1065cdf0e10cSrcweir 					xRange->split( nCount, 0 );
1066cdf0e10cSrcweir 				}
1067cdf0e10cSrcweir 
1068cdf0e10cSrcweir 				if( bUndo )
1069cdf0e10cSrcweir 					mpModel->EndUndo();
1070cdf0e10cSrcweir 			}
1071cdf0e10cSrcweir 			aEnd.mnRow += mxTable->getRowCount() - nRowCount;
1072cdf0e10cSrcweir 			aEnd.mnCol += mxTable->getColumnCount() - nColCount;
1073cdf0e10cSrcweir 
1074cdf0e10cSrcweir 			setSelectedCells( aStart, aEnd );
1075cdf0e10cSrcweir 		}
1076cdf0e10cSrcweir 	}
1077cdf0e10cSrcweir }
1078cdf0e10cSrcweir 
DistributeColumns()1079cdf0e10cSrcweir void SvxTableController::DistributeColumns()
1080cdf0e10cSrcweir {
1081cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< SdrTableObj* >( mxTableObj.get() );
1082cdf0e10cSrcweir 	if( pTableObj )
1083cdf0e10cSrcweir 	{
1084cdf0e10cSrcweir 		const bool bUndo = mpModel && mpModel->IsUndoEnabled();
1085cdf0e10cSrcweir 		if( bUndo )
1086cdf0e10cSrcweir 		{
1087cdf0e10cSrcweir 			mpModel->BegUndo( ImpGetResStr(STR_TABLE_DISTRIBUTE_COLUMNS) );
1088cdf0e10cSrcweir 			mpModel->AddUndo( mpModel->GetSdrUndoFactory().CreateUndoGeoObject(*pTableObj) );
1089cdf0e10cSrcweir 		}
1090cdf0e10cSrcweir 
1091cdf0e10cSrcweir 		CellPos aStart, aEnd;
1092cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
1093cdf0e10cSrcweir 		pTableObj->DistributeColumns( aStart.mnCol, aEnd.mnCol );
1094cdf0e10cSrcweir 
1095cdf0e10cSrcweir 		if( bUndo )
1096cdf0e10cSrcweir 			mpModel->EndUndo();
1097cdf0e10cSrcweir 	}
1098cdf0e10cSrcweir }
1099cdf0e10cSrcweir 
DistributeRows()1100cdf0e10cSrcweir void SvxTableController::DistributeRows()
1101cdf0e10cSrcweir {
1102cdf0e10cSrcweir 	SdrTableObj* pTableObj = dynamic_cast< SdrTableObj* >( mxTableObj.get() );
1103cdf0e10cSrcweir 	if( pTableObj )
1104cdf0e10cSrcweir 	{
1105cdf0e10cSrcweir 		const bool bUndo = mpModel && mpModel->IsUndoEnabled();
1106cdf0e10cSrcweir 		if( bUndo )
1107cdf0e10cSrcweir 		{
1108cdf0e10cSrcweir 			mpModel->BegUndo( ImpGetResStr(STR_TABLE_DISTRIBUTE_ROWS) );
1109cdf0e10cSrcweir 			mpModel->AddUndo( mpModel->GetSdrUndoFactory().CreateUndoGeoObject(*pTableObj) );
1110cdf0e10cSrcweir 		}
1111cdf0e10cSrcweir 
1112cdf0e10cSrcweir 		CellPos aStart, aEnd;
1113cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
1114cdf0e10cSrcweir 		pTableObj->DistributeRows( aStart.mnRow, aEnd.mnRow );
1115cdf0e10cSrcweir 
1116cdf0e10cSrcweir 		if( bUndo )
1117cdf0e10cSrcweir 			mpModel->EndUndo();
1118cdf0e10cSrcweir 	}
1119cdf0e10cSrcweir }
1120cdf0e10cSrcweir 
DeleteMarked()1121cdf0e10cSrcweir bool SvxTableController::DeleteMarked()
1122cdf0e10cSrcweir {
1123cdf0e10cSrcweir 	if( mbCellSelectionMode )
1124cdf0e10cSrcweir 	{
1125cdf0e10cSrcweir 		if( mxTable.is() )
1126cdf0e10cSrcweir 		{
1127cdf0e10cSrcweir 			CellPos aStart, aEnd;
1128cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
1129cdf0e10cSrcweir 			for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
1130cdf0e10cSrcweir 			{
1131cdf0e10cSrcweir 				for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
1132cdf0e10cSrcweir 				{
1133cdf0e10cSrcweir 					CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
1134cdf0e10cSrcweir 					if( xCell.is() )
1135cdf0e10cSrcweir 						xCell->SetOutlinerParaObject( 0 );
1136cdf0e10cSrcweir 				}
1137cdf0e10cSrcweir 			}
1138cdf0e10cSrcweir 
1139cdf0e10cSrcweir 			UpdateTableShape();
1140cdf0e10cSrcweir 			return true;
1141cdf0e10cSrcweir 		}
1142cdf0e10cSrcweir 	}
1143cdf0e10cSrcweir 
1144cdf0e10cSrcweir 	return false;
1145cdf0e10cSrcweir }
1146cdf0e10cSrcweir 
GetStyleSheet(SfxStyleSheet * & rpStyleSheet) const1147cdf0e10cSrcweir bool SvxTableController::GetStyleSheet( SfxStyleSheet*& rpStyleSheet ) const
1148cdf0e10cSrcweir {
1149cdf0e10cSrcweir 	if( hasSelectedCells() )
1150cdf0e10cSrcweir 	{
1151cdf0e10cSrcweir 		rpStyleSheet = 0;
1152cdf0e10cSrcweir 
1153cdf0e10cSrcweir 		if( mxTable.is() )
1154cdf0e10cSrcweir 		{
1155cdf0e10cSrcweir 			SfxStyleSheet* pRet=0;
1156cdf0e10cSrcweir 			bool b1st=true;
1157cdf0e10cSrcweir 
1158cdf0e10cSrcweir 			CellPos aStart, aEnd;
1159cdf0e10cSrcweir 			const_cast<SvxTableController&>(*this).getSelectedCells( aStart, aEnd );
1160cdf0e10cSrcweir 
1161cdf0e10cSrcweir 			for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
1162cdf0e10cSrcweir 			{
1163cdf0e10cSrcweir 				for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
1164cdf0e10cSrcweir 				{
1165cdf0e10cSrcweir 					CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
1166cdf0e10cSrcweir 					if( xCell.is() )
1167cdf0e10cSrcweir 					{
1168cdf0e10cSrcweir 						SfxStyleSheet* pSS=xCell->GetStyleSheet();
1169cdf0e10cSrcweir 						if(b1st)
1170cdf0e10cSrcweir 						{
1171cdf0e10cSrcweir 							pRet=pSS;
1172cdf0e10cSrcweir 						}
1173cdf0e10cSrcweir 						else if(pRet != pSS)
1174cdf0e10cSrcweir 						{
1175cdf0e10cSrcweir 							return true;
1176cdf0e10cSrcweir 						}
1177cdf0e10cSrcweir 						b1st=false;
1178cdf0e10cSrcweir 					}
1179cdf0e10cSrcweir 				}
1180cdf0e10cSrcweir 			}
1181cdf0e10cSrcweir 			rpStyleSheet = pRet;
1182cdf0e10cSrcweir 			return true;
1183cdf0e10cSrcweir 		}
1184cdf0e10cSrcweir 	}
1185cdf0e10cSrcweir 	return false;
1186cdf0e10cSrcweir }
1187cdf0e10cSrcweir 
SetStyleSheet(SfxStyleSheet * pStyleSheet,bool bDontRemoveHardAttr)1188cdf0e10cSrcweir bool SvxTableController::SetStyleSheet( SfxStyleSheet* pStyleSheet, bool bDontRemoveHardAttr )
1189cdf0e10cSrcweir {
1190cdf0e10cSrcweir 	if( hasSelectedCells() && (!pStyleSheet || pStyleSheet->GetFamily() == SFX_STYLE_FAMILY_FRAME) )
1191cdf0e10cSrcweir 	{
1192cdf0e10cSrcweir 		if( mxTable.is() )
1193cdf0e10cSrcweir 		{
1194cdf0e10cSrcweir 			CellPos aStart, aEnd;
1195cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
1196cdf0e10cSrcweir 
1197cdf0e10cSrcweir 			for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
1198cdf0e10cSrcweir 			{
1199cdf0e10cSrcweir 				for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
1200cdf0e10cSrcweir 				{
1201cdf0e10cSrcweir 					CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
1202cdf0e10cSrcweir 					if( xCell.is() )
1203cdf0e10cSrcweir 						xCell->SetStyleSheet(pStyleSheet,bDontRemoveHardAttr);
1204cdf0e10cSrcweir 				}
1205cdf0e10cSrcweir 			}
1206cdf0e10cSrcweir 
1207cdf0e10cSrcweir 			UpdateTableShape();
1208cdf0e10cSrcweir 			return true;
1209cdf0e10cSrcweir 		}
1210cdf0e10cSrcweir 	}
1211cdf0e10cSrcweir 	return false;
1212cdf0e10cSrcweir }
1213cdf0e10cSrcweir 
1214cdf0e10cSrcweir // --------------------------------------------------------------------
1215cdf0e10cSrcweir // internals
1216cdf0e10cSrcweir // --------------------------------------------------------------------
1217cdf0e10cSrcweir 
checkTableObject()1218cdf0e10cSrcweir bool SvxTableController::checkTableObject()
1219cdf0e10cSrcweir {
1220cdf0e10cSrcweir 	return mxTableObj.is();
1221cdf0e10cSrcweir }
1222cdf0e10cSrcweir 
1223cdf0e10cSrcweir // --------------------------------------------------------------------
1224cdf0e10cSrcweir 
getKeyboardAction(const KeyEvent & rKEvt,Window *)1225cdf0e10cSrcweir sal_uInt16 SvxTableController::getKeyboardAction( const KeyEvent& rKEvt, Window* /*pWindow*/ )
1226cdf0e10cSrcweir {
1227cdf0e10cSrcweir 	const bool bMod1 = rKEvt.GetKeyCode().IsMod1(); // ctrl
1228cdf0e10cSrcweir 	const bool bMod2 = rKEvt.GetKeyCode().IsMod2() != 0; // Alt
1229cdf0e10cSrcweir 
1230cdf0e10cSrcweir 	const bool bTextEdit = mpView->IsTextEdit();
1231cdf0e10cSrcweir 
1232cdf0e10cSrcweir 	sal_uInt16 nAction = ACTION_HANDLED_BY_VIEW;
1233cdf0e10cSrcweir 
1234cdf0e10cSrcweir 	::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
1235cdf0e10cSrcweir 	if( !pTableObj )
1236cdf0e10cSrcweir 		return nAction;
1237cdf0e10cSrcweir 
1238cdf0e10cSrcweir 	// handle special keys
1239cdf0e10cSrcweir 	const sal_Int16 nCode = rKEvt.GetKeyCode().GetCode();
1240cdf0e10cSrcweir 	switch( nCode )
1241cdf0e10cSrcweir 	{
1242cdf0e10cSrcweir 	case awt::Key::ESCAPE:			// handle escape
1243cdf0e10cSrcweir 	{
1244cdf0e10cSrcweir 		if( bTextEdit )
1245cdf0e10cSrcweir 		{
1246cdf0e10cSrcweir 			// escape during text edit ends text edit
1247cdf0e10cSrcweir 			nAction = ACTION_STOP_TEXT_EDIT;
1248cdf0e10cSrcweir 		}
1249cdf0e10cSrcweir 		if( mbCellSelectionMode )
1250cdf0e10cSrcweir 		{
1251cdf0e10cSrcweir 			// escape with selected cells removes selection
1252cdf0e10cSrcweir 			nAction = ACTION_REMOVE_SELECTION;
1253cdf0e10cSrcweir 		}
1254cdf0e10cSrcweir 		break;
1255cdf0e10cSrcweir 	}
1256cdf0e10cSrcweir 	case awt::Key::RETURN:		// handle return
1257cdf0e10cSrcweir 	{
1258cdf0e10cSrcweir 		if( !bMod1 && !bMod2 && !bTextEdit )
1259cdf0e10cSrcweir 		{
1260cdf0e10cSrcweir 			// when not already editing, return starts text edit
1261cdf0e10cSrcweir 			setSelectionStart( pTableObj->getFirstCell() );
1262cdf0e10cSrcweir 			nAction = ACTION_EDIT_CELL;
1263cdf0e10cSrcweir 		}
1264cdf0e10cSrcweir 		break;
1265cdf0e10cSrcweir 	}
1266cdf0e10cSrcweir 	case awt::Key::F2:			// f2 toggles text edit
1267cdf0e10cSrcweir 	{
1268cdf0e10cSrcweir 		if( bMod1 || bMod2 )	// f2 with modifiers is handled by the view
1269cdf0e10cSrcweir 		{
1270cdf0e10cSrcweir 		}
1271cdf0e10cSrcweir 		else if( bTextEdit )
1272cdf0e10cSrcweir 		{
1273cdf0e10cSrcweir 			// f2 during text edit stops text edit
1274cdf0e10cSrcweir 			nAction = ACTION_STOP_TEXT_EDIT;
1275cdf0e10cSrcweir 		}
1276cdf0e10cSrcweir 		else if( mbCellSelectionMode )
1277cdf0e10cSrcweir 		{
1278cdf0e10cSrcweir 			// f2 with selected cells removes selection
1279cdf0e10cSrcweir 			nAction = ACTION_REMOVE_SELECTION;
1280cdf0e10cSrcweir 		}
1281cdf0e10cSrcweir 		else
1282cdf0e10cSrcweir 		{
1283cdf0e10cSrcweir 			// f2 with no selection and no text edit starts text edit
1284cdf0e10cSrcweir 			setSelectionStart( pTableObj->getFirstCell() );
1285cdf0e10cSrcweir 			nAction = ACTION_EDIT_CELL;
1286cdf0e10cSrcweir 		}
1287cdf0e10cSrcweir 		break;
1288cdf0e10cSrcweir 	}
1289cdf0e10cSrcweir 	case awt::Key::HOME:
1290cdf0e10cSrcweir 	case awt::Key::NUM7:
1291cdf0e10cSrcweir 	{
1292cdf0e10cSrcweir 		if( (bMod1 ||  bMod2) && (bTextEdit || mbCellSelectionMode) )
1293cdf0e10cSrcweir 		{
1294cdf0e10cSrcweir 			if( bMod1 && !bMod2 )
1295cdf0e10cSrcweir 			{
1296cdf0e10cSrcweir 				// strg + home jumps to first cell
1297cdf0e10cSrcweir 				nAction = ACTION_GOTO_FIRST_CELL;
1298cdf0e10cSrcweir 			}
1299cdf0e10cSrcweir 			else if( !bMod1 && bMod2 )
1300cdf0e10cSrcweir 			{
1301cdf0e10cSrcweir 				// alt + home jumps to first column
1302cdf0e10cSrcweir 				nAction = ACTION_GOTO_FIRST_COLUMN;
1303cdf0e10cSrcweir 			}
1304cdf0e10cSrcweir 		}
1305cdf0e10cSrcweir 		break;
1306cdf0e10cSrcweir 	}
1307cdf0e10cSrcweir 	case awt::Key::END:
1308cdf0e10cSrcweir 	case awt::Key::NUM1:
1309cdf0e10cSrcweir 	{
1310cdf0e10cSrcweir 		if( (bMod1 ||  bMod2) && (bTextEdit || mbCellSelectionMode) )
1311cdf0e10cSrcweir 		{
1312cdf0e10cSrcweir 			if( bMod1 && !bMod2 )
1313cdf0e10cSrcweir 			{
1314cdf0e10cSrcweir 				// strg + end jumps to last cell
1315cdf0e10cSrcweir 				nAction = ACTION_GOTO_LAST_CELL;
1316cdf0e10cSrcweir 			}
1317cdf0e10cSrcweir 			else if( !bMod1 && bMod2 )
1318cdf0e10cSrcweir 			{
1319cdf0e10cSrcweir 				// alt + home jumps to last column
1320cdf0e10cSrcweir 				nAction = ACTION_GOTO_LAST_COLUMN;
1321cdf0e10cSrcweir 			}
1322cdf0e10cSrcweir 		}
1323cdf0e10cSrcweir 		break;
1324cdf0e10cSrcweir 	}
1325cdf0e10cSrcweir 
1326cdf0e10cSrcweir 	case awt::Key::TAB:
1327cdf0e10cSrcweir 	{
1328cdf0e10cSrcweir 		if( bTextEdit || mbCellSelectionMode )
1329cdf0e10cSrcweir 			nAction = ACTION_TAB;
1330cdf0e10cSrcweir 		break;
1331cdf0e10cSrcweir 	}
1332cdf0e10cSrcweir 
1333cdf0e10cSrcweir 	case awt::Key::UP:
1334cdf0e10cSrcweir 	case awt::Key::NUM8:
1335cdf0e10cSrcweir 	case awt::Key::DOWN:
1336cdf0e10cSrcweir 	case awt::Key::NUM2:
1337cdf0e10cSrcweir 	case awt::Key::LEFT:
1338cdf0e10cSrcweir 	case awt::Key::NUM4:
1339cdf0e10cSrcweir 	case awt::Key::RIGHT:
1340cdf0e10cSrcweir 	case awt::Key::NUM6:
1341cdf0e10cSrcweir 	{
1342cdf0e10cSrcweir 		bool bTextMove = false;
1343cdf0e10cSrcweir 
1344cdf0e10cSrcweir 		if( !bMod1 && bMod2 )
1345cdf0e10cSrcweir 		{
1346cdf0e10cSrcweir 			if( (nCode == awt::Key::UP) || (nCode == awt::Key::NUM8) )
1347cdf0e10cSrcweir 			{
1348cdf0e10cSrcweir 				nAction = ACTION_GOTO_LEFT_CELL;
1349cdf0e10cSrcweir 			}
1350cdf0e10cSrcweir 			else if( (nCode == awt::Key::DOWN) || (nCode == awt::Key::NUM2) )
1351cdf0e10cSrcweir 			{
1352cdf0e10cSrcweir 				nAction = ACTION_GOTO_RIGHT_CELL;
1353cdf0e10cSrcweir 			}
1354cdf0e10cSrcweir 			break;
1355cdf0e10cSrcweir 		}
1356cdf0e10cSrcweir 
1357cdf0e10cSrcweir 		if( !bTextMove )
1358cdf0e10cSrcweir 		{
1359cdf0e10cSrcweir 			OutlinerView* pOLV = mpView->GetTextEditOutlinerView();
1360cdf0e10cSrcweir 			if( pOLV )
1361cdf0e10cSrcweir 			{
1362cdf0e10cSrcweir 				RemoveSelection();
1363cdf0e10cSrcweir 				// during text edit, check if we navigate out of the cell
1364cdf0e10cSrcweir 				ESelection aOldSelection = pOLV->GetSelection();
1365cdf0e10cSrcweir 				pOLV->PostKeyEvent(rKEvt);
1366cdf0e10cSrcweir 				bTextMove = pOLV && ( aOldSelection.IsEqual(pOLV->GetSelection()) );
1367cdf0e10cSrcweir 				if( !bTextMove )
1368cdf0e10cSrcweir 				{
1369cdf0e10cSrcweir 					nAction = ACTION_NONE;
1370cdf0e10cSrcweir 				}
1371cdf0e10cSrcweir 			}
1372cdf0e10cSrcweir 		}
1373cdf0e10cSrcweir 
1374cdf0e10cSrcweir 		if( mbCellSelectionMode || bTextMove )
1375cdf0e10cSrcweir 		{
1376cdf0e10cSrcweir 			// no text edit, navigate in cells if selection active
1377cdf0e10cSrcweir 			switch( nCode )
1378cdf0e10cSrcweir 			{
1379cdf0e10cSrcweir 			case awt::Key::LEFT:
1380cdf0e10cSrcweir 			case awt::Key::NUM4:
1381cdf0e10cSrcweir 				nAction = ACTION_GOTO_LEFT_CELL;
1382cdf0e10cSrcweir 				break;
1383cdf0e10cSrcweir 			case awt::Key::RIGHT:
1384cdf0e10cSrcweir 			case awt::Key::NUM6:
1385cdf0e10cSrcweir 				nAction = ACTION_GOTO_RIGHT_CELL;
1386cdf0e10cSrcweir 				break;
1387cdf0e10cSrcweir 			case awt::Key::DOWN:
1388cdf0e10cSrcweir 			case awt::Key::NUM2:
1389cdf0e10cSrcweir 				nAction = ACTION_GOTO_DOWN_CELL;
1390cdf0e10cSrcweir 				break;
1391cdf0e10cSrcweir 			case awt::Key::UP:
1392cdf0e10cSrcweir 			case awt::Key::NUM8:
1393cdf0e10cSrcweir 				nAction = ACTION_GOTO_UP_CELL;
1394cdf0e10cSrcweir 				break;
1395cdf0e10cSrcweir 			}
1396cdf0e10cSrcweir 		}
1397cdf0e10cSrcweir 		break;
1398cdf0e10cSrcweir 	}
1399cdf0e10cSrcweir 	case awt::Key::PAGEUP:
1400cdf0e10cSrcweir 		if( bMod2 )
1401cdf0e10cSrcweir 			nAction = ACTION_GOTO_FIRST_ROW;
1402cdf0e10cSrcweir 		break;
1403cdf0e10cSrcweir 
1404cdf0e10cSrcweir 	case awt::Key::PAGEDOWN:
1405cdf0e10cSrcweir 		if( bMod2 )
1406cdf0e10cSrcweir 			nAction = ACTION_GOTO_LAST_ROW;
1407cdf0e10cSrcweir 		break;
1408cdf0e10cSrcweir 	}
1409cdf0e10cSrcweir 	return nAction;
1410cdf0e10cSrcweir }
1411cdf0e10cSrcweir 
executeAction(sal_uInt16 nAction,bool bSelect,Window * pWindow)1412cdf0e10cSrcweir bool SvxTableController::executeAction( sal_uInt16 nAction, bool bSelect, Window* pWindow )
1413cdf0e10cSrcweir {
1414cdf0e10cSrcweir 	::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
1415cdf0e10cSrcweir 	if( !pTableObj )
1416cdf0e10cSrcweir 		return false;
1417cdf0e10cSrcweir 
1418cdf0e10cSrcweir 	switch( nAction )
1419cdf0e10cSrcweir 	{
1420cdf0e10cSrcweir 	case ACTION_GOTO_FIRST_CELL:
1421cdf0e10cSrcweir 	{
1422cdf0e10cSrcweir 		gotoCell( pTableObj->getFirstCell(), bSelect, pWindow, nAction );
1423cdf0e10cSrcweir 		break;
1424cdf0e10cSrcweir 	}
1425cdf0e10cSrcweir 
1426cdf0e10cSrcweir 	case ACTION_GOTO_LEFT_CELL:
1427cdf0e10cSrcweir 	{
1428cdf0e10cSrcweir 		gotoCell( pTableObj->getLeftCell( getSelectionEnd(), !bSelect ), bSelect, pWindow, nAction );
1429cdf0e10cSrcweir 		break;
1430cdf0e10cSrcweir 	}
1431cdf0e10cSrcweir 
1432cdf0e10cSrcweir 	case ACTION_GOTO_RIGHT_CELL:
1433cdf0e10cSrcweir 	{
1434cdf0e10cSrcweir 		gotoCell( pTableObj->getRightCell( getSelectionEnd(), !bSelect ), bSelect, pWindow, nAction);
1435cdf0e10cSrcweir 		break;
1436cdf0e10cSrcweir 	}
1437cdf0e10cSrcweir 
1438cdf0e10cSrcweir 	case ACTION_GOTO_LAST_CELL:
1439cdf0e10cSrcweir 	{
1440cdf0e10cSrcweir 		gotoCell( pTableObj->getLastCell(), bSelect, pWindow, nAction );
1441cdf0e10cSrcweir 		break;
1442cdf0e10cSrcweir 	}
1443cdf0e10cSrcweir 
1444cdf0e10cSrcweir 	case ACTION_GOTO_FIRST_COLUMN:
1445cdf0e10cSrcweir 	{
1446cdf0e10cSrcweir 		CellPos aPos( pTableObj->getFirstCell().mnCol, getSelectionEnd().mnRow );
1447cdf0e10cSrcweir 		gotoCell( aPos, bSelect, pWindow, nAction );
1448cdf0e10cSrcweir 		break;
1449cdf0e10cSrcweir 	}
1450cdf0e10cSrcweir 
1451cdf0e10cSrcweir 	case ACTION_GOTO_LAST_COLUMN:
1452cdf0e10cSrcweir 	{
1453cdf0e10cSrcweir 		CellPos aPos( pTableObj->getLastCell().mnCol, getSelectionEnd().mnRow );
1454cdf0e10cSrcweir 		gotoCell( aPos, bSelect, pWindow, nAction );
1455cdf0e10cSrcweir 		break;
1456cdf0e10cSrcweir 	}
1457cdf0e10cSrcweir 
1458cdf0e10cSrcweir 	case ACTION_GOTO_FIRST_ROW:
1459cdf0e10cSrcweir 	{
1460cdf0e10cSrcweir 		CellPos aPos( getSelectionEnd().mnCol, pTableObj->getFirstCell().mnRow );
1461cdf0e10cSrcweir 		gotoCell( aPos, bSelect, pWindow, nAction );
1462cdf0e10cSrcweir 		break;
1463cdf0e10cSrcweir 	}
1464cdf0e10cSrcweir 
1465cdf0e10cSrcweir 	case ACTION_GOTO_UP_CELL:
1466cdf0e10cSrcweir 	{
1467cdf0e10cSrcweir 		gotoCell( pTableObj->getUpCell(getSelectionEnd(), !bSelect), bSelect, pWindow, nAction );
1468cdf0e10cSrcweir 		break;
1469cdf0e10cSrcweir 	}
1470cdf0e10cSrcweir 
1471cdf0e10cSrcweir 	case ACTION_GOTO_DOWN_CELL:
1472cdf0e10cSrcweir 	{
1473cdf0e10cSrcweir 		gotoCell( pTableObj->getDownCell(getSelectionEnd(), !bSelect), bSelect, pWindow, nAction );
1474cdf0e10cSrcweir 		break;
1475cdf0e10cSrcweir 	}
1476cdf0e10cSrcweir 
1477cdf0e10cSrcweir 	case ACTION_GOTO_LAST_ROW:
1478cdf0e10cSrcweir 	{
1479cdf0e10cSrcweir 		CellPos aPos( getSelectionEnd().mnCol, pTableObj->getLastCell().mnRow );
1480cdf0e10cSrcweir 		gotoCell( aPos, bSelect, pWindow, nAction );
1481cdf0e10cSrcweir 		break;
1482cdf0e10cSrcweir 	}
1483cdf0e10cSrcweir 
1484cdf0e10cSrcweir 	case ACTION_EDIT_CELL:
1485cdf0e10cSrcweir 		EditCell( getSelectionStart(), pWindow, 0, nAction );
1486cdf0e10cSrcweir 		break;
1487cdf0e10cSrcweir 
1488cdf0e10cSrcweir 	case ACTION_STOP_TEXT_EDIT:
1489cdf0e10cSrcweir 		StopTextEdit();
1490cdf0e10cSrcweir 		break;
1491cdf0e10cSrcweir 
1492cdf0e10cSrcweir 	case ACTION_REMOVE_SELECTION:
1493cdf0e10cSrcweir 		RemoveSelection();
1494cdf0e10cSrcweir 		break;
1495cdf0e10cSrcweir 
1496cdf0e10cSrcweir 	case ACTION_START_SELECTION:
1497cdf0e10cSrcweir 		StartSelection( getSelectionStart() );
1498cdf0e10cSrcweir 		break;
1499cdf0e10cSrcweir 
1500cdf0e10cSrcweir 	case ACTION_TAB:
1501cdf0e10cSrcweir 	{
1502cdf0e10cSrcweir 		if( bSelect )
1503cdf0e10cSrcweir 			gotoCell( pTableObj->getPreviousCell( getSelectionEnd(), true ), false, pWindow, nAction );
1504cdf0e10cSrcweir 		else
1505cdf0e10cSrcweir         {
1506cdf0e10cSrcweir             CellPos aSelectionEnd( getSelectionEnd() );
1507cdf0e10cSrcweir             CellPos aNextCell( pTableObj->getNextCell( aSelectionEnd, true ) );
1508cdf0e10cSrcweir             if( aSelectionEnd == aNextCell )
1509cdf0e10cSrcweir             {
1510cdf0e10cSrcweir                 onInsert( SID_TABLE_INSERT_ROW, 0 );
1511cdf0e10cSrcweir                 aNextCell = pTableObj->getNextCell( aSelectionEnd, true );
1512cdf0e10cSrcweir             }
1513cdf0e10cSrcweir 			gotoCell( aNextCell, false, pWindow, nAction );
1514cdf0e10cSrcweir         }
1515cdf0e10cSrcweir 		break;
1516cdf0e10cSrcweir 	}
1517cdf0e10cSrcweir 	}
1518cdf0e10cSrcweir 
1519cdf0e10cSrcweir 	return nAction != ACTION_HANDLED_BY_VIEW;
1520cdf0e10cSrcweir }
1521cdf0e10cSrcweir 
1522cdf0e10cSrcweir // --------------------------------------------------------------------
1523cdf0e10cSrcweir 
gotoCell(const CellPos & rPos,bool bSelect,Window * pWindow,sal_uInt16 nAction)1524cdf0e10cSrcweir void SvxTableController::gotoCell( const CellPos& rPos, bool bSelect, Window* pWindow, sal_uInt16 nAction )
1525cdf0e10cSrcweir {
1526cdf0e10cSrcweir 	if( mxTableObj.is() && static_cast<SdrTableObj*>(mxTableObj.get())->IsTextEditActive() )
1527cdf0e10cSrcweir 		mpView->SdrEndTextEdit(sal_True);
1528cdf0e10cSrcweir 
1529cdf0e10cSrcweir 	if( bSelect )
1530cdf0e10cSrcweir 	{
1531cdf0e10cSrcweir 		maCursorLastPos = rPos;
1532cdf0e10cSrcweir 		if( mxTableObj.is() )
1533cdf0e10cSrcweir 			static_cast< SdrTableObj* >( mxTableObj.get() )->setActiveCell( rPos );
1534cdf0e10cSrcweir 
1535cdf0e10cSrcweir 		if( !mbCellSelectionMode )
1536cdf0e10cSrcweir 		{
1537cdf0e10cSrcweir 			setSelectedCells( maCursorFirstPos, rPos );
1538cdf0e10cSrcweir 		}
1539cdf0e10cSrcweir 		else
1540cdf0e10cSrcweir 		{
1541cdf0e10cSrcweir 			UpdateSelection( rPos );
1542cdf0e10cSrcweir 		}
1543cdf0e10cSrcweir 	}
1544cdf0e10cSrcweir 	else
1545cdf0e10cSrcweir 	{
1546cdf0e10cSrcweir 		RemoveSelection();
1547cdf0e10cSrcweir 		EditCell( rPos, pWindow, 0, nAction );
1548cdf0e10cSrcweir 	}
1549cdf0e10cSrcweir }
1550cdf0e10cSrcweir 
1551cdf0e10cSrcweir // --------------------------------------------------------------------
1552cdf0e10cSrcweir 
getSelectionStart()1553cdf0e10cSrcweir const CellPos& SvxTableController::getSelectionStart()
1554cdf0e10cSrcweir {
1555cdf0e10cSrcweir 	checkCell( maCursorFirstPos );
1556cdf0e10cSrcweir 	return maCursorFirstPos;
1557cdf0e10cSrcweir }
1558cdf0e10cSrcweir 
1559cdf0e10cSrcweir // --------------------------------------------------------------------
1560cdf0e10cSrcweir 
setSelectionStart(const CellPos & rPos)1561cdf0e10cSrcweir void SvxTableController::setSelectionStart( const CellPos& rPos )
1562cdf0e10cSrcweir {
1563cdf0e10cSrcweir 	maCursorFirstPos = rPos;
1564cdf0e10cSrcweir }
1565cdf0e10cSrcweir 
1566cdf0e10cSrcweir // --------------------------------------------------------------------
1567cdf0e10cSrcweir 
getSelectionEnd()1568cdf0e10cSrcweir const CellPos& SvxTableController::getSelectionEnd()
1569cdf0e10cSrcweir {
1570cdf0e10cSrcweir 	checkCell( maCursorLastPos );
1571cdf0e10cSrcweir 	return maCursorLastPos;
1572cdf0e10cSrcweir }
1573cdf0e10cSrcweir 
1574cdf0e10cSrcweir // --------------------------------------------------------------------
1575cdf0e10cSrcweir 
getSelectionCursor()1576cdf0e10cSrcweir Reference< XCellCursor > SvxTableController::getSelectionCursor()
1577cdf0e10cSrcweir {
1578cdf0e10cSrcweir 	Reference< XCellCursor > xCursor;
1579cdf0e10cSrcweir 
1580cdf0e10cSrcweir 	if( mxTable.is() )
1581cdf0e10cSrcweir 	{
1582cdf0e10cSrcweir 		if( hasSelectedCells() )
1583cdf0e10cSrcweir 		{
1584cdf0e10cSrcweir 			CellPos aStart, aEnd;
1585cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
1586cdf0e10cSrcweir 			xCursor = mxTable->createCursorByRange( mxTable->getCellRangeByPosition( aStart.mnCol, aStart.mnRow, aEnd.mnCol, aEnd.mnRow ) );
1587cdf0e10cSrcweir 		}
1588cdf0e10cSrcweir 		else
1589cdf0e10cSrcweir 		{
1590cdf0e10cSrcweir 			xCursor = mxTable->createCursor();
1591cdf0e10cSrcweir 		}
1592cdf0e10cSrcweir 	}
1593cdf0e10cSrcweir 
1594cdf0e10cSrcweir 	return xCursor;
1595cdf0e10cSrcweir }
1596cdf0e10cSrcweir 
MergeRange(sal_Int32 nFirstCol,sal_Int32 nFirstRow,sal_Int32 nLastCol,sal_Int32 nLastRow)1597cdf0e10cSrcweir void SvxTableController::MergeRange( sal_Int32 nFirstCol, sal_Int32 nFirstRow, sal_Int32 nLastCol, sal_Int32 nLastRow )
1598cdf0e10cSrcweir {
1599cdf0e10cSrcweir 	if( mxTable.is() ) try
1600cdf0e10cSrcweir 	{
1601cdf0e10cSrcweir 		Reference< XMergeableCellRange > xRange( mxTable->createCursorByRange( mxTable->getCellRangeByPosition( nFirstCol, nFirstRow,nLastCol, nLastRow ) ), UNO_QUERY_THROW );
1602cdf0e10cSrcweir 		if( xRange->isMergeable() )
1603cdf0e10cSrcweir 		{
1604cdf0e10cSrcweir 			const bool bUndo = mpModel && mpModel->IsUndoEnabled();
1605cdf0e10cSrcweir 			if( bUndo )
1606cdf0e10cSrcweir 			{
1607cdf0e10cSrcweir 				mpModel->BegUndo( ImpGetResStr(STR_TABLE_MERGE) );
1608cdf0e10cSrcweir 				mpModel->AddUndo( mpModel->GetSdrUndoFactory().CreateUndoGeoObject(*mxTableObj.get()) );
1609cdf0e10cSrcweir 			}
1610cdf0e10cSrcweir 
1611cdf0e10cSrcweir 			xRange->merge();
1612cdf0e10cSrcweir 
1613cdf0e10cSrcweir 			if( bUndo )
1614cdf0e10cSrcweir 				mpModel->EndUndo();
1615cdf0e10cSrcweir 		}
1616cdf0e10cSrcweir 	}
1617cdf0e10cSrcweir 	catch( Exception& )
1618cdf0e10cSrcweir 	{
1619cdf0e10cSrcweir 		DBG_ASSERT( false, "sdr::table::SvxTableController::MergeRange(), exception caught!" );
1620cdf0e10cSrcweir 	}
1621cdf0e10cSrcweir }
1622cdf0e10cSrcweir 
1623cdf0e10cSrcweir 
1624cdf0e10cSrcweir 
1625cdf0e10cSrcweir // --------------------------------------------------------------------
1626cdf0e10cSrcweir 
checkCell(CellPos & rPos)1627cdf0e10cSrcweir void SvxTableController::checkCell( CellPos& rPos )
1628cdf0e10cSrcweir {
1629cdf0e10cSrcweir 	if( mxTable.is() ) try
1630cdf0e10cSrcweir 	{
1631cdf0e10cSrcweir 		if( rPos.mnCol >= mxTable->getColumnCount() )
1632cdf0e10cSrcweir 			rPos.mnCol = mxTable->getColumnCount()-1;
1633cdf0e10cSrcweir 
1634cdf0e10cSrcweir 		if( rPos.mnRow >= mxTable->getRowCount() )
1635cdf0e10cSrcweir 			rPos.mnRow = mxTable->getRowCount()-1;
1636cdf0e10cSrcweir 	}
1637cdf0e10cSrcweir 	catch( Exception& e )
1638cdf0e10cSrcweir 	{
1639cdf0e10cSrcweir 		(void)e;
1640cdf0e10cSrcweir 		DBG_ERROR("sdr::table::SvxTableController::checkCell(), exception caught!" );
1641cdf0e10cSrcweir 	}
1642cdf0e10cSrcweir }
1643cdf0e10cSrcweir 
1644cdf0e10cSrcweir // --------------------------------------------------------------------
1645cdf0e10cSrcweir 
findMergeOrigin(CellPos & rPos)1646cdf0e10cSrcweir void SvxTableController::findMergeOrigin( CellPos& rPos )
1647cdf0e10cSrcweir {
1648cdf0e10cSrcweir 	if( mxTable.is() ) try
1649cdf0e10cSrcweir 	{
1650cdf0e10cSrcweir 		Reference< XMergeableCell > xCell( mxTable->getCellByPosition( rPos.mnCol, rPos.mnRow ), UNO_QUERY_THROW );
1651cdf0e10cSrcweir 		if( xCell.is() && xCell->isMerged() )
1652cdf0e10cSrcweir 		{
1653cdf0e10cSrcweir 			::findMergeOrigin( mxTable, rPos.mnCol, rPos.mnRow, rPos.mnCol, rPos.mnRow );
1654cdf0e10cSrcweir 		}
1655cdf0e10cSrcweir 	}
1656cdf0e10cSrcweir 	catch( Exception& e )
1657cdf0e10cSrcweir 	{
1658cdf0e10cSrcweir 		(void)e;
1659cdf0e10cSrcweir 		DBG_ERROR("sdr::table::SvxTableController::findMergeOrigin(), exception caught!" );
1660cdf0e10cSrcweir 	}
1661cdf0e10cSrcweir }
1662cdf0e10cSrcweir 
1663cdf0e10cSrcweir // --------------------------------------------------------------------
1664cdf0e10cSrcweir 
EditCell(const CellPos & rPos,::Window * pWindow,const awt::MouseEvent * pMouseEvent,sal_uInt16 nAction)1665cdf0e10cSrcweir void SvxTableController::EditCell( const CellPos& rPos, ::Window* pWindow, const awt::MouseEvent* pMouseEvent /*= 0*/, sal_uInt16 nAction /*= ACTION_NONE */ )
1666cdf0e10cSrcweir {
1667cdf0e10cSrcweir 	SdrPageView* pPV = mpView->GetSdrPageView();
1668cdf0e10cSrcweir 
1669cdf0e10cSrcweir 	::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
1670cdf0e10cSrcweir 	if( pTableObj && pTableObj->GetPage() == pPV->GetPage() )
1671cdf0e10cSrcweir 	{
1672cdf0e10cSrcweir 		bool bEmptyOutliner = false;
1673cdf0e10cSrcweir 
1674cdf0e10cSrcweir 		if(!pTableObj->GetOutlinerParaObject() && mpView->GetTextEditOutliner())
1675cdf0e10cSrcweir 		{
1676cdf0e10cSrcweir 			::Outliner* pOutl = mpView->GetTextEditOutliner();
1677cdf0e10cSrcweir 			sal_uIntPtr nParaAnz = pOutl->GetParagraphCount();
1678cdf0e10cSrcweir 			Paragraph* p1stPara = pOutl->GetParagraph( 0 );
1679cdf0e10cSrcweir 
1680cdf0e10cSrcweir 			if(nParaAnz==1 && p1stPara)
1681cdf0e10cSrcweir 			{
1682cdf0e10cSrcweir 				// Bei nur einem Pararaph
1683cdf0e10cSrcweir 				if (pOutl->GetText(p1stPara).Len() == 0)
1684cdf0e10cSrcweir 				{
1685cdf0e10cSrcweir 					bEmptyOutliner = true;
1686cdf0e10cSrcweir 				}
1687cdf0e10cSrcweir 			}
1688cdf0e10cSrcweir 		}
1689cdf0e10cSrcweir 
1690cdf0e10cSrcweir 		CellPos aPos( rPos );
1691cdf0e10cSrcweir 		findMergeOrigin( aPos );
1692cdf0e10cSrcweir 
1693cdf0e10cSrcweir 		if( pTableObj != mpView->GetTextEditObject() || bEmptyOutliner || !pTableObj->IsTextEditActive( aPos ) )
1694cdf0e10cSrcweir 		{
1695cdf0e10cSrcweir 			if( pTableObj->IsTextEditActive() )
1696cdf0e10cSrcweir 				mpView->SdrEndTextEdit(sal_True);
1697cdf0e10cSrcweir 
1698cdf0e10cSrcweir 			pTableObj->setActiveCell( aPos );
1699cdf0e10cSrcweir 
1700cdf0e10cSrcweir 			// create new outliner, owner will be the SdrObjEditView
1701cdf0e10cSrcweir 			SdrOutliner* pOutl = SdrMakeOutliner( OUTLINERMODE_OUTLINEOBJECT, mpModel );
1702cdf0e10cSrcweir 			if( pTableObj->IsVerticalWriting() )
1703cdf0e10cSrcweir 				pOutl->SetVertical( sal_True );
1704cdf0e10cSrcweir 
1705cdf0e10cSrcweir 			if(mpView->SdrBeginTextEdit(pTableObj, pPV, pWindow, sal_True, pOutl))
1706cdf0e10cSrcweir 			{
1707cdf0e10cSrcweir 				maCursorLastPos = maCursorFirstPos = rPos;
1708cdf0e10cSrcweir 
1709cdf0e10cSrcweir 				OutlinerView* pOLV = mpView->GetTextEditOutlinerView();
1710cdf0e10cSrcweir 
1711cdf0e10cSrcweir 				bool bNoSel = true;
1712cdf0e10cSrcweir 
1713cdf0e10cSrcweir 				if( pMouseEvent )
1714cdf0e10cSrcweir 				{
1715cdf0e10cSrcweir 					::MouseEvent aMEvt( *pMouseEvent );
1716cdf0e10cSrcweir 
1717cdf0e10cSrcweir 					SdrViewEvent aVEvt;
1718cdf0e10cSrcweir 					SdrHitKind eHit = mpView->PickAnything(aMEvt, SDRMOUSEBUTTONDOWN, aVEvt);
1719cdf0e10cSrcweir 
1720cdf0e10cSrcweir 					if (eHit == SDRHIT_TEXTEDIT)
1721cdf0e10cSrcweir 					{
1722cdf0e10cSrcweir 						// Text getroffen
1723cdf0e10cSrcweir 						pOLV->MouseButtonDown(aMEvt);
1724cdf0e10cSrcweir 						pOLV->MouseMove(aMEvt);
1725cdf0e10cSrcweir 						pOLV->MouseButtonUp(aMEvt);
1726cdf0e10cSrcweir //						pOLV->MouseButtonDown(aMEvt);
1727cdf0e10cSrcweir 						bNoSel = false;
1728cdf0e10cSrcweir 					}
1729cdf0e10cSrcweir 					else
1730cdf0e10cSrcweir 					{
1731cdf0e10cSrcweir 						nAction = ACTION_GOTO_LEFT_CELL;
1732cdf0e10cSrcweir 					}
1733cdf0e10cSrcweir 				}
1734cdf0e10cSrcweir 
1735cdf0e10cSrcweir 				if( bNoSel )
1736cdf0e10cSrcweir 				{
1737cdf0e10cSrcweir 					// Move cursor to end of text
1738cdf0e10cSrcweir 					ESelection aNewSelection;
1739cdf0e10cSrcweir 
1740cdf0e10cSrcweir 					const WritingMode eMode = pTableObj->GetWritingMode();
1741cdf0e10cSrcweir 					if( ((nAction == ACTION_GOTO_LEFT_CELL) || (nAction == ACTION_GOTO_RIGHT_CELL)) && (eMode != WritingMode_TB_RL) )
1742cdf0e10cSrcweir 					{
1743cdf0e10cSrcweir 						const bool bLast = ((nAction == ACTION_GOTO_LEFT_CELL) && (eMode == WritingMode_LR_TB)) ||
1744cdf0e10cSrcweir 											 ((nAction == ACTION_GOTO_RIGHT_CELL) && (eMode == WritingMode_RL_TB));
1745cdf0e10cSrcweir 
1746cdf0e10cSrcweir 						if( bLast )
1747cdf0e10cSrcweir 							aNewSelection = ESelection(EE_PARA_NOT_FOUND, EE_INDEX_NOT_FOUND, EE_PARA_NOT_FOUND, EE_INDEX_NOT_FOUND);
1748cdf0e10cSrcweir 					}
1749cdf0e10cSrcweir 					pOLV->SetSelection(aNewSelection);
1750cdf0e10cSrcweir 				}
1751cdf0e10cSrcweir 			}
1752cdf0e10cSrcweir 		}
1753cdf0e10cSrcweir 	}
1754cdf0e10cSrcweir }
1755cdf0e10cSrcweir 
1756cdf0e10cSrcweir // --------------------------------------------------------------------
1757cdf0e10cSrcweir 
StopTextEdit()1758cdf0e10cSrcweir bool SvxTableController::StopTextEdit()
1759cdf0e10cSrcweir {
1760cdf0e10cSrcweir 	if(mpView->IsTextEdit())
1761cdf0e10cSrcweir 	{
1762cdf0e10cSrcweir 		mpView->SdrEndTextEdit();
1763cdf0e10cSrcweir 		mpView->SetCurrentObj(OBJ_TABLE);
1764cdf0e10cSrcweir 		mpView->SetEditMode(SDREDITMODE_EDIT);
1765cdf0e10cSrcweir 		return true;
1766cdf0e10cSrcweir 	}
1767cdf0e10cSrcweir 	else
1768cdf0e10cSrcweir 	{
1769cdf0e10cSrcweir 		return false;
1770cdf0e10cSrcweir 	}
1771cdf0e10cSrcweir }
1772cdf0e10cSrcweir 
1773cdf0e10cSrcweir // --------------------------------------------------------------------
1774cdf0e10cSrcweir 
DeleteTable()1775cdf0e10cSrcweir void SvxTableController::DeleteTable()
1776cdf0e10cSrcweir {
1777cdf0e10cSrcweir 	//
1778cdf0e10cSrcweir }
1779cdf0e10cSrcweir 
1780cdf0e10cSrcweir // --------------------------------------------------------------------
1781cdf0e10cSrcweir 
getSelectedCells(CellPos & rFirst,CellPos & rLast)1782cdf0e10cSrcweir void SvxTableController::getSelectedCells( CellPos& rFirst, CellPos& rLast )
1783cdf0e10cSrcweir {
1784cdf0e10cSrcweir 	if( mbCellSelectionMode )
1785cdf0e10cSrcweir 	{
1786cdf0e10cSrcweir 		checkCell( maCursorFirstPos );
1787cdf0e10cSrcweir 		checkCell( maCursorLastPos );
1788cdf0e10cSrcweir 
1789cdf0e10cSrcweir 		rFirst.mnCol = std::min( maCursorFirstPos.mnCol, maCursorLastPos.mnCol );
1790cdf0e10cSrcweir 		rFirst.mnRow = std::min( maCursorFirstPos.mnRow, maCursorLastPos.mnRow );
1791cdf0e10cSrcweir 		rLast.mnCol = std::max( maCursorFirstPos.mnCol, maCursorLastPos.mnCol );
1792cdf0e10cSrcweir 		rLast.mnRow = std::max( maCursorFirstPos.mnRow, maCursorLastPos.mnRow );
1793cdf0e10cSrcweir 
1794cdf0e10cSrcweir 		bool bExt = false;
1795cdf0e10cSrcweir 		if( mxTable.is() ) do
1796cdf0e10cSrcweir 		{
1797cdf0e10cSrcweir 			bExt = false;
1798cdf0e10cSrcweir 			for( sal_Int32 nRow = rFirst.mnRow; nRow <= rLast.mnRow && !bExt; nRow++ )
1799cdf0e10cSrcweir 			{
1800cdf0e10cSrcweir 				for( sal_Int32 nCol = rFirst.mnCol; nCol <= rLast.mnCol && !bExt; nCol++ )
1801cdf0e10cSrcweir 				{
1802cdf0e10cSrcweir 					Reference< XMergeableCell > xCell( mxTable->getCellByPosition( nCol, nRow ), UNO_QUERY );
1803cdf0e10cSrcweir 					if( !xCell.is() )
1804cdf0e10cSrcweir 						continue;
1805cdf0e10cSrcweir 
1806cdf0e10cSrcweir 					if( xCell->isMerged() )
1807cdf0e10cSrcweir 					{
1808cdf0e10cSrcweir 						CellPos aPos( nCol, nRow );
1809cdf0e10cSrcweir 						findMergeOrigin( aPos );
1810cdf0e10cSrcweir 						if( (aPos.mnCol < rFirst.mnCol) || (aPos.mnRow < rFirst.mnRow) )
1811cdf0e10cSrcweir 						{
1812cdf0e10cSrcweir 							rFirst.mnCol = std::min( rFirst.mnCol, aPos.mnCol );
1813cdf0e10cSrcweir 							rFirst.mnRow = std::min( rFirst.mnRow, aPos.mnRow );
1814cdf0e10cSrcweir 							bExt = true;
1815cdf0e10cSrcweir 						}
1816cdf0e10cSrcweir 					}
1817cdf0e10cSrcweir 					else
1818cdf0e10cSrcweir 					{
1819cdf0e10cSrcweir 						if( ((nCol + xCell->getColumnSpan() - 1) > rLast.mnCol) || (nRow + xCell->getRowSpan() - 1 ) > rLast.mnRow )
1820cdf0e10cSrcweir 						{
1821cdf0e10cSrcweir 							rLast.mnCol = std::max( rLast.mnCol, nCol + xCell->getColumnSpan() - 1 );
1822cdf0e10cSrcweir 							rLast.mnRow = std::max( rLast.mnRow, nRow + xCell->getRowSpan() - 1 );
1823cdf0e10cSrcweir 							bExt = true;
1824cdf0e10cSrcweir 						}
1825cdf0e10cSrcweir 					}
1826cdf0e10cSrcweir 				}
1827cdf0e10cSrcweir 			}
1828cdf0e10cSrcweir 		}
1829cdf0e10cSrcweir 		while(bExt);
1830cdf0e10cSrcweir 	}
1831cdf0e10cSrcweir 	else if( mpView && mpView->IsTextEdit() )
1832cdf0e10cSrcweir 	{
1833cdf0e10cSrcweir 		rFirst = getSelectionStart();
1834cdf0e10cSrcweir 		findMergeOrigin( rFirst );
1835cdf0e10cSrcweir 		rLast = rFirst;
1836cdf0e10cSrcweir 
1837cdf0e10cSrcweir 		if( mxTable.is() )
1838cdf0e10cSrcweir 		{
1839cdf0e10cSrcweir 			Reference< XMergeableCell > xCell( mxTable->getCellByPosition( rLast.mnCol, rLast.mnRow ), UNO_QUERY );
1840cdf0e10cSrcweir 			if( xCell.is() )
1841cdf0e10cSrcweir 			{
1842cdf0e10cSrcweir 				rLast.mnCol += xCell->getColumnSpan() - 1;
1843cdf0e10cSrcweir 				rLast.mnRow += xCell->getRowSpan() - 1;
1844cdf0e10cSrcweir 			}
1845cdf0e10cSrcweir 		}
1846cdf0e10cSrcweir 	}
1847cdf0e10cSrcweir 	else
1848cdf0e10cSrcweir 	{
1849cdf0e10cSrcweir 		rFirst.mnCol = 0;
1850cdf0e10cSrcweir 		rFirst.mnRow = 0;
1851cdf0e10cSrcweir 		if( mxTable.is() )
1852cdf0e10cSrcweir 		{
1853cdf0e10cSrcweir 			rLast.mnRow = mxTable->getRowCount()-1;
1854cdf0e10cSrcweir 			rLast.mnCol = mxTable->getColumnCount()-1;
1855cdf0e10cSrcweir 		}
1856cdf0e10cSrcweir 		else
1857cdf0e10cSrcweir 		{
1858cdf0e10cSrcweir 			rLast.mnRow = 0;
1859cdf0e10cSrcweir 			rLast.mnCol = 0;
1860cdf0e10cSrcweir 		}
1861cdf0e10cSrcweir 	}
1862cdf0e10cSrcweir }
1863cdf0e10cSrcweir 
1864cdf0e10cSrcweir // --------------------------------------------------------------------
1865cdf0e10cSrcweir 
StartSelection(const CellPos & rPos)1866cdf0e10cSrcweir void SvxTableController::StartSelection( const CellPos& rPos )
1867cdf0e10cSrcweir {
1868cdf0e10cSrcweir 	StopTextEdit();
1869cdf0e10cSrcweir 	mbCellSelectionMode = true;
1870cdf0e10cSrcweir 	maCursorLastPos = maCursorFirstPos = rPos;
1871cdf0e10cSrcweir 	mpView->MarkListHasChanged();
1872cdf0e10cSrcweir }
1873cdf0e10cSrcweir 
1874cdf0e10cSrcweir // --------------------------------------------------------------------
1875cdf0e10cSrcweir 
setSelectedCells(const CellPos & rStart,const CellPos & rEnd)1876cdf0e10cSrcweir void SvxTableController::setSelectedCells( const CellPos& rStart, const CellPos& rEnd )
1877cdf0e10cSrcweir {
1878cdf0e10cSrcweir 	StopTextEdit();
1879cdf0e10cSrcweir 	mbCellSelectionMode = true;
1880cdf0e10cSrcweir 	maCursorFirstPos = rStart;
1881cdf0e10cSrcweir 	UpdateSelection( rEnd );
1882cdf0e10cSrcweir }
1883cdf0e10cSrcweir 
1884cdf0e10cSrcweir // --------------------------------------------------------------------
1885cdf0e10cSrcweir 
UpdateSelection(const CellPos & rPos)1886cdf0e10cSrcweir void SvxTableController::UpdateSelection( const CellPos& rPos )
1887cdf0e10cSrcweir {
1888cdf0e10cSrcweir 	maCursorLastPos = rPos;
1889cdf0e10cSrcweir 	mpView->MarkListHasChanged();
1890cdf0e10cSrcweir }
1891cdf0e10cSrcweir 
1892cdf0e10cSrcweir // --------------------------------------------------------------------
1893cdf0e10cSrcweir 
clearSelection()1894cdf0e10cSrcweir void SvxTableController::clearSelection()
1895cdf0e10cSrcweir {
1896cdf0e10cSrcweir 	RemoveSelection();
1897cdf0e10cSrcweir }
1898cdf0e10cSrcweir 
1899cdf0e10cSrcweir // --------------------------------------------------------------------
1900cdf0e10cSrcweir 
selectAll()1901cdf0e10cSrcweir void SvxTableController::selectAll()
1902cdf0e10cSrcweir {
1903cdf0e10cSrcweir 	if( mxTable.is() )
1904cdf0e10cSrcweir 	{
1905cdf0e10cSrcweir 		CellPos aPos1, aPos2( mxTable->getColumnCount()-1, mxTable->getRowCount()-1 );
1906cdf0e10cSrcweir 		if( (aPos2.mnCol >= 0) && (aPos2.mnRow >= 0) )
1907cdf0e10cSrcweir 		{
1908cdf0e10cSrcweir 			setSelectedCells( aPos1, aPos2 );
1909cdf0e10cSrcweir 		}
1910cdf0e10cSrcweir 	}
1911cdf0e10cSrcweir }
1912cdf0e10cSrcweir 
1913cdf0e10cSrcweir // --------------------------------------------------------------------
1914cdf0e10cSrcweir 
RemoveSelection()1915cdf0e10cSrcweir void SvxTableController::RemoveSelection()
1916cdf0e10cSrcweir {
1917cdf0e10cSrcweir 	if( mbCellSelectionMode )
1918cdf0e10cSrcweir 	{
1919cdf0e10cSrcweir 		mbCellSelectionMode = false;
1920cdf0e10cSrcweir 		mpView->MarkListHasChanged();
1921cdf0e10cSrcweir 	}
1922cdf0e10cSrcweir }
1923cdf0e10cSrcweir 
1924cdf0e10cSrcweir // --------------------------------------------------------------------
1925cdf0e10cSrcweir 
onTableModified()1926cdf0e10cSrcweir void SvxTableController::onTableModified()
1927cdf0e10cSrcweir {
1928cdf0e10cSrcweir 	if( mnUpdateEvent == 0 )
1929cdf0e10cSrcweir 		mnUpdateEvent = Application::PostUserEvent( LINK( this, SvxTableController, UpdateHdl ) );
1930cdf0e10cSrcweir }
1931cdf0e10cSrcweir // --------------------------------------------------------------------
1932cdf0e10cSrcweir 
updateSelectionOverlay()1933cdf0e10cSrcweir void SvxTableController::updateSelectionOverlay()
1934cdf0e10cSrcweir {
1935cdf0e10cSrcweir 	destroySelectionOverlay();
1936cdf0e10cSrcweir 	if( mbCellSelectionMode )
1937cdf0e10cSrcweir 	{
1938cdf0e10cSrcweir 		::sdr::table::SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
1939cdf0e10cSrcweir 		if( pTableObj )
1940cdf0e10cSrcweir 		{
1941cdf0e10cSrcweir 			sdr::overlay::OverlayObjectCell::RangeVector aRanges;
1942cdf0e10cSrcweir 
1943cdf0e10cSrcweir 			Rectangle aRect;
1944cdf0e10cSrcweir 			CellPos aStart,aEnd;
1945cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
1946cdf0e10cSrcweir 			pTableObj->getCellBounds( aStart, aRect );
1947cdf0e10cSrcweir 
1948cdf0e10cSrcweir 			basegfx::B2DRange a2DRange( basegfx::B2DPoint(aRect.Left(), aRect.Top()) );
1949cdf0e10cSrcweir 			a2DRange.expand( basegfx::B2DPoint(aRect.Right(), aRect.Bottom()) );
1950cdf0e10cSrcweir 
1951cdf0e10cSrcweir 			findMergeOrigin( aEnd );
1952cdf0e10cSrcweir 			pTableObj->getCellBounds( aEnd, aRect );
1953cdf0e10cSrcweir 			a2DRange.expand( basegfx::B2DPoint(aRect.Left(), aRect.Top()) );
1954cdf0e10cSrcweir 			a2DRange.expand( basegfx::B2DPoint(aRect.Right(), aRect.Bottom()) );
1955cdf0e10cSrcweir 			aRanges.push_back( a2DRange );
1956cdf0e10cSrcweir 
1957cdf0e10cSrcweir 			::Color aHighlight( COL_BLUE );
1958cdf0e10cSrcweir 			OutputDevice* pOutDev = mpView->GetFirstOutputDevice();
1959cdf0e10cSrcweir 			if( pOutDev )
1960cdf0e10cSrcweir 				aHighlight = pOutDev->GetSettings().GetStyleSettings().GetHighlightColor();
1961cdf0e10cSrcweir 
1962cdf0e10cSrcweir 			const sal_uInt32 nCount = mpView->PaintWindowCount();
1963cdf0e10cSrcweir 			for( sal_uInt32 nIndex = 0; nIndex < nCount; nIndex++ )
1964cdf0e10cSrcweir 			{
1965cdf0e10cSrcweir 				SdrPaintWindow* pPaintWindow = mpView->GetPaintWindow(nIndex);
1966cdf0e10cSrcweir 				if( pPaintWindow )
1967cdf0e10cSrcweir 				{
1968cdf0e10cSrcweir 					::sdr::overlay::OverlayManager* pOverlayManager = pPaintWindow->GetOverlayManager();
1969cdf0e10cSrcweir 					if( pOverlayManager )
1970cdf0e10cSrcweir 					{
1971cdf0e10cSrcweir 						// sdr::overlay::CellOverlayType eType = sdr::overlay::CELL_OVERLAY_INVERT;
1972cdf0e10cSrcweir 						sdr::overlay::CellOverlayType eType = sdr::overlay::CELL_OVERLAY_TRANSPARENT;
1973cdf0e10cSrcweir 
1974cdf0e10cSrcweir 						sdr::overlay::OverlayObjectCell* pOverlay = new sdr::overlay::OverlayObjectCell( eType, aHighlight, aRanges );
1975cdf0e10cSrcweir 
1976cdf0e10cSrcweir 						pOverlayManager->add(*pOverlay);
1977cdf0e10cSrcweir 						mpSelectionOverlay = new ::sdr::overlay::OverlayObjectList;
1978cdf0e10cSrcweir 						mpSelectionOverlay->append(*pOverlay);
1979cdf0e10cSrcweir 					}
1980cdf0e10cSrcweir 				}
1981cdf0e10cSrcweir 			}
1982cdf0e10cSrcweir 		}
1983cdf0e10cSrcweir 	}
1984cdf0e10cSrcweir }
1985cdf0e10cSrcweir 
1986cdf0e10cSrcweir // --------------------------------------------------------------------
1987cdf0e10cSrcweir 
destroySelectionOverlay()1988cdf0e10cSrcweir void SvxTableController::destroySelectionOverlay()
1989cdf0e10cSrcweir {
1990cdf0e10cSrcweir 	if( mpSelectionOverlay )
1991cdf0e10cSrcweir 	{
1992cdf0e10cSrcweir 		delete mpSelectionOverlay;
1993cdf0e10cSrcweir 		mpSelectionOverlay = 0;
1994cdf0e10cSrcweir 	}
1995cdf0e10cSrcweir }
1996cdf0e10cSrcweir 
1997cdf0e10cSrcweir // --------------------------------------------------------------------
1998cdf0e10cSrcweir 
MergeAttrFromSelectedCells(SfxItemSet & rAttr,bool bOnlyHardAttr) const1999cdf0e10cSrcweir void SvxTableController::MergeAttrFromSelectedCells(SfxItemSet& rAttr, bool bOnlyHardAttr) const
2000cdf0e10cSrcweir {
2001cdf0e10cSrcweir 	if( mxTable.is() )
2002cdf0e10cSrcweir 	{
2003cdf0e10cSrcweir 		CellPos aStart, aEnd;
2004cdf0e10cSrcweir 		const_cast<SvxTableController&>(*this).getSelectedCells( aStart, aEnd );
2005cdf0e10cSrcweir 
2006cdf0e10cSrcweir 		for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
2007cdf0e10cSrcweir 		{
2008cdf0e10cSrcweir 			for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
2009cdf0e10cSrcweir 			{
2010cdf0e10cSrcweir 				CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
2011cdf0e10cSrcweir 				if( xCell.is() && !xCell->isMerged() )
2012cdf0e10cSrcweir 				{
2013cdf0e10cSrcweir 					const SfxItemSet& rSet = xCell->GetItemSet();
2014cdf0e10cSrcweir 					SfxWhichIter aIter(rSet);
2015cdf0e10cSrcweir 					sal_uInt16 nWhich(aIter.FirstWhich());
2016cdf0e10cSrcweir 					while(nWhich)
2017cdf0e10cSrcweir 					{
2018cdf0e10cSrcweir 						if(!bOnlyHardAttr)
2019cdf0e10cSrcweir 						{
2020cdf0e10cSrcweir 							if(SFX_ITEM_DONTCARE == rSet.GetItemState(nWhich, sal_False))
2021cdf0e10cSrcweir 								rAttr.InvalidateItem(nWhich);
2022cdf0e10cSrcweir 							else
2023cdf0e10cSrcweir 								rAttr.MergeValue(rSet.Get(nWhich), sal_True);
2024cdf0e10cSrcweir 						}
2025cdf0e10cSrcweir 						else if(SFX_ITEM_SET == rSet.GetItemState(nWhich, sal_False))
2026cdf0e10cSrcweir 						{
2027cdf0e10cSrcweir 							const SfxPoolItem& rItem = rSet.Get(nWhich);
2028cdf0e10cSrcweir 							rAttr.MergeValue(rItem, sal_True);
2029cdf0e10cSrcweir 						}
2030cdf0e10cSrcweir 
2031cdf0e10cSrcweir 						nWhich = aIter.NextWhich();
2032cdf0e10cSrcweir 					}
2033cdf0e10cSrcweir 				}
2034cdf0e10cSrcweir 			}
2035cdf0e10cSrcweir 		}
2036cdf0e10cSrcweir 	}
2037cdf0e10cSrcweir 
2038cdf0e10cSrcweir 	if( mpView->IsTextEdit() )
2039cdf0e10cSrcweir 	{
2040cdf0e10cSrcweir 	}
2041cdf0e10cSrcweir }
2042cdf0e10cSrcweir 
2043cdf0e10cSrcweir // --------------------------------------------------------------------
2044cdf0e10cSrcweir 
2045cdf0e10cSrcweir const sal_uInt16 CELL_BEFORE = 0x0001;
2046cdf0e10cSrcweir const sal_uInt16 CELL_LEFT   = 0x0002;
2047cdf0e10cSrcweir const sal_uInt16 CELL_RIGHT  = 0x0004;
2048cdf0e10cSrcweir const sal_uInt16 CELL_AFTER  = 0x0008;
2049cdf0e10cSrcweir 
2050cdf0e10cSrcweir const sal_uInt16 CELL_UPPER  = 0x0010;
2051cdf0e10cSrcweir const sal_uInt16 CELL_TOP    = 0x0020;
2052cdf0e10cSrcweir const sal_uInt16 CELL_BOTTOM = 0x0040;
2053cdf0e10cSrcweir const sal_uInt16 CELL_LOWER  = 0x0080;
2054cdf0e10cSrcweir 
2055cdf0e10cSrcweir // --------------------------------------------------------------------
2056cdf0e10cSrcweir 
ImplSetLinePreserveColor(SvxBoxItem & rNewFrame,const SvxBorderLine * pNew,sal_uInt16 nLine)2057cdf0e10cSrcweir static void ImplSetLinePreserveColor( SvxBoxItem& rNewFrame, const SvxBorderLine* pNew, sal_uInt16 nLine )
2058cdf0e10cSrcweir {
2059cdf0e10cSrcweir 	if( pNew )
2060cdf0e10cSrcweir 	{
2061cdf0e10cSrcweir 		const SvxBorderLine* pOld = rNewFrame.GetLine(nLine);
2062cdf0e10cSrcweir 		if( pOld )
2063cdf0e10cSrcweir 		{
2064cdf0e10cSrcweir 			SvxBorderLine aNewLine( *pNew );
2065cdf0e10cSrcweir 			aNewLine.SetColor( pOld->GetColor() );
2066cdf0e10cSrcweir 			rNewFrame.SetLine( &aNewLine, nLine );
2067cdf0e10cSrcweir 			return;
2068cdf0e10cSrcweir 		}
2069cdf0e10cSrcweir 	}
2070cdf0e10cSrcweir 	rNewFrame.SetLine( pNew, nLine );
2071cdf0e10cSrcweir }
2072cdf0e10cSrcweir 
2073cdf0e10cSrcweir // --------------------------------------------------------------------
2074cdf0e10cSrcweir 
ImplApplyBoxItem(sal_uInt16 nCellFlags,const SvxBoxItem * pBoxItem,const SvxBoxInfoItem * pBoxInfoItem,SvxBoxItem & rNewFrame)2075cdf0e10cSrcweir static void ImplApplyBoxItem( sal_uInt16 nCellFlags, const SvxBoxItem* pBoxItem, const SvxBoxInfoItem* pBoxInfoItem, SvxBoxItem& rNewFrame )
2076cdf0e10cSrcweir {
2077cdf0e10cSrcweir 	if( (nCellFlags & (CELL_BEFORE|CELL_AFTER|CELL_UPPER|CELL_LOWER)) != 0 )
2078cdf0e10cSrcweir 	{
2079cdf0e10cSrcweir 		// current cell is outside the selection
2080cdf0e10cSrcweir 
2081cdf0e10cSrcweir 		if( (nCellFlags & ( CELL_BEFORE|CELL_AFTER)) == 0 ) // check if its not nw or ne corner
2082cdf0e10cSrcweir 		{
2083cdf0e10cSrcweir 			if( nCellFlags & CELL_UPPER )
2084cdf0e10cSrcweir 			{
2085cdf0e10cSrcweir 				if( pBoxInfoItem->IsValid(VALID_TOP) )
2086cdf0e10cSrcweir 					rNewFrame.SetLine(0, BOX_LINE_BOTTOM );
2087cdf0e10cSrcweir 			}
2088cdf0e10cSrcweir 			else if( nCellFlags & CELL_LOWER )
2089cdf0e10cSrcweir 			{
2090cdf0e10cSrcweir 				if( pBoxInfoItem->IsValid(VALID_BOTTOM) )
2091cdf0e10cSrcweir 					rNewFrame.SetLine( 0, BOX_LINE_TOP );
2092cdf0e10cSrcweir 			}
2093cdf0e10cSrcweir 		}
2094cdf0e10cSrcweir 		else if( (nCellFlags & ( CELL_UPPER|CELL_LOWER)) == 0 ) // check if its not sw or se corner
2095cdf0e10cSrcweir 		{
2096cdf0e10cSrcweir 			if( nCellFlags & CELL_BEFORE )
2097cdf0e10cSrcweir 			{
2098cdf0e10cSrcweir 				if( pBoxInfoItem->IsValid(VALID_LEFT) )
2099cdf0e10cSrcweir 					rNewFrame.SetLine( 0, BOX_LINE_RIGHT );
2100cdf0e10cSrcweir 			}
2101cdf0e10cSrcweir 			else if( nCellFlags & CELL_AFTER )
2102cdf0e10cSrcweir 			{
2103cdf0e10cSrcweir 				if( pBoxInfoItem->IsValid(VALID_RIGHT) )
2104cdf0e10cSrcweir 					rNewFrame.SetLine( 0, BOX_LINE_LEFT );
2105cdf0e10cSrcweir 			}
2106cdf0e10cSrcweir 		}
2107cdf0e10cSrcweir 	}
2108cdf0e10cSrcweir 	else
2109cdf0e10cSrcweir 	{
2110cdf0e10cSrcweir 		// current cell is inside the selection
2111cdf0e10cSrcweir 
2112cdf0e10cSrcweir 		if( (nCellFlags & CELL_LEFT) ? pBoxInfoItem->IsValid(VALID_LEFT) : pBoxInfoItem->IsValid(VALID_VERT) )
2113cdf0e10cSrcweir 			rNewFrame.SetLine( (nCellFlags & CELL_LEFT) ? pBoxItem->GetLeft() : pBoxInfoItem->GetVert(), BOX_LINE_LEFT );
2114cdf0e10cSrcweir 
2115cdf0e10cSrcweir 		if( (nCellFlags & CELL_RIGHT) ? pBoxInfoItem->IsValid(VALID_RIGHT) : pBoxInfoItem->IsValid(VALID_VERT) )
2116cdf0e10cSrcweir 			rNewFrame.SetLine( (nCellFlags & CELL_RIGHT) ? pBoxItem->GetRight() : pBoxInfoItem->GetVert(), BOX_LINE_RIGHT );
2117cdf0e10cSrcweir 
2118cdf0e10cSrcweir 		if( (nCellFlags & CELL_TOP) ? pBoxInfoItem->IsValid(VALID_TOP) : pBoxInfoItem->IsValid(VALID_HORI) )
2119cdf0e10cSrcweir 			rNewFrame.SetLine( (nCellFlags & CELL_TOP) ? pBoxItem->GetTop() : pBoxInfoItem->GetHori(), BOX_LINE_TOP );
2120cdf0e10cSrcweir 
2121cdf0e10cSrcweir 		if( (nCellFlags & CELL_BOTTOM) ? pBoxInfoItem->IsValid(VALID_BOTTOM) : pBoxInfoItem->IsValid(VALID_HORI) )
2122cdf0e10cSrcweir 			rNewFrame.SetLine( (nCellFlags & CELL_BOTTOM) ? pBoxItem->GetBottom() : pBoxInfoItem->GetHori(), BOX_LINE_BOTTOM );
2123cdf0e10cSrcweir 
2124cdf0e10cSrcweir 		// apply distance to borders
2125cdf0e10cSrcweir 		if( pBoxInfoItem->IsValid( VALID_DISTANCE ) )
2126cdf0e10cSrcweir 			for( sal_uInt16 nLine = 0; nLine < 4; ++nLine )
2127cdf0e10cSrcweir 				rNewFrame.SetDistance( pBoxItem->GetDistance( nLine ), nLine );
2128cdf0e10cSrcweir 	}
2129cdf0e10cSrcweir }
2130cdf0e10cSrcweir 
2131cdf0e10cSrcweir // --------------------------------------------------------------------
2132cdf0e10cSrcweir 
ImplSetLineColor(SvxBoxItem & rNewFrame,sal_uInt16 nLine,const Color & rColor)2133cdf0e10cSrcweir static void ImplSetLineColor( SvxBoxItem& rNewFrame, sal_uInt16 nLine, const Color& rColor )
2134cdf0e10cSrcweir {
2135cdf0e10cSrcweir 	const SvxBorderLine* pSourceLine = rNewFrame.GetLine( nLine );
2136cdf0e10cSrcweir 	if( pSourceLine )
2137cdf0e10cSrcweir 	{
2138cdf0e10cSrcweir 		SvxBorderLine aLine( *pSourceLine );
2139cdf0e10cSrcweir 		aLine.SetColor( rColor );
2140cdf0e10cSrcweir 		rNewFrame.SetLine( &aLine, nLine );
2141cdf0e10cSrcweir 	}
2142cdf0e10cSrcweir }
2143cdf0e10cSrcweir 
2144cdf0e10cSrcweir // --------------------------------------------------------------------
2145cdf0e10cSrcweir 
ImplApplyLineColorItem(sal_uInt16 nCellFlags,const SvxColorItem * pLineColorItem,SvxBoxItem & rNewFrame)2146cdf0e10cSrcweir static void ImplApplyLineColorItem( sal_uInt16 nCellFlags, const SvxColorItem* pLineColorItem, SvxBoxItem& rNewFrame )
2147cdf0e10cSrcweir {
2148cdf0e10cSrcweir 	const Color aColor( pLineColorItem->GetValue() );
2149cdf0e10cSrcweir 
2150cdf0e10cSrcweir 	if( (nCellFlags & (CELL_LOWER|CELL_BEFORE|CELL_AFTER)) == 0 )
2151cdf0e10cSrcweir 		ImplSetLineColor( rNewFrame, BOX_LINE_BOTTOM, aColor );
2152cdf0e10cSrcweir 
2153cdf0e10cSrcweir 	if( (nCellFlags & (CELL_UPPER|CELL_BEFORE|CELL_AFTER)) == 0 )
2154cdf0e10cSrcweir 		ImplSetLineColor( rNewFrame, BOX_LINE_TOP, aColor );
2155cdf0e10cSrcweir 
2156cdf0e10cSrcweir 	if( (nCellFlags & (CELL_UPPER|CELL_LOWER|CELL_AFTER)) == 0 )
2157cdf0e10cSrcweir 		ImplSetLineColor( rNewFrame, BOX_LINE_RIGHT, aColor );
2158cdf0e10cSrcweir 
2159cdf0e10cSrcweir 	if( (nCellFlags & (CELL_UPPER|CELL_LOWER|CELL_BEFORE)) == 0 )
2160cdf0e10cSrcweir 		ImplSetLineColor( rNewFrame, BOX_LINE_LEFT, aColor );
2161cdf0e10cSrcweir }
2162cdf0e10cSrcweir 
2163cdf0e10cSrcweir // --------------------------------------------------------------------
2164cdf0e10cSrcweir 
ImplApplyBorderLineItem(sal_uInt16 nCellFlags,const SvxBorderLine * pBorderLineItem,SvxBoxItem & rNewFrame)2165cdf0e10cSrcweir static void ImplApplyBorderLineItem( sal_uInt16 nCellFlags, const SvxBorderLine* pBorderLineItem, SvxBoxItem& rNewFrame )
2166cdf0e10cSrcweir {
2167cdf0e10cSrcweir 	if( (nCellFlags & ( CELL_BEFORE|CELL_AFTER|CELL_UPPER|CELL_LOWER)) != 0 )
2168cdf0e10cSrcweir 	{
2169cdf0e10cSrcweir 		if( (nCellFlags & ( CELL_BEFORE|CELL_AFTER)) == 0 ) // check if its not nw or ne corner
2170cdf0e10cSrcweir 		{
2171cdf0e10cSrcweir 			if( nCellFlags & CELL_UPPER )
2172cdf0e10cSrcweir 			{
2173cdf0e10cSrcweir 				if( rNewFrame.GetBottom() )
2174cdf0e10cSrcweir 					ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_BOTTOM );
2175cdf0e10cSrcweir 			}
2176cdf0e10cSrcweir 			else if( nCellFlags & CELL_LOWER )
2177cdf0e10cSrcweir 			{
2178cdf0e10cSrcweir 				if( rNewFrame.GetTop() )
2179cdf0e10cSrcweir 					ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_TOP );
2180cdf0e10cSrcweir 			}
2181cdf0e10cSrcweir 		}
2182cdf0e10cSrcweir 		else if( (nCellFlags & ( CELL_UPPER|CELL_LOWER)) == 0 ) // check if its not sw or se corner
2183cdf0e10cSrcweir 		{
2184cdf0e10cSrcweir 			if( nCellFlags & CELL_BEFORE )
2185cdf0e10cSrcweir 			{
2186cdf0e10cSrcweir 				if( rNewFrame.GetRight() )
2187cdf0e10cSrcweir 					ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_RIGHT );
2188cdf0e10cSrcweir 			}
2189cdf0e10cSrcweir 			else if( nCellFlags & CELL_AFTER )
2190cdf0e10cSrcweir 			{
2191cdf0e10cSrcweir 				if( rNewFrame.GetLeft() )
2192cdf0e10cSrcweir 					ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_LEFT );
2193cdf0e10cSrcweir 			}
2194cdf0e10cSrcweir 		}
2195cdf0e10cSrcweir 	}
2196cdf0e10cSrcweir 	else
2197cdf0e10cSrcweir 	{
2198cdf0e10cSrcweir 		if( rNewFrame.GetBottom() )
2199cdf0e10cSrcweir 			ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_BOTTOM );
2200cdf0e10cSrcweir 		if( rNewFrame.GetTop() )
2201cdf0e10cSrcweir 			ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_TOP );
2202cdf0e10cSrcweir 		if( rNewFrame.GetRight() )
2203cdf0e10cSrcweir 			ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_RIGHT );
2204cdf0e10cSrcweir 		if( rNewFrame.GetLeft() )
2205cdf0e10cSrcweir 			ImplSetLinePreserveColor( rNewFrame, pBorderLineItem, BOX_LINE_LEFT );
2206cdf0e10cSrcweir 	}
2207cdf0e10cSrcweir }
2208cdf0e10cSrcweir 
2209cdf0e10cSrcweir // --------------------------------------------------------------------
2210cdf0e10cSrcweir 
ApplyBorderAttr(const SfxItemSet & rAttr)2211cdf0e10cSrcweir void SvxTableController::ApplyBorderAttr( const SfxItemSet& rAttr )
2212cdf0e10cSrcweir {
2213cdf0e10cSrcweir 	if( mxTable.is() )
2214cdf0e10cSrcweir 	{
2215cdf0e10cSrcweir 		const sal_Int32 nRowCount = mxTable->getRowCount();
2216cdf0e10cSrcweir 		const sal_Int32 nColCount = mxTable->getColumnCount();
2217cdf0e10cSrcweir 		if( nRowCount && nColCount )
2218cdf0e10cSrcweir 		{
2219cdf0e10cSrcweir 			const SvxBoxItem* pBoxItem = 0;
2220cdf0e10cSrcweir 			if(SFX_ITEM_SET == rAttr.GetItemState(SDRATTR_TABLE_BORDER, sal_False) )
2221cdf0e10cSrcweir 				pBoxItem = dynamic_cast< const SvxBoxItem* >( &rAttr.Get( SDRATTR_TABLE_BORDER ) );
2222cdf0e10cSrcweir 
2223cdf0e10cSrcweir 			const SvxBoxInfoItem* pBoxInfoItem = 0;
2224cdf0e10cSrcweir 			if(SFX_ITEM_SET == rAttr.GetItemState(SDRATTR_TABLE_BORDER_INNER, sal_False) )
2225cdf0e10cSrcweir 				pBoxInfoItem = dynamic_cast< const SvxBoxInfoItem* >( &rAttr.Get( SDRATTR_TABLE_BORDER_INNER ) );
2226cdf0e10cSrcweir 
2227cdf0e10cSrcweir 			const SvxColorItem* pLineColorItem = 0;
2228cdf0e10cSrcweir 			if(SFX_ITEM_SET == rAttr.GetItemState(SID_FRAME_LINECOLOR, sal_False) )
2229cdf0e10cSrcweir 				pLineColorItem = dynamic_cast< const SvxColorItem* >( &rAttr.Get( SID_FRAME_LINECOLOR ) );
2230cdf0e10cSrcweir 
2231cdf0e10cSrcweir 			const SvxBorderLine* pBorderLineItem = 0;
2232cdf0e10cSrcweir 			if(SFX_ITEM_SET == rAttr.GetItemState(SID_FRAME_LINESTYLE, sal_False) )
2233cdf0e10cSrcweir 				pBorderLineItem = ((const SvxLineItem&)rAttr.Get( SID_FRAME_LINESTYLE )).GetLine();
2234cdf0e10cSrcweir 
2235cdf0e10cSrcweir 			if( pBoxInfoItem && !pBoxItem )
2236cdf0e10cSrcweir 			{
2237cdf0e10cSrcweir 				const static SvxBoxItem gaEmptyBoxItem( SDRATTR_TABLE_BORDER );
2238cdf0e10cSrcweir 				pBoxItem = &gaEmptyBoxItem;
2239cdf0e10cSrcweir 			}
2240cdf0e10cSrcweir 			else if( pBoxItem && !pBoxInfoItem )
2241cdf0e10cSrcweir 			{
2242cdf0e10cSrcweir 				const static SvxBoxInfoItem gaEmptyBoxInfoItem( SDRATTR_TABLE_BORDER_INNER );
2243cdf0e10cSrcweir 				pBoxInfoItem = &gaEmptyBoxInfoItem;
2244cdf0e10cSrcweir 			}
2245cdf0e10cSrcweir 
2246cdf0e10cSrcweir 			CellPos aStart, aEnd;
2247cdf0e10cSrcweir 			getSelectedCells( aStart, aEnd );
2248cdf0e10cSrcweir 
2249cdf0e10cSrcweir 			const sal_Int32 nLastRow = std::min( aEnd.mnRow + 2, nRowCount );
2250cdf0e10cSrcweir 			const sal_Int32 nLastCol = std::min( aEnd.mnCol + 2, nColCount );
2251cdf0e10cSrcweir 
2252cdf0e10cSrcweir 			for( sal_Int32 nRow = std::max( aStart.mnRow - 1, (sal_Int32)0 ); nRow < nLastRow; nRow++ )
2253cdf0e10cSrcweir 			{
2254cdf0e10cSrcweir 				sal_uInt16 nRowFlags = 0;
2255cdf0e10cSrcweir 				nRowFlags |= (nRow == aStart.mnRow) ? CELL_TOP : 0;
2256cdf0e10cSrcweir 				nRowFlags |= (nRow == aEnd.mnRow)   ? CELL_BOTTOM : 0;
2257cdf0e10cSrcweir 				nRowFlags |= (nRow < aStart.mnRow)  ? CELL_UPPER : 0;
2258cdf0e10cSrcweir 				nRowFlags |= (nRow > aEnd.mnRow)    ? CELL_LOWER : 0;
2259cdf0e10cSrcweir 
2260cdf0e10cSrcweir 				for( sal_Int32 nCol = std::max( aStart.mnCol - 1, (sal_Int32)0 ); nCol < nLastCol; nCol++ )
2261cdf0e10cSrcweir 				{
2262cdf0e10cSrcweir 					CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
2263cdf0e10cSrcweir 					if( !xCell.is() )
2264cdf0e10cSrcweir 						continue;
2265cdf0e10cSrcweir 
2266cdf0e10cSrcweir 					const SfxItemSet& rSet = xCell->GetItemSet();
2267cdf0e10cSrcweir 					const SvxBoxItem* pOldOuter = (const SvxBoxItem*)	  &rSet.Get( SDRATTR_TABLE_BORDER );
2268cdf0e10cSrcweir 
2269cdf0e10cSrcweir 					SvxBoxItem aNewFrame( *pOldOuter );
2270cdf0e10cSrcweir 
2271cdf0e10cSrcweir 					sal_uInt16 nCellFlags = nRowFlags;
2272cdf0e10cSrcweir 					nCellFlags |= (nCol == aStart.mnCol) ? CELL_LEFT : 0;
2273cdf0e10cSrcweir 					nCellFlags |= (nCol == aEnd.mnCol)   ? CELL_RIGHT : 0;
2274cdf0e10cSrcweir 					nCellFlags |= (nCol < aStart.mnCol)  ? CELL_BEFORE : 0;
2275cdf0e10cSrcweir 					nCellFlags |= (nCol > aEnd.mnCol)    ? CELL_AFTER : 0;
2276cdf0e10cSrcweir 
2277cdf0e10cSrcweir 					if( pBoxItem && pBoxInfoItem )
2278cdf0e10cSrcweir 						ImplApplyBoxItem( nCellFlags, pBoxItem, pBoxInfoItem, aNewFrame );
2279cdf0e10cSrcweir 
2280cdf0e10cSrcweir 					if( pLineColorItem )
2281cdf0e10cSrcweir 						ImplApplyLineColorItem( nCellFlags, pLineColorItem, aNewFrame );
2282cdf0e10cSrcweir 
2283cdf0e10cSrcweir 					if( pBorderLineItem )
2284cdf0e10cSrcweir 						ImplApplyBorderLineItem( nCellFlags, pBorderLineItem, aNewFrame );
2285cdf0e10cSrcweir 
2286cdf0e10cSrcweir 					if (aNewFrame != *pOldOuter)
2287cdf0e10cSrcweir 					{
2288cdf0e10cSrcweir 						SfxItemSet aAttr(*rSet.GetPool(), rSet.GetRanges());
2289cdf0e10cSrcweir 						aAttr.Put(aNewFrame);
2290cdf0e10cSrcweir 						xCell->SetMergedItemSetAndBroadcast( aAttr, false );
2291cdf0e10cSrcweir 					}
2292cdf0e10cSrcweir 				}
2293cdf0e10cSrcweir 			}
2294cdf0e10cSrcweir 		}
2295cdf0e10cSrcweir 	}
2296cdf0e10cSrcweir }
2297cdf0e10cSrcweir 
2298cdf0e10cSrcweir // --------------------------------------------------------------------
2299cdf0e10cSrcweir 
UpdateTableShape()2300cdf0e10cSrcweir void SvxTableController::UpdateTableShape()
2301cdf0e10cSrcweir {
2302cdf0e10cSrcweir 	SdrObject* pTableObj = mxTableObj.get();
2303cdf0e10cSrcweir 	if( pTableObj )
2304cdf0e10cSrcweir 	{
2305cdf0e10cSrcweir 		pTableObj->ActionChanged();
2306cdf0e10cSrcweir 		pTableObj->BroadcastObjectChange();
2307cdf0e10cSrcweir 	}
2308cdf0e10cSrcweir 	updateSelectionOverlay();
2309cdf0e10cSrcweir }
2310cdf0e10cSrcweir 
2311cdf0e10cSrcweir 
2312cdf0e10cSrcweir // --------------------------------------------------------------------
2313cdf0e10cSrcweir 
SetAttrToSelectedCells(const SfxItemSet & rAttr,bool bReplaceAll)2314cdf0e10cSrcweir void SvxTableController::SetAttrToSelectedCells(const SfxItemSet& rAttr, bool bReplaceAll)
2315cdf0e10cSrcweir {
2316cdf0e10cSrcweir 	if( mxTable.is() )
2317cdf0e10cSrcweir 	{
2318cdf0e10cSrcweir 		const bool bUndo = mpModel && mpModel->IsUndoEnabled();
2319cdf0e10cSrcweir 
2320cdf0e10cSrcweir 		if( bUndo )
2321cdf0e10cSrcweir 			mpModel->BegUndo( ImpGetResStr(STR_TABLE_NUMFORMAT) );
2322cdf0e10cSrcweir 
2323cdf0e10cSrcweir 		CellPos aStart, aEnd;
2324cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
2325cdf0e10cSrcweir 
2326cdf0e10cSrcweir 		SfxItemSet aAttr(*rAttr.GetPool(), rAttr.GetRanges());
2327cdf0e10cSrcweir 		aAttr.Put(rAttr, sal_True);
2328cdf0e10cSrcweir 
2329cdf0e10cSrcweir 		const bool bFrame = (rAttr.GetItemState( SDRATTR_TABLE_BORDER ) == SFX_ITEM_SET) || (rAttr.GetItemState( SDRATTR_TABLE_BORDER_INNER ) == SFX_ITEM_SET);
2330cdf0e10cSrcweir 
2331cdf0e10cSrcweir 		if( bFrame )
2332cdf0e10cSrcweir 		{
2333cdf0e10cSrcweir 			aAttr.ClearItem( SDRATTR_TABLE_BORDER );
2334cdf0e10cSrcweir 			aAttr.ClearItem( SDRATTR_TABLE_BORDER_INNER );
2335cdf0e10cSrcweir 		}
2336cdf0e10cSrcweir 
2337cdf0e10cSrcweir 		for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
2338cdf0e10cSrcweir 		{
2339cdf0e10cSrcweir 			for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
2340cdf0e10cSrcweir 			{
2341cdf0e10cSrcweir 				CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
2342cdf0e10cSrcweir 				if( xCell.is() )
2343cdf0e10cSrcweir 				{
2344cdf0e10cSrcweir 					if( bUndo )
2345cdf0e10cSrcweir 						xCell->AddUndo();
2346cdf0e10cSrcweir 					xCell->SetMergedItemSetAndBroadcast(aAttr, bReplaceAll);
2347cdf0e10cSrcweir 				}
2348cdf0e10cSrcweir 			}
2349cdf0e10cSrcweir 		}
2350cdf0e10cSrcweir 
2351cdf0e10cSrcweir 		if( bFrame )
2352cdf0e10cSrcweir 		{
2353cdf0e10cSrcweir 			ApplyBorderAttr( rAttr );
2354cdf0e10cSrcweir 		}
2355cdf0e10cSrcweir 
2356cdf0e10cSrcweir 		UpdateTableShape();
2357cdf0e10cSrcweir 
2358cdf0e10cSrcweir 		if( bUndo )
2359cdf0e10cSrcweir 			mpModel->EndUndo();
2360cdf0e10cSrcweir 
2361cdf0e10cSrcweir 	}
2362cdf0e10cSrcweir }
2363cdf0e10cSrcweir 
2364cdf0e10cSrcweir // --------------------------------------------------------------------
2365cdf0e10cSrcweir 
GetAttributes(SfxItemSet & rTargetSet,bool bOnlyHardAttr) const2366cdf0e10cSrcweir bool SvxTableController::GetAttributes(SfxItemSet& rTargetSet, bool bOnlyHardAttr) const
2367cdf0e10cSrcweir {
2368cdf0e10cSrcweir 	if( mxTableObj.is() && hasSelectedCells() )
2369cdf0e10cSrcweir 	{
2370cdf0e10cSrcweir 		MergeAttrFromSelectedCells( rTargetSet, bOnlyHardAttr );
2371cdf0e10cSrcweir 
2372cdf0e10cSrcweir 		if( mpView->IsTextEdit() )
2373cdf0e10cSrcweir 		{
2374cdf0e10cSrcweir 			if( mxTableObj->GetOutlinerParaObject() )
2375cdf0e10cSrcweir 				rTargetSet.Put( SvxScriptTypeItem( mxTableObj->GetOutlinerParaObject()->GetTextObject().GetScriptType() ) );
2376cdf0e10cSrcweir 
2377cdf0e10cSrcweir 			OutlinerView* pTextEditOutlinerView = mpView->GetTextEditOutlinerView();
2378cdf0e10cSrcweir 			if(pTextEditOutlinerView)
2379cdf0e10cSrcweir 			{
2380cdf0e10cSrcweir 				// FALSE= InvalidItems nicht al Default, sondern als "Loecher" betrachten
2381cdf0e10cSrcweir 				rTargetSet.Put(pTextEditOutlinerView->GetAttribs(), sal_False);
2382cdf0e10cSrcweir 				rTargetSet.Put( SvxScriptTypeItem( pTextEditOutlinerView->GetSelectedScriptType() ), sal_False );
2383cdf0e10cSrcweir 			}
2384cdf0e10cSrcweir 		}
2385cdf0e10cSrcweir 
2386cdf0e10cSrcweir 		return true;
2387cdf0e10cSrcweir 	}
2388cdf0e10cSrcweir 	else
2389cdf0e10cSrcweir 	{
2390cdf0e10cSrcweir 		return false;
2391cdf0e10cSrcweir 	}
2392cdf0e10cSrcweir }
2393cdf0e10cSrcweir 
2394cdf0e10cSrcweir // --------------------------------------------------------------------
2395cdf0e10cSrcweir 
SetAttributes(const SfxItemSet & rSet,bool bReplaceAll)2396cdf0e10cSrcweir bool SvxTableController::SetAttributes(const SfxItemSet& rSet, bool bReplaceAll)
2397cdf0e10cSrcweir {
2398cdf0e10cSrcweir 	if( mbCellSelectionMode || mpView->IsTextEdit()  )
2399cdf0e10cSrcweir 	{
2400cdf0e10cSrcweir 		SetAttrToSelectedCells( rSet, bReplaceAll );
2401cdf0e10cSrcweir 		return true;
2402cdf0e10cSrcweir 	}
2403cdf0e10cSrcweir 	return false;
2404cdf0e10cSrcweir }
2405cdf0e10cSrcweir 
2406cdf0e10cSrcweir // --------------------------------------------------------------------
2407cdf0e10cSrcweir 
GetMarkedObjModel(SdrPage * pNewPage)2408cdf0e10cSrcweir bool SvxTableController::GetMarkedObjModel( SdrPage* pNewPage )
2409cdf0e10cSrcweir {
2410cdf0e10cSrcweir 	if( mxTableObj.is() && mbCellSelectionMode && pNewPage ) try
2411cdf0e10cSrcweir 	{
2412cdf0e10cSrcweir 		::sdr::table::SdrTableObj& rTableObj = *static_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
2413cdf0e10cSrcweir 
2414cdf0e10cSrcweir 		CellPos aStart, aEnd;
2415cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
2416cdf0e10cSrcweir 
2417cdf0e10cSrcweir 		SdrTableObj* pNewTableObj = rTableObj.CloneRange( aStart, aEnd );
2418cdf0e10cSrcweir 
2419cdf0e10cSrcweir 		pNewTableObj->SetPage( pNewPage );
2420cdf0e10cSrcweir 		pNewTableObj->SetModel( pNewPage->GetModel() );
2421cdf0e10cSrcweir 
2422cdf0e10cSrcweir 		SdrInsertReason aReason(SDRREASON_VIEWCALL);
2423cdf0e10cSrcweir 		pNewPage->InsertObject(pNewTableObj,CONTAINER_APPEND,&aReason);
2424cdf0e10cSrcweir 
2425cdf0e10cSrcweir 		return true;
2426cdf0e10cSrcweir 	}
2427cdf0e10cSrcweir 	catch( Exception& )
2428cdf0e10cSrcweir 	{
2429cdf0e10cSrcweir 		DBG_ERROR( "svx::SvxTableController::GetMarkedObjModel(), exception caught!" );
2430cdf0e10cSrcweir 	}
2431cdf0e10cSrcweir 	return false;
2432cdf0e10cSrcweir }
2433cdf0e10cSrcweir 
2434cdf0e10cSrcweir // --------------------------------------------------------------------
2435cdf0e10cSrcweir 
PasteObjModel(const SdrModel & rModel)2436cdf0e10cSrcweir bool SvxTableController::PasteObjModel( const SdrModel& rModel )
2437cdf0e10cSrcweir {
2438cdf0e10cSrcweir 	if( mxTableObj.is() && mpView && (rModel.GetPageCount() >= 1) )
2439cdf0e10cSrcweir 	{
2440cdf0e10cSrcweir 		const SdrPage* pPastePage = rModel.GetPage(0);
2441cdf0e10cSrcweir 		if( pPastePage && pPastePage->GetObjCount() == 1 )
2442cdf0e10cSrcweir 		{
2443cdf0e10cSrcweir 			SdrTableObj* pPasteTableObj = dynamic_cast< SdrTableObj* >( pPastePage->GetObj(0) );
2444cdf0e10cSrcweir 			if( pPasteTableObj )
2445cdf0e10cSrcweir 			{
2446cdf0e10cSrcweir 				return PasteObject( pPasteTableObj );
2447cdf0e10cSrcweir 			}
2448cdf0e10cSrcweir 		}
2449cdf0e10cSrcweir 	}
2450cdf0e10cSrcweir 
2451cdf0e10cSrcweir 	return false;
2452cdf0e10cSrcweir }
2453cdf0e10cSrcweir 
2454cdf0e10cSrcweir // --------------------------------------------------------------------
2455cdf0e10cSrcweir 
PasteObject(SdrTableObj * pPasteTableObj)2456cdf0e10cSrcweir bool SvxTableController::PasteObject( SdrTableObj* pPasteTableObj )
2457cdf0e10cSrcweir {
2458cdf0e10cSrcweir 	if( !pPasteTableObj )
2459cdf0e10cSrcweir 		return false;
2460cdf0e10cSrcweir 
2461cdf0e10cSrcweir 	Reference< XTable > xPasteTable( pPasteTableObj->getTable() );
2462cdf0e10cSrcweir 	if( !xPasteTable.is() )
2463cdf0e10cSrcweir 		return false;
2464cdf0e10cSrcweir 
2465cdf0e10cSrcweir 	if( !mxTable.is() )
2466cdf0e10cSrcweir 		return false;
2467cdf0e10cSrcweir 
2468cdf0e10cSrcweir 	sal_Int32 nPasteColumns = xPasteTable->getColumnCount();
2469cdf0e10cSrcweir 	sal_Int32 nPasteRows = xPasteTable->getRowCount();
2470cdf0e10cSrcweir 
2471cdf0e10cSrcweir 	CellPos aStart, aEnd;
2472cdf0e10cSrcweir 	getSelectedCells( aStart, aEnd );
2473cdf0e10cSrcweir 
2474cdf0e10cSrcweir 	if( mpView->IsTextEdit() )
2475cdf0e10cSrcweir 		mpView->SdrEndTextEdit(sal_True);
2476cdf0e10cSrcweir 
2477cdf0e10cSrcweir 	sal_Int32 nColumns = mxTable->getColumnCount();
2478cdf0e10cSrcweir 	sal_Int32 nRows = mxTable->getRowCount();
2479cdf0e10cSrcweir 
2480cdf0e10cSrcweir 	const sal_Int32 nMissing = nPasteRows - ( nRows - aStart.mnRow );
2481cdf0e10cSrcweir 	if( nMissing > 0 )
2482cdf0e10cSrcweir 	{
2483cdf0e10cSrcweir 		Reference< XTableRows > xRows( mxTable->getRows() );
2484cdf0e10cSrcweir 		xRows->insertByIndex( nRows, nMissing );
2485cdf0e10cSrcweir 		nRows = mxTable->getRowCount();
2486cdf0e10cSrcweir 	}
2487cdf0e10cSrcweir 
2488cdf0e10cSrcweir 	nPasteRows = std::min( nPasteRows, nRows - aStart.mnRow );
2489cdf0e10cSrcweir 	nPasteColumns = std::min( nPasteColumns, nColumns - aStart.mnCol );
2490cdf0e10cSrcweir 
2491cdf0e10cSrcweir 	// copy cell contents
2492cdf0e10cSrcweir 	for( sal_Int32 nRow = 0; nRow < nPasteRows; ++nRow )
2493cdf0e10cSrcweir 	{
2494cdf0e10cSrcweir 		for( sal_Int32 nCol = 0; nCol < nPasteColumns; ++nCol )
2495cdf0e10cSrcweir 		{
2496cdf0e10cSrcweir 			CellRef xTargetCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( aStart.mnCol + nCol, aStart.mnRow + nRow ).get() ) );
2497cdf0e10cSrcweir 			if( xTargetCell.is() && !xTargetCell->isMerged() )
2498cdf0e10cSrcweir 			{
2499cdf0e10cSrcweir 				xTargetCell->AddUndo();
2500cdf0e10cSrcweir 				xTargetCell->cloneFrom( dynamic_cast< Cell* >( xPasteTable->getCellByPosition( nCol, nRow ).get() ) );
2501cdf0e10cSrcweir 				nCol += xTargetCell->getColumnSpan() - 1;
2502cdf0e10cSrcweir 			}
2503cdf0e10cSrcweir 		}
2504cdf0e10cSrcweir 	}
2505cdf0e10cSrcweir 
2506cdf0e10cSrcweir 	UpdateTableShape();
2507cdf0e10cSrcweir 
2508cdf0e10cSrcweir 	return true;
2509cdf0e10cSrcweir }
2510cdf0e10cSrcweir 
TakeFormatPaintBrush(boost::shared_ptr<SfxItemSet> &)2511cdf0e10cSrcweir bool SvxTableController::TakeFormatPaintBrush( boost::shared_ptr< SfxItemSet >& /*rFormatSet*/  )
2512cdf0e10cSrcweir {
2513cdf0e10cSrcweir     // SdrView::TakeFormatPaintBrush() is enough
2514cdf0e10cSrcweir     return false;
2515cdf0e10cSrcweir }
2516cdf0e10cSrcweir 
ApplyFormatPaintBrush(SfxItemSet & rFormatSet,bool bNoCharacterFormats,bool bNoParagraphFormats)2517cdf0e10cSrcweir bool SvxTableController::ApplyFormatPaintBrush( SfxItemSet& rFormatSet, bool bNoCharacterFormats, bool bNoParagraphFormats )
2518cdf0e10cSrcweir {
2519cdf0e10cSrcweir 	if( mbCellSelectionMode )
2520cdf0e10cSrcweir 	{
2521cdf0e10cSrcweir     	SdrTextObj* pTableObj = dynamic_cast<SdrTextObj*>( mxTableObj.get() );
2522cdf0e10cSrcweir     	if( !pTableObj )
2523cdf0e10cSrcweir     	    return false;
2524cdf0e10cSrcweir 
2525cdf0e10cSrcweir 		const bool bUndo = mpModel && mpModel->IsUndoEnabled();
2526cdf0e10cSrcweir 
2527cdf0e10cSrcweir 		if( bUndo )
2528cdf0e10cSrcweir 			mpModel->BegUndo( ImpGetResStr(STR_TABLE_NUMFORMAT) );
2529cdf0e10cSrcweir 
2530cdf0e10cSrcweir 		CellPos aStart, aEnd;
2531cdf0e10cSrcweir 		getSelectedCells( aStart, aEnd );
2532cdf0e10cSrcweir 
2533cdf0e10cSrcweir 		SfxItemSet aAttr(*rFormatSet.GetPool(), rFormatSet.GetRanges());
2534cdf0e10cSrcweir 		aAttr.Put(rFormatSet, sal_True);
2535cdf0e10cSrcweir 
2536cdf0e10cSrcweir 		const bool bFrame = (rFormatSet.GetItemState( SDRATTR_TABLE_BORDER ) == SFX_ITEM_SET) || (rFormatSet.GetItemState( SDRATTR_TABLE_BORDER_INNER ) == SFX_ITEM_SET);
2537cdf0e10cSrcweir 
2538cdf0e10cSrcweir 		if( bFrame )
2539cdf0e10cSrcweir 		{
2540cdf0e10cSrcweir 			aAttr.ClearItem( SDRATTR_TABLE_BORDER );
2541cdf0e10cSrcweir 			aAttr.ClearItem( SDRATTR_TABLE_BORDER_INNER );
2542cdf0e10cSrcweir 		}
2543cdf0e10cSrcweir 
2544cdf0e10cSrcweir         const sal_uInt16* pRanges = rFormatSet.GetRanges();
2545cdf0e10cSrcweir         bool bTextOnly = true;
2546cdf0e10cSrcweir 
2547cdf0e10cSrcweir         while( *pRanges )
2548cdf0e10cSrcweir         {
2549cdf0e10cSrcweir             if( (*pRanges != EE_PARA_START) && (*pRanges != EE_CHAR_START) )
2550cdf0e10cSrcweir             {
2551cdf0e10cSrcweir                 bTextOnly = true;
2552cdf0e10cSrcweir                 break;
2553cdf0e10cSrcweir             }
2554cdf0e10cSrcweir             pRanges += 2;
2555cdf0e10cSrcweir         }
2556cdf0e10cSrcweir 
2557cdf0e10cSrcweir         const bool bReplaceAll = false;
2558cdf0e10cSrcweir 		for( sal_Int32 nRow = aStart.mnRow; nRow <= aEnd.mnRow; nRow++ )
2559cdf0e10cSrcweir 		{
2560cdf0e10cSrcweir 			for( sal_Int32 nCol = aStart.mnCol; nCol <= aEnd.mnCol; nCol++ )
2561cdf0e10cSrcweir 			{
2562cdf0e10cSrcweir 				CellRef xCell( dynamic_cast< Cell* >( mxTable->getCellByPosition( nCol, nRow ).get() ) );
2563cdf0e10cSrcweir 				if( xCell.is() )
2564cdf0e10cSrcweir 				{
2565cdf0e10cSrcweir 					if( bUndo )
2566cdf0e10cSrcweir 						xCell->AddUndo();
2567cdf0e10cSrcweir 				    if( !bTextOnly )
2568cdf0e10cSrcweir 					    xCell->SetMergedItemSetAndBroadcast(aAttr, bReplaceAll);
2569cdf0e10cSrcweir 
2570cdf0e10cSrcweir                     SdrText* pText = static_cast< SdrText* >( xCell.get() );
2571cdf0e10cSrcweir                     mpView->ApplyFormatPaintBrushToText( rFormatSet, *pTableObj, pText, bNoCharacterFormats, bNoParagraphFormats );
2572cdf0e10cSrcweir 				}
2573cdf0e10cSrcweir 			}
2574cdf0e10cSrcweir 		}
2575cdf0e10cSrcweir 
2576cdf0e10cSrcweir 		if( bFrame )
2577cdf0e10cSrcweir 		{
2578cdf0e10cSrcweir 			ApplyBorderAttr( rFormatSet );
2579cdf0e10cSrcweir 		}
2580cdf0e10cSrcweir 
2581cdf0e10cSrcweir 		UpdateTableShape();
2582cdf0e10cSrcweir 
2583cdf0e10cSrcweir 		if( bUndo )
2584cdf0e10cSrcweir 			mpModel->EndUndo();
2585cdf0e10cSrcweir 
2586cdf0e10cSrcweir 	    return true;
2587cdf0e10cSrcweir 
2588cdf0e10cSrcweir 	}
2589cdf0e10cSrcweir     return false;
2590cdf0e10cSrcweir }
2591cdf0e10cSrcweir 
2592cdf0e10cSrcweir 
2593cdf0e10cSrcweir // --------------------------------------------------------------------
2594cdf0e10cSrcweir 
IMPL_LINK(SvxTableController,UpdateHdl,void *,EMPTYARG)2595cdf0e10cSrcweir IMPL_LINK( SvxTableController, UpdateHdl, void *, EMPTYARG )
2596cdf0e10cSrcweir {
2597cdf0e10cSrcweir 	mnUpdateEvent = 0;
2598cdf0e10cSrcweir 
2599cdf0e10cSrcweir 	if( mbCellSelectionMode )
2600cdf0e10cSrcweir 	{
2601cdf0e10cSrcweir 		CellPos aStart( maCursorFirstPos );
2602cdf0e10cSrcweir 		CellPos aEnd( maCursorLastPos );
2603cdf0e10cSrcweir 		checkCell(aStart);
2604cdf0e10cSrcweir 		checkCell(aEnd);
2605cdf0e10cSrcweir 		if( aStart != maCursorFirstPos  || aEnd != maCursorLastPos )
2606cdf0e10cSrcweir 		{
2607cdf0e10cSrcweir 			setSelectedCells( aStart, aEnd );
2608cdf0e10cSrcweir 		}
2609cdf0e10cSrcweir 	}
2610cdf0e10cSrcweir 	updateSelectionOverlay();
2611cdf0e10cSrcweir 
2612cdf0e10cSrcweir 	return 0;
2613cdf0e10cSrcweir }
2614cdf0e10cSrcweir 
selectRow(sal_Int32 row)2615*9b8096d0SSteve Yin sal_Bool SvxTableController::selectRow( sal_Int32 row )
2616*9b8096d0SSteve Yin {
2617*9b8096d0SSteve Yin 	if( !mxTable.is() )
2618*9b8096d0SSteve Yin 		return sal_False;
2619*9b8096d0SSteve Yin 	CellPos aStart( 0, row ), aEnd( mxTable->getColumnCount() - 1, row );
2620*9b8096d0SSteve Yin 	StartSelection( aEnd );
2621*9b8096d0SSteve Yin 	gotoCell( aStart, true, 0 );
2622*9b8096d0SSteve Yin 	return sal_True;
2623*9b8096d0SSteve Yin }
selectColumn(sal_Int32 column)2624*9b8096d0SSteve Yin sal_Bool SvxTableController::selectColumn( sal_Int32 column )
2625*9b8096d0SSteve Yin {
2626*9b8096d0SSteve Yin 	if( !mxTable.is() )
2627*9b8096d0SSteve Yin 		return sal_False;
2628*9b8096d0SSteve Yin 	CellPos aStart( column, 0 ), aEnd( column, mxTable->getRowCount() - 1 );
2629*9b8096d0SSteve Yin 	StartSelection( aEnd );
2630*9b8096d0SSteve Yin 	gotoCell( aStart, true, 0 );
2631*9b8096d0SSteve Yin 	return sal_True;
2632*9b8096d0SSteve Yin }
deselectRow(sal_Int32 row)2633*9b8096d0SSteve Yin sal_Bool SvxTableController::deselectRow( sal_Int32 row )
2634*9b8096d0SSteve Yin {
2635*9b8096d0SSteve Yin 	if( !mxTable.is() )
2636*9b8096d0SSteve Yin 		return sal_False;
2637*9b8096d0SSteve Yin 	CellPos aStart( 0, row ), aEnd( mxTable->getColumnCount() - 1, row );
2638*9b8096d0SSteve Yin 	StartSelection( aEnd );
2639*9b8096d0SSteve Yin 	gotoCell( aStart, false, 0 );
2640*9b8096d0SSteve Yin 	return sal_True;
2641*9b8096d0SSteve Yin }
deselectColumn(sal_Int32 column)2642*9b8096d0SSteve Yin sal_Bool SvxTableController::deselectColumn( sal_Int32 column )
2643*9b8096d0SSteve Yin {
2644*9b8096d0SSteve Yin 	if( !mxTable.is() )
2645*9b8096d0SSteve Yin 		return sal_False;
2646*9b8096d0SSteve Yin 	CellPos aStart( column, 0 ), aEnd( column, mxTable->getRowCount() - 1 );
2647*9b8096d0SSteve Yin 	StartSelection( aEnd );
2648*9b8096d0SSteve Yin 	gotoCell( aStart, false, 0 );
2649*9b8096d0SSteve Yin 	return sal_True;
2650*9b8096d0SSteve Yin }
isRowSelected(sal_Int32 nRow)2651*9b8096d0SSteve Yin sal_Bool SvxTableController::isRowSelected( sal_Int32 nRow )
2652*9b8096d0SSteve Yin {
2653*9b8096d0SSteve Yin 	if( hasSelectedCells() )
2654*9b8096d0SSteve Yin 	{
2655*9b8096d0SSteve Yin 		CellPos aFirstPos, aLastPos;
2656*9b8096d0SSteve Yin 		getSelectedCells( aFirstPos, aLastPos );
2657*9b8096d0SSteve Yin 		if( (aFirstPos.mnCol == 0) && (nRow >= aFirstPos.mnRow && nRow <= aLastPos.mnRow) && (mxTable->getColumnCount() - 1 == aLastPos.mnCol) )
2658*9b8096d0SSteve Yin 			return sal_True;
2659*9b8096d0SSteve Yin 	}
2660*9b8096d0SSteve Yin 	return sal_False;
2661*9b8096d0SSteve Yin }
isColumnSelected(sal_Int32 nColumn)2662*9b8096d0SSteve Yin sal_Bool SvxTableController::isColumnSelected( sal_Int32 nColumn )
2663*9b8096d0SSteve Yin {
2664*9b8096d0SSteve Yin 	if( hasSelectedCells() )
2665*9b8096d0SSteve Yin 	{
2666*9b8096d0SSteve Yin 		CellPos aFirstPos, aLastPos;
2667*9b8096d0SSteve Yin 		getSelectedCells( aFirstPos, aLastPos );
2668*9b8096d0SSteve Yin 		if( (aFirstPos.mnRow == 0) && (nColumn >= aFirstPos.mnCol && nColumn <= aLastPos.mnCol) && (mxTable->getRowCount() - 1 == aLastPos.mnRow) )
2669*9b8096d0SSteve Yin 			return sal_True;
2670*9b8096d0SSteve Yin 	}
2671*9b8096d0SSteve Yin 	return sal_False;
2672*9b8096d0SSteve Yin }
2673*9b8096d0SSteve Yin 
isRowHeader()2674*9b8096d0SSteve Yin sal_Bool SvxTableController::isRowHeader()
2675*9b8096d0SSteve Yin {
2676*9b8096d0SSteve Yin 	SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
2677*9b8096d0SSteve Yin 	SdrModel* pModel = pTableObj ? pTableObj->GetModel() : 0;
2678*9b8096d0SSteve Yin 
2679*9b8096d0SSteve Yin 	if( !pTableObj || !pModel )
2680*9b8096d0SSteve Yin 		return sal_False;
2681*9b8096d0SSteve Yin 
2682*9b8096d0SSteve Yin 	TableStyleSettings aSettings( pTableObj->getTableStyleSettings() );
2683*9b8096d0SSteve Yin 
2684*9b8096d0SSteve Yin 	return aSettings.mbUseFirstRow;
2685*9b8096d0SSteve Yin }
2686*9b8096d0SSteve Yin 
isColumnHeader()2687*9b8096d0SSteve Yin sal_Bool SvxTableController::isColumnHeader()
2688*9b8096d0SSteve Yin {
2689*9b8096d0SSteve Yin 	SdrTableObj* pTableObj = dynamic_cast< ::sdr::table::SdrTableObj* >( mxTableObj.get() );
2690*9b8096d0SSteve Yin 	SdrModel* pModel = pTableObj ? pTableObj->GetModel() : 0;
2691*9b8096d0SSteve Yin 
2692*9b8096d0SSteve Yin 	if( !pTableObj || !pModel )
2693*9b8096d0SSteve Yin 		return sal_False;
2694*9b8096d0SSteve Yin 
2695*9b8096d0SSteve Yin 	TableStyleSettings aSettings( pTableObj->getTableStyleSettings() );
2696*9b8096d0SSteve Yin 
2697*9b8096d0SSteve Yin 	return aSettings.mbUseFirstColumn;
2698*9b8096d0SSteve Yin }
2699cdf0e10cSrcweir } }
2700