/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: sc_inputwin.cxx,v $
 *
 *  $Revision: 1.7 $
 *
 *  last change: $Author: rt $ $Date: 2006/10/27 15:38:54 $
 *
 *  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
 *
 ************************************************************************/

#ifdef PCH
#endif

#pragma hdrstop

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

#include "scitems.hxx"
#include "eetext.hxx"
#define ITEMID_FIELD EE_FEATURE_FIELD

#include <bf_svx/editview.hxx>
#include <bf_sfx2/dispatch.hxx>
#include <bf_sfx2/event.hxx>
#include <bf_sfx2/imgmgr.hxx>
//#include <vcl/system.hxx>
#include <stdlib.h>		// qsort


#include "inputwin.hxx"
#include "scmod.hxx"
#include "scresid.hxx"
#include "bf_sc.hrc"
#include "globstr.hrc"
#include "editutil.hxx"
#include "inputhdl.hxx"
#include "tabvwsh.hxx"
#include "docsh.hxx"
#include "rangenam.hxx"
#include "compiler.hrc"


namespace binfilter {

#define TEXT_STARTPOS		3
#define THESIZE				1000000	//!!! langt... :-)
#define TBX_WINDOW_HEIGHT 	22 // in Pixeln - fuer alle Systeme gleich?


//==================================================================
//	class ScInputWindowWrapper
//==================================================================

/*N*/ SFX_IMPL_CHILDWINDOW(ScInputWindowWrapper,FID_INPUTLINE_STATUS)

/*N*/ ScInputWindowWrapper::ScInputWindowWrapper( Window*			 pParent,
/*N*/ 											USHORT			 nId,
/*N*/ 											SfxBindings*	 pBindings,
/*N*/ 											SfxChildWinInfo* pInfo )
/*N*/ 	:	SfxChildWindow( pParent, nId )
/*N*/ {
/*N*/     ScInputWindow* pWin=new ScInputWindow( pParent, pBindings );
/*N*/ 	pWindow = pWin;
/*N*/ 
/*N*/ 	pWin->Show();
/*N*/ 
/*N*/ 	pWin->SetSizePixel( pWin->CalcWindowSizePixel() );
/*N*/ 
/*N*/ 	eChildAlignment = SFX_ALIGN_LOWESTTOP;
/*N*/ 	pBindings->Invalidate( FID_TOGGLEINPUTLINE );
/*N*/ }

//	GetInfo fliegt wieder raus, wenn es ein SFX_IMPL_TOOLBOX gibt !!!!

/*N*/ SfxChildWinInfo __EXPORT ScInputWindowWrapper::GetInfo() const
/*N*/ {
/*N*/ 	SfxChildWinInfo aInfo = SfxChildWindow::GetInfo();
/*N*/ 	return aInfo;
/*N*/ }

//==================================================================

#define IMAGE(id) pImgMgr->SeekImage(id,bDark,pScMod)

//==================================================================
//	class ScInputWindow
//==================================================================

/*N*/ ScInputWindow::ScInputWindow( Window* pParent, SfxBindings* pBind ) :
/*N*/ #ifdef OS2
/*N*/ // #37192# ohne WB_CLIPCHILDREN wg. os/2 Paintproblem
/*N*/ 		ToolBox         ( pParent, WinBits(WB_BORDER|WB_3DLOOK) ),
/*N*/ #else
/*N*/ // mit WB_CLIPCHILDREN, sonst Flicker
/*N*/ 		ToolBox         ( pParent, WinBits(WB_BORDER|WB_3DLOOK|WB_CLIPCHILDREN) ),
/*N*/ #endif
/*N*/ 		aWndPos         ( this ),
/*N*/ 		aTextWindow     ( this ),
/*N*/ 		aTextOk			( ScResId( SCSTR_QHELP_BTNOK ) ),		// nicht immer neu aus Resource
/*N*/ 		aTextCancel		( ScResId( SCSTR_QHELP_BTNCANCEL ) ),
/*N*/ 		aTextSum		( ScResId( SCSTR_QHELP_BTNSUM ) ),
/*N*/ 		aTextEqual		( ScResId( SCSTR_QHELP_BTNEQUAL ) ),
/*N*/         pBindings       ( pBind ),
/*N*/ 		bIsOkCancelMode ( FALSE ),
/*N*/ 		pInputHdl		( NULL )
/*N*/ {
/*N*/     SfxImageManager* pImgMgr = pBindings->GetImageManager();
/*N*/ 	ScTabViewShell*	 pViewSh = PTR_CAST( ScTabViewShell, SfxViewShell::Current() );
/*N*/ 	ScModule*		 pScMod  = SC_MOD();
/*N*/ 
/*N*/ 	BOOL bDark = GetDisplayBackground().GetColor().IsDark();
/*N*/ 
/*N*/ 	// Positionsfenster, 3 Buttons, Eingabefenster
/*N*/ 	InsertWindow    ( 1, &aWndPos, 0,								      0 );
/*N*/ 	InsertSeparator ( 												   	  1 );
/*N*/ 	InsertItem      ( SID_INPUT_FUNCTION, IMAGE( SID_INPUT_FUNCTION ), 0, 2 );
/*N*/ 	InsertItem      ( SID_INPUT_SUM, 	  IMAGE( SID_INPUT_SUM ), 0,      3 );
/*N*/ 	InsertItem      ( SID_INPUT_EQUAL,	  IMAGE( SID_INPUT_EQUAL ), 0,    4 );
/*N*/ 	InsertSeparator ( 												      5 );
/*N*/ 	InsertWindow    ( 7, &aTextWindow, 0,                                 6 );
/*N*/ 
/*N*/ 	aWndPos	   .SetQuickHelpText( ScResId( SCSTR_QHELP_POSWND ) );
/*N*/ 	aWndPos    .SetHelpId		( HID_INSWIN_POS );
/*N*/ 	aTextWindow.SetQuickHelpText( ScResId( SCSTR_QHELP_INPUTWND ) );
/*N*/ 	aTextWindow.SetHelpId		( HID_INSWIN_INPUT );
/*N*/ 
/*N*/ 	//	kein SetHelpText, die Hilfetexte kommen aus der Hilfe
/*N*/ 
/*N*/ 	SetItemText ( SID_INPUT_FUNCTION, ScResId( SCSTR_QHELP_BTNCALC ) );
/*N*/ 	SetHelpId	( SID_INPUT_FUNCTION, HID_INSWIN_CALC );
/*N*/ 
/*N*/ 	SetItemText ( SID_INPUT_SUM, aTextSum );
/*N*/ 	SetHelpId	( SID_INPUT_SUM, HID_INSWIN_SUMME );
/*N*/ 
/*N*/ 	SetItemText ( SID_INPUT_EQUAL, aTextEqual );
/*N*/ 	SetHelpId	( SID_INPUT_EQUAL, HID_INSWIN_FUNC );
/*N*/ 
/*N*/ 	SetHelpId( HID_SC_INPUTWIN );	// fuer die ganze Eingabezeile
/*N*/ 
/*N*/ 	aWndPos		.Show();
/*N*/ 	aTextWindow	.Show();
/*N*/ 
/*N*/ 	pInputHdl = SC_MOD()->GetInputHdl( NULL, FALSE );	// use own handler even if ref-handler is set
/*N*/ 	if (pInputHdl)
/*?*/ 		pInputHdl->SetInputWindow( this );
/*N*/ 
/*N*/ 	if ( pInputHdl && pInputHdl->GetFormString().Len() )
/*N*/ 	{
	DBG_BF_ASSERT(0, "STRIP"); //STRIP001 /*?*/ 		//	Umschalten waehrend der Funktionsautopilot aktiv ist
/*N*/ 	}
/*N*/ 	else if ( pInputHdl && pInputHdl->IsInputMode() )
/*N*/ 	{
/*?*/ 		//	wenn waehrend des Editierens die Eingabezeile weg war
/*?*/ 		//	(Editieren einer Formel, dann umschalten zu fremdem Dokument/Hilfe),
/*?*/ 		//	wieder den gerade editierten Text aus dem InputHandler anzeigen
/*?*/ 
	DBG_BF_ASSERT(0, "STRIP"); //STRIP001 /*?*/ 		aTextWindow.SetTextString( pInputHdl->GetEditString() );	// Text anzeigen
/*N*/ 	}
/*N*/ 	else if ( pViewSh )
/*N*/ 	pViewSh->UpdateInputHandler( TRUE ); // unbedingtes Update
/*N*/ 
/*N*/ 	pImgMgr->RegisterToolBox( this, SC_MOD() );
/*N*/ }

/*N*/ __EXPORT ScInputWindow::~ScInputWindow()
/*N*/ {
/*N*/     BOOL bDown = ( ScGlobal::pSysLocale == NULL );    // after Clear?
/*N*/ 
/*N*/ 	//	if any view's input handler has a pointer to this input window, reset it
/*N*/ 	//	(may be several ones, #74522#)
/*N*/ 	//	member pInputHdl is not used here
/*N*/ 
/*N*/ 	if ( !bDown )
/*N*/ 	{
/*N*/ 		TypeId aScType = TYPE(ScTabViewShell);
/*N*/ 		SfxViewShell* pSh = SfxViewShell::GetFirst( &aScType );
/*N*/ 		while ( pSh )
/*N*/ 		{
/*N*/ 			ScInputHandler* pHdl = ((ScTabViewShell*)pSh)->GetInputHandler();
/*N*/ 			if ( pHdl && pHdl->GetInputWindow() == this )
/*?*/ 				pHdl->SetInputWindow( NULL );
/*N*/ 			pSh = SfxViewShell::GetNext( *pSh, &aScType );
/*N*/ 		}
/*N*/ 	}
/*N*/ 
/*N*/     pBindings->GetImageManager()->ReleaseToolBox( this );
/*N*/ }




/*N*/ void __EXPORT ScInputWindow::Resize()
/*N*/ {
/*N*/ 	ToolBox::Resize();
/*N*/ 
/*N*/ 	long nWidth = GetSizePixel().Width();
/*N*/ 	long nLeft  = aTextWindow.GetPosPixel().X();
/*N*/ 	Size aSize  = aTextWindow.GetSizePixel();
/*N*/ 
/*N*/ 	aSize.Width() = Max( ((long)(nWidth - nLeft - 5)), (long)0 );
/*N*/ 	aTextWindow.SetSizePixel( aSize );
/*N*/ 	aTextWindow.Invalidate();
/*N*/ }





















/*N*/ void ScInputWindow::StateChanged( StateChangedType nType )
/*N*/ {
/*N*/ 	ToolBox::StateChanged( nType );
/*N*/ 
/*N*/ 	if ( nType == STATE_CHANGE_INITSHOW ) Resize();
/*N*/ }


//========================================================================
// 							Eingabefenster
//========================================================================

/*N*/ ScTextWnd::ScTextWnd( Window* pParent )
/*N*/ 	:	Window		 ( pParent, WinBits(WB_HIDE | WB_BORDER) ),
/*N*/ 		DragSourceHelper( this ),
/*N*/ 		pEditEngine	 ( NULL ),
/*N*/ 		pEditView	 ( NULL ),
/*N*/         pAccTextData ( NULL ),
/*N*/ 		bIsInsertMode( TRUE ),
/*N*/ 		bFormulaMode ( FALSE ),
/*N*/         bInputMode   ( FALSE )
/*N*/ {
/*N*/ 	EnableRTL( FALSE );		// #106269# EditEngine can't be used with VCL EnableRTL
/*N*/ 
/*N*/ 	bIsRTL = GetSettings().GetLayoutRTL();
/*N*/ 
/*N*/ 	//	#79096# always use application font, so a font with cjk chars can be installed
/*N*/ 	Font aAppFont = GetFont();
/*N*/ 	aTextFont = aAppFont;
/*N*/ 	aTextFont.SetSize( PixelToLogic( aAppFont.GetSize(), MAP_TWIP ) );	// AppFont ist in Pixeln
/*N*/ 
/*N*/ 	const StyleSettings& rStyleSettings = Application::GetSettings().GetStyleSettings();
/*N*/ 
/*N*/ 	Color aBgColor= rStyleSettings.GetWindowColor();
/*N*/ 	Color aTxtColor= rStyleSettings.GetWindowTextColor();
/*N*/ 
/*N*/ 	aTextFont.SetTransparent ( TRUE );
/*N*/ 	aTextFont.SetFillColor   ( aBgColor );
/*N*/ 	//aTextFont.SetColor		 ( COL_FIELDTEXT );
/*N*/ 	aTextFont.SetColor		 (aTxtColor);
/*N*/ 	aTextFont.SetWeight		 ( WEIGHT_NORMAL );
/*N*/ 
/*N*/ 	SetSizePixel		( Size(1,TBX_WINDOW_HEIGHT) );
/*N*/ 	SetBackground		( aBgColor );
/*N*/ 	SetLineColor		( COL_BLACK );
/*N*/ 	SetMapMode		    ( MAP_TWIP );
/*N*/ 	SetPointer		    ( POINTER_TEXT );
/*N*/ }

/*N*/ __EXPORT ScTextWnd::~ScTextWnd()
/*N*/ {
/*N*/ 	delete pEditView;
/*N*/ 	delete pEditEngine;
/*N*/     if (pAccTextData)
/*?*/      {DBG_BF_ASSERT(0, "STRIP"); }//STRIP001    pAccTextData->Dispose();
/*N*/ }


/*N*/ void __EXPORT ScTextWnd::Resize()
/*N*/ {
/*N*/ 	if (pEditView)
/*?*/ 	{
/*?*/ 		Size aSize = GetOutputSizePixel();
/*?*/ 		long nDiff =  aSize.Height()
/*?*/ 					- LogicToPixel( Size( 0, GetTextHeight() ) ).Height();
/*?*/ 
/*?*/ #ifdef OS2_DOCH_NICHT
/*?*/ 		nDiff-=2;		// wird durch 2 geteilt
/*?*/ 						// passt sonst nicht zur normalen Textausgabe
/*?*/ #endif
/*?*/ 
/*?*/ 		aSize.Width() -= 2 * TEXT_STARTPOS - 1;
/*?*/ 
/*?*/ 		pEditView->SetOutputArea(
/*?*/ 			PixelToLogic( Rectangle( Point( TEXT_STARTPOS, (nDiff > 0) ? nDiff/2 : 1 ),
/*?*/ 									 aSize ) ) );
/*N*/ 	}
/*N*/ }






//========================================================================
// 							Positionsfenster
//========================================================================

/*N*/ ScPosWnd::ScPosWnd( Window* pParent ) :
/*N*/ 	ComboBox	( pParent, WinBits(WB_HIDE | WB_DROPDOWN) ),
/*N*/ 	pAccel		( NULL ),
/*N*/ 	bFormulaMode( FALSE )
/*N*/ {
/*N*/ 	Size aSize( GetTextWidth( String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM("GW99999:GW99999")) ),
/*N*/ 				GetTextHeight() );
/*N*/ 	aSize.Width() += 25;	// ??
/*N*/ 	aSize.Height() = CalcWindowSizePixel(11);		// Funktionen: 10 MRU + "andere..."
/*N*/ 	SetSizePixel( aSize );
/*N*/ 
/*N*/ 	FillRangeNames();
/*N*/ 
/*N*/ 	StartListening( *SFX_APP() );		// fuer Navigator-Bereichsnamen-Updates
/*N*/ }

