/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: svx_fmview.cxx,v $
 *
 *  $Revision: 1.6 $
 *
 *  last change: $Author: rt $ $Date: 2006/10/27 20:58:36 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/
#pragma hdrstop




#ifndef	_SVX_FMVWIMP_HXX
#include "fmvwimp.hxx"
#endif

#ifndef _SFX_OBJSH_HXX //autogen
#include <bf_sfx2/objsh.hxx>
#endif
#ifndef _SFXVIEWSH_HXX
#include <bf_sfx2/viewsh.hxx>
#endif
#ifndef _SFXVIEWFRM_HXX
#include <bf_sfx2/viewfrm.hxx>
#endif

#ifndef _SFXDISPATCH_HXX //autogen
#include <bf_sfx2/dispatch.hxx>
#endif




#ifndef _SVX_FMOBJ_HXX
#include "fmobj.hxx"
#endif
#ifndef _SVDITER_HXX //autogen
#include "svditer.hxx"
#endif
#ifndef _SVDPAGV_HXX //autogen
#include "svdpagv.hxx"
#endif
#ifndef _FM_FMMODEL_HXX
#include "fmmodel.hxx"
#endif
#ifndef _FM_FMPAGE_HXX
#include "fmpage.hxx"
#endif
#ifndef _SVX_FMSHELL_HXX
#include "fmshell.hxx"
#endif
#ifndef _SVX_FMPGEIMP_HXX
#include "fmpgeimp.hxx"
#endif

#ifndef _COM_SUN_STAR_SDBC_XROWSETLISTENER_HPP_
#include <com/sun/star/sdbc/XRowSetListener.hpp>
#endif

#ifndef _COM_SUN_STAR_SDB_XSQLQUERYCOMPOSERFACTORY_HPP_
#include <com/sun/star/sdb/XSQLQueryComposerFactory.hpp>
#endif

#ifndef _SVX_FMSHIMP_HXX
#include "fmshimp.hxx"
#endif
#ifndef _SVX_FMSERVS_HXX
#include "fmservs.hxx"
#endif
#ifndef _SVX_FMPROP_HRC
#include "fmprop.hrc"
#endif
#ifndef _SVX_FMUNDO_HXX
#include "fmundo.hxx"
#endif


#ifndef _COM_SUN_STAR_UI_DIALOGS_XEXECUTABLEDIALOG_HPP_
#include <com/sun/star/ui/dialogs/XExecutableDialog.hpp>
#endif
#ifndef _LEGACYBINFILTERMGR_HXX
#include <legacysmgr/legacy_binfilters_smgr.hxx>	//STRIP002 
#endif
namespace binfilter {

using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::lang;
using namespace ::com::sun::star::sdbc;
using namespace ::com::sun::star::sdb;
using namespace ::com::sun::star::ui::dialogs;
using namespace ::com::sun::star::beans;
using namespace ::com::sun::star::container;
using namespace ::com::sun::star::form;
using namespace ::com::sun::star::util;
using namespace ::binfilter::svxform;//STRIP008 using namespace ::svxform;
using namespace ::binfilter ::svx;

//========================================================================
//------------------------------------------------------------------------
/*N*/ TYPEINIT1(FmFormView, E3dView);

//------------------------------------------------------------------------
/*N*/ FmFormView::FmFormView( FmFormModel* pModel, OutputDevice* pOut )
/*N*/ 	:E3dView(pModel,pOut)
/*N*/ {
/*N*/ 	Init();
/*N*/ }

//------------------------------------------------------------------------

//------------------------------------------------------------------------

//------------------------------------------------------------------------
/*N*/ void FmFormView::Init()
/*N*/ {
/*N*/ 	pFormShell = NULL;
/*N*/ 	pImpl = new FmXFormView(::legacy_binfilters::getLegacyProcessServiceFactory(),this);
/*N*/ 	pImpl->acquire();
/*N*/ 
/*N*/ 	//////////////////////////////////////////////////////////////////////
/*N*/ 	// Model setzen
/*N*/ 	SdrModel* pModel = GetModel();
/*N*/ 
/*N*/ 	DBG_ASSERT( pModel->ISA(FmFormModel), "Falsches Model" );
/*N*/ 	if( !pModel->ISA(FmFormModel) ) return;
/*N*/ 	FmFormModel* pFormModel = (FmFormModel*)pModel;
/*N*/ 
/*N*/ 	//////////////////////////////////////////////////////////////////////
/*N*/ 	// DesignMode vom Model holen
/*N*/ 	sal_Bool bInitDesignMode = pFormModel->GetOpenInDesignMode();
/*N*/ 	if ( pFormModel->OpenInDesignModeIsDefaulted( ) )
/*N*/ 	{	// this means that nobody ever explicitly set this on the model, and the model has never
/*N*/ 		// been loaded from a stream.
/*N*/ 		// This means this is a newly created document. This means, we want to have it in design
/*N*/ 		// mode by default (though a newly created model returns true for GetOpenInDesignMode).
/*N*/ 		// We _want_ to have this because it makes a lot of hacks following the original fix
/*N*/ 		// for #94595# unnecessary
/*N*/ 		// #96399# - 2002-10-11 - fs@openoffice.org
/*N*/ 		DBG_ASSERT( !bInitDesignMode, "FmFormView::Init: doesn't the model default to FALSE anymore?" );
/*N*/ 			// if this asserts, either the on-contruction default in the model has changed (then this here
/*N*/ 			// may not be necessary anymore), or we're not dealing with a new document ....
/*N*/ 		bInitDesignMode = sal_True;
/*N*/ 	}
/*N*/ 
/*N*/ 	SfxObjectShell* pObjShell = pFormModel->GetObjectShell();
/*N*/ 	sal_Bool bReadOnly = sal_False;
/*N*/ 	if( pObjShell )
/*N*/ 		bReadOnly = pObjShell->IsReadOnly();
/*N*/ 	if( bReadOnly )
/*N*/ 		bInitDesignMode = sal_False;
/*N*/ 
/*N*/ 	// dieses wird in der Shell vorgenommen
/*N*/ 	// bDesignMode = !bInitDesignMode;	// erzwingt, dass SetDesignMode ausgefuehrt wird
/*N*/ 	SetDesignMode( bInitDesignMode );
/*N*/ }

//------------------------------------------------------------------------
/*N*/ FmFormView::~FmFormView()
/*N*/ {
/*N*/ 	pImpl->notifyViewDying();
/*N*/ 	pImpl->release();
/*N*/ 
/*N*/ 	// Bei der Shell abmelden
/*N*/ 	if( pFormShell )
/*N*/ 		pFormShell->SetView( NULL );
/*N*/ }

//------------------------------------------------------------------------
/*N*/ void FmFormView::MarkListHasChanged()
/*N*/ {
/*N*/ 	E3dView::MarkListHasChanged();
/*N*/ 
/*N*/ 	if ( pFormShell && IsDesignMode() )
/*N*/ 	{
/*N*/ 		FmFormObj* pObj = getMarkedGrid();
/*N*/ 		if ( pImpl->m_pMarkedGrid && pImpl->m_pMarkedGrid != pObj )
/*N*/ 		{DBG_BF_ASSERT(0, "STRIP");//STRIP001 
/*N*/ 		}
/*N*/ 
/*N*/ 		pFormShell->GetImpl()->SetSelectionDelayed(this);
/*N*/ 	}
/*N*/ }

//------------------------------------------------------------------------

//------------------------------------------------------------------------
/*N*/ void FmFormView::DelWin(OutputDevice* pWin1)
/*N*/ {
/*N*/ 	E3dView::DelWin(pWin1);
/*N*/ }

//------------------------------------------------------------------------
/*N*/ void FmFormView::ChangeDesignMode(sal_Bool bDesign)
/*N*/ {
/*N*/ 	if (bDesign == IsDesignMode())
/*N*/ 		return;
/*N*/ 
/*N*/ 	FmFormModel* pModel = PTR_CAST(FmFormModel, GetModel());
/*N*/ 	if (pModel)
/*N*/ 	{	// fuer die Zeit des Uebergangs das Undo-Environment ausschalten, das sichert, dass man dort auch nicht-transiente
/*N*/ 		// Properties mal eben aendern kann (sollte allerdings mit Vorsicht genossen und beim Rueckschalten des Modes
/*N*/ 		// auch immer wieder rueckgaegig gemacht werden. Ein Beispiel ist das Setzen der maximalen Text-Laenge durch das
/*N*/ 		// FmXEditModel an seinem Control.)
/*N*/ 		pModel->GetUndoEnv().Lock();
/*N*/ 	}
/*N*/ 
/*N*/ 	// Reihenfolge beim umsetzen !Designmode
/*N*/ 	// a.) Datenbankforms laden
/*N*/ 	// b.) Designmode an die ::com::sun::star::sdbcx::View weitergeben
/*N*/ 	// c.) Controls aktivieren
/*N*/ 
/*N*/ 	SdrPageView* pCurPageView = GetPageViewPvNum(0);
/*N*/ 	FmFormPage*  pCurPage = pCurPageView ? PTR_CAST(FmFormPage,pCurPageView->GetPage()) : NULL;
/*N*/ 
/*N*/ 	if (pCurPage && bDesign)
/*N*/ 	{
/*N*/ 		DeactivateControls(pCurPageView);
/*N*/ 		DBG_ASSERT( pFormShell && pFormShell->GetImpl(), "FmFormView::ChangeDesignMode: no valid shell!" );
/*N*/ 			// Since fixing 101864, 96009, et.al., we route the deactivation through the FormShell. I _suppose_
/*N*/ 			// the shell is always existent here, but I am not sure if there is a valid scenario where it isn't.
/*N*/ 			// Thus this assertion.
/*N*/ 
/*N*/ 		if ( pFormShell && pFormShell->GetImpl() )
/*N*/ 			pFormShell->GetImpl()->viewDeactivated( this );
/*N*/ 		else
/*?*/ 			pImpl->Deactivate( sal_True );
/*N*/ 	}
/*N*/ 
/*N*/ 	// über all angemeldeten Pages iterieren
/*N*/ 	// nur die aktive wird umgeschaltet
/*N*/ 	sal_uInt16 nCount = GetPageViewCount();
/*N*/ 	for (sal_uInt16 i = 0; i < nCount; i++)
/*N*/ 	{
/*N*/ 		FmFormPage* pPage = PTR_CAST(FmFormPage,GetPageViewPvNum(i)->GetPage());
/*N*/ 		if (pPage)
/*N*/ 		{
/*N*/ 			// during load the environment covers the error handling
/*N*/ 			if (!bDesign)
/*?*/ 				ActivateControls(pCurPageView);
/*N*/ 
/*N*/ 			DBG_ASSERT( pFormShell && pFormShell->GetImpl(), "FmFormView::ChangeDesignMode: no valid shell!" );
/*N*/ 			if ( pFormShell && pFormShell->GetImpl() )
/*N*/ 				pFormShell->GetImpl()->loadForms( pPage, FORMS_RESET | ( bDesign ? FORMS_UNLOAD : FORMS_LOAD ) );
/*N*/ 		}
/*N*/ 	}
/*N*/ 
/*N*/ 	SetDesignMode(bDesign);
/*N*/ 	if (pCurPage)
/*N*/ 	{
/*N*/ 		if (bDesign)
/*N*/ 		{
/*N*/ 			//////////////////////////////////////////////////////////////////
/*N*/ 			// UnoObjekte neu zeichnen
/*N*/ 			if (pCurPageView)
/*N*/ 			{
/*N*/ 				SdrObjListIter aIter(*pCurPage);
/*N*/ 				while( aIter.IsMore() )
/*N*/ 				{
/*?*/ 					SdrObject* pObj = aIter.Next();
/*?*/ 					if (pObj && pObj->IsUnoObj())
/*?*/ 						pObj->SendRepaintBroadcast();
/*N*/ 				}
/*N*/ 			}
/*N*/ 		}
/*N*/ 		else
/*N*/ 		{
/*N*/ 			// notify our shell that we have been activated
/*?*/ 			if ( pFormShell && pFormShell->GetImpl() )
/*?*/ 				pFormShell->GetImpl()->viewActivated( this );
/*?*/ 			else
/*?*/ 				pImpl->Activate();
/*?*/ 
/*?*/ 			// set the auto focus to the first control (if indicated by the model to do so)
/*?*/ 			sal_Bool bForceControlFocus = pModel ? pModel->GetAutoControlFocus() : sal_False;
/*?*/ 			if (bForceControlFocus)
/*?*/				DBG_BF_ASSERT(0, "STRIP"); //STRIP001 /*?*/ 				pImpl->AutoFocus();
/*N*/ 		}
/*N*/ 	}
/*N*/ 
/*N*/ 	// und mein Undo-Environment wieder an
/*N*/ 	if (pModel)
/*N*/ 		pModel->GetUndoEnv().UnLock();
/*N*/ }

//------------------------------------------------------------------------

//------------------------------------------------------------------------
/*N*/ SdrPageView* FmFormView::ShowPage(SdrPage* pPage, const Point& rOffs)
/*N*/ {
/*N*/ 	SdrPageView* pPV = E3dView::ShowPage(pPage, rOffs);
/*N*/ 
/*N*/ 	if (pPage)
/*N*/ 	{
/*N*/ 		if (!IsDesignMode())
/*N*/ 		{
/*N*/ 			// creating the controllers
/*N*/ 			ActivateControls(pPV);
/*N*/ 
/*N*/ 			// Alles deselektieren
/*N*/ 			UnmarkAll();
/*N*/ 
/*N*/ 			// notify our shell that we have been activated
/*N*/ 			if ( pFormShell && pFormShell->GetImpl() )
/*N*/ 				pFormShell->GetImpl()->viewActivated( this );
/*N*/ 			else
/*N*/ 				pImpl->Activate( );
/*N*/ 		}	// nur wenn die Shell bereits im DesignMode ist
/*N*/ 		else if (pFormShell && pFormShell->IsDesignMode())
/*N*/ 		{
/*N*/ 			FmXFormShell* pFormShellImpl = pFormShell->GetImpl();
/*N*/ 			Reference< ::com::sun::star::container::XIndexAccess >  xForms(((FmFormPage*)pPage)->GetForms(), UNO_QUERY);
/*N*/ 			pFormShellImpl->ResetForms(xForms, sal_True);
/*N*/ 
/*N*/ 			// damit der Formular-Navigator auf den Seitenwechsel reagieren kann
/*N*/ 			pFormShell->GetViewShell()->GetViewFrame()->GetBindings().Invalidate(SID_FM_FMEXPLORER_CONTROL , sal_True, sal_False);
/*N*/ 
/*N*/ 			pFormShellImpl->SetSelection(GetMarkList());
/*N*/ 		}
/*N*/ 	}
/*N*/ 	return pPV;
/*N*/ }

//------------------------------------------------------------------------
/*N*/ void FmFormView::HidePage(SdrPageView* pPV)
/*N*/ {
/*N*/ 	if (!IsDesignMode())
/*N*/ 	{
/*N*/ 		// Controls wieder deaktivieren
/*N*/ 		DeactivateControls(pPV);
/*N*/ 		if ( pFormShell && pFormShell->GetImpl() )
/*N*/ 			pFormShell->GetImpl()->viewDeactivated( this );
/*N*/ 		else
/*N*/ 			pImpl->Deactivate( sal_True );
/*N*/ 	}
/*N*/ 	E3dView::HidePage(pPV);
/*N*/ }

//------------------------------------------------------------------------

//------------------------------------------------------------------------

//------------------------------------------------------------------------
/*N*/ void FmFormView::ActivateControls(SdrPageView* pPageView)
/*N*/ {
/*N*/ 	if (!pPageView) return;
/*N*/ 	const SdrPageViewWinList& rWinList = pPageView->GetWinList();
/*N*/ 	for (sal_uInt16 i = 0; i < rWinList.GetCount(); i++)
/*N*/ 	{
/*N*/ 		if (rWinList[i].GetControlList().GetCount())
/*N*/ 		{
/*N*/ 			pImpl->addWindow(&rWinList[i]);
/*N*/ 		}
/*N*/ 	}
/*N*/ }

//------------------------------------------------------------------------
/*N*/ void FmFormView::DeactivateControls(SdrPageView* pPageView)
/*N*/ {
/*N*/ 	if( !pPageView ) return;
/*N*/ 	const SdrPageViewWinList& rWinList = pPageView->GetWinList();
/*N*/ 	for (sal_uInt16 i = 0; i < rWinList.GetCount(); i++)
/*N*/ 	{
/*N*/ 		if (rWinList[i].GetControlList().GetCount())
/*N*/ 		{
/*N*/ 			pImpl->removeWindow(rWinList[i].GetControlContainerRef() );
/*N*/ 		}
/*N*/ 	}
/*N*/ }

//------------------------------------------------------------------------

//------------------------------------------------------------------------

//------------------------------------------------------------------------

//------------------------------------------------------------------------

//------------------------------------------------------------------------
// -----------------------------------------------------------------------------
// -----------------------------------------------------------------------------
// -----------------------------------------------------------------------------
/*N*/ FmFormObj* FmFormView::getMarkedGrid() const
/*N*/ {
/*N*/ 	FmFormObj* pObj = NULL;
/*N*/ 	const SdrMarkList& rMarkList = GetMarkList();
/*N*/ 	if ( 1 == rMarkList.GetMarkCount() )
/*N*/ 	{
/*?*/ 		SdrMark* pMark = rMarkList.GetMark(0);
/*?*/ 		if ( pMark )
/*?*/ 		{
/*?*/ 			pObj = PTR_CAST(FmFormObj,pMark->GetObj());
/*?*/ 			if ( pObj )
/*?*/ 			{
/*?*/ 				Reference<XServiceInfo> xServInfo(pObj->GetUnoControlModel(),UNO_QUERY);
/*?*/ 				if ( !xServInfo.is() || !xServInfo->supportsService(FM_SUN_COMPONENT_GRIDCONTROL) )
/*?*/ 					pObj = NULL;
/*?*/ 			}
/*?*/ 		}
/*N*/ 	}
/*N*/ 	return pObj;
/*N*/ }
// -----------------------------------------------------------------------------
}