/*N*/ __EXPORT ScPosWnd::~ScPosWnd()
/*N*/ {
/*N*/ 	EndListening( *SFX_APP() );
/*N*/ 
/*N*/ 	delete pAccel;
/*N*/ }



/*N*/ void ScPosWnd::FillRangeNames()
/*N*/ {
/*N*/ 	Clear();
/*N*/ 
/*N*/ 	SfxObjectShell* pObjSh = SfxObjectShell::Current();
/*N*/ 	if ( pObjSh && pObjSh->ISA(ScDocShell) )
/*N*/ 	{
/*?*/ 		ScDocument* pDoc = ((ScDocShell*)pObjSh)->GetDocument();
/*?*/ 
/*?*/ 		//	per Hand sortieren, weil Funktionen nicht sortiert werden:
/*?*/ 
/*?*/ 		ScRangeName* pRangeNames = pDoc->GetRangeName();
/*?*/ 		USHORT nCount = pRangeNames->GetCount();
/*?*/ 		if ( nCount > 0 )
/*?*/ 		{
/*?*/ 			USHORT nValidCount = 0;
/*?*/ 			ScRange aDummy;
/*?*/ 			USHORT i;
/*?*/ 			for ( i=0; i<nCount; i++ )
/*?*/ 			{
/*?*/ 				ScRangeData* pData = (*pRangeNames)[i];
/*?*/ 				if (pData->IsReference(aDummy))
/*?*/ 					nValidCount++;
/*?*/ 			}
/*?*/ 			if ( nValidCount )
/*?*/ 			{
/*?*/ 				ScRangeData** ppSortArray = new ScRangeData* [ nValidCount ];
/*?*/ 				USHORT j;
/*?*/ 				for ( i=0, j=0; i<nCount; i++ )
/*?*/ 				{
/*?*/ 					ScRangeData* pData = (*pRangeNames)[i];
/*?*/ 					if (pData->IsReference(aDummy))
/*?*/ 						ppSortArray[j++] = pData;
/*?*/ 				}
/*?*/ #ifndef ICC
/*?*/ 				qsort( (void*)ppSortArray, nValidCount, sizeof(ScRangeData*),
/*?*/ 					&ScRangeData::QsortNameCompare );
/*?*/ #else
/*?*/ 				qsort( (void*)ppSortArray, nValidCount, sizeof(ScRangeData*),
/*?*/ 					ICCQsortNameCompare );
/*?*/ #endif
/*?*/ 				for ( j=0; j<nValidCount; j++ )
/*?*/ 					InsertEntry( ppSortArray[j]->GetName() );
/*?*/ 				delete [] ppSortArray;
/*?*/ 			}
/*?*/ 		}
/*N*/ 	}
/*N*/ 	SetText(aPosStr);
/*N*/ }


/*N*/ void __EXPORT ScPosWnd::SFX_NOTIFY( SfxBroadcaster& rBC, const TypeId& rBCType,
/*N*/ 									  const SfxHint& rHint, const TypeId& rHintType )
/*N*/ {
/*N*/ 	if ( !bFormulaMode )
/*N*/ 	{
/*N*/ 		//	muss die Liste der Bereichsnamen updgedated werden?
/*N*/ 
/*N*/ 		if ( rHint.ISA(SfxSimpleHint) )
/*N*/ 		{
/*N*/ 			ULONG nHintId = ((SfxSimpleHint&)rHint).GetId();
/*N*/ 			if ( nHintId == SC_HINT_AREAS_CHANGED || nHintId == SC_HINT_NAVIGATOR_UPDATEALL)
/*N*/ 				FillRangeNames();
/*N*/ 		}
/*N*/ 		else if ( rHint.ISA(SfxEventHint) )
/*N*/ 		{
/*N*/ 			ULONG nEventId = ((SfxEventHint&)rHint).GetEventId();
/*N*/ 			if ( nEventId == SFX_EVENT_ACTIVATEDOC )
/*?*/ 				FillRangeNames();
/*N*/ 		}
/*N*/ 	}
/*N*/ }










}
