/**************************************************************
 * 
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 * 
 *   http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 * 
 *************************************************************/



#if !TEST_LAYOUT
// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_svx.hxx"
#endif /* !TEST_LAYOUT */

#ifdef SVX_DLLIMPLEMENTATION
#undef SVX_DLLIMPLEMENTATION
#endif

// include ---------------------------------------------------------------

#if TEST_LAYOUT
#include <cstdio>
#endif /* TEST_LAYOUT */
#include <tools/shl.hxx>
#include <svtools/itemset.hxx>
#include <svtools/itempool.hxx>
#include <sfx2/objsh.hxx>
#include <vcl/msgbox.hxx>

#define _SVX_ZOOM_CXX

#include <svx/dialogs.hrc>
#if !TEST_LAYOUT
#include "zoom.hrc"
#endif /* !TEST_LAYOUT */

#include "zoom.hxx"
#if TEST_LAYOUT
#define SVX_ZOOM_OPTIMAL "Zoom optimal"
#define SVX_ZOOM_PAGEWIDTH "Zoom page width"
#define SVX_ZOOM_WHOLEPAGE "Zoom whole page"
struct SvxZoomItem
{
    void SetType( char const* s )
    {
        fputs( s, stderr );
    }

    void SetValue( int n )
    {
        fprintf( stderr, "Zoom factor: %d\n", int( n ) );
    }
};
#define SfxPoolItem LAYOUT_SfxPoolItem
class LAYOUT_SfxPoolItem
{
};
struct SvxViewLayoutItem : public LAYOUT_SfxPoolItem
{
    bool IsBookMode()
    {
        return false;
    }
    USHORT GetValue()
    {
        return 0;
    }

    void SetValue( int n )
    {
        fprintf( stderr, "Zoom factor: %d\n", int( n ) );
    }
    void SetBookMode( bool )
    {
    }
#if 0 // needed for real SfxPoolItem
    int operator==( const SfxPoolItem& ) const
    {
        return 0;
    }
    SfxPoolItem* Clone( SfxItemPool* ) const
    {
        return 0;
    }
#endif
};
#else /* !TEST_LAYOUT */
#include <svx/zoomitem.hxx>
#include <svx/viewlayoutitem.hxx>
#include <svx/dialmgr.hxx>
#endif /* !TEST_LAYOUT */
#include "zoom_def.hxx"

#include <layout/layout-pre.hxx>

#if ENABLE_LAYOUT
#undef SVX_RES
#define SVX_RES(x) #x
#undef SfxModalDialog
#define SfxModalDialog( parent, id ) Dialog( parent, "zoom.xml", id )
#endif /* ENABLE_LAYOUT */

// static ----------------------------------------------------------------

static USHORT pRanges[] =
{
	SID_ATTR_ZOOM,
	SID_ATTR_ZOOM,
	0
};

#define SPECIAL_FACTOR	((USHORT)0xFFFF)

// class SvxZoomDialog ---------------------------------------------------

USHORT SvxZoomDialog::GetFactor() const
{
    if ( a100Btn.IsChecked() )
		return 100;
    if ( aUserBtn.IsChecked() )
		return (USHORT)aUserEdit.GetValue();
	else
		return SPECIAL_FACTOR;
}

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

void SvxZoomDialog::SetFactor( USHORT nNewFactor, USHORT nBtnId )
{
#if TEST_LAYOUT
    printf ("\t\t set factor %d\n", (int)nNewFactor);
#endif /* !TEST_LAYOUT */
	aUserEdit.Disable();

	if ( !nBtnId )
	{
        if ( nNewFactor == 100 )
		{
			a100Btn.Check();
			a100Btn.GrabFocus();
		}
        else
		{
			aUserBtn.Check();
			aUserEdit.Enable();
			aUserEdit.SetValue( (long)nNewFactor );
			aUserEdit.GrabFocus();
		}
	}
	else
	{
		aUserEdit.SetValue( (long)nNewFactor );

		if ( ZOOMBTN_OPTIMAL == nBtnId )
		{
			aOptimalBtn.Check();
			aOptimalBtn.GrabFocus();
		}
		else if ( ZOOMBTN_PAGEWIDTH == nBtnId )
		{
			aPageWidthBtn.Check();
			aPageWidthBtn.GrabFocus();
		}
		else if ( ZOOMBTN_WHOLEPAGE == nBtnId )
		{
			aWholePageBtn.Check();
			aWholePageBtn.GrabFocus();
		}
	}
}

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

void SvxZoomDialog::SetButtonText( USHORT nBtnId, const String& rNewTxt )
{
	switch ( nBtnId )
	{
		case ZOOMBTN_OPTIMAL: // Optimal-Button
			aOptimalBtn.SetText( rNewTxt );
			break;

		case ZOOMBTN_PAGEWIDTH: // Seitenbreite-Button
			aPageWidthBtn.SetText( rNewTxt );
			break;

		case ZOOMBTN_WHOLEPAGE: // Ganze Seite-Button
			aWholePageBtn.SetText( rNewTxt );
			break;

		default:
			DBG_ERROR( "wrong button number" );
	}
}

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

void SvxZoomDialog::HideButton( USHORT nBtnId )
{
	switch ( nBtnId )
	{
		case ZOOMBTN_OPTIMAL: // Optimal-Button
			aOptimalBtn.Hide();
			break;

		case ZOOMBTN_PAGEWIDTH: // Seitenbreite-Button
			aPageWidthBtn.Hide();
			break;

		case ZOOMBTN_WHOLEPAGE: // Ganze Seite-Button
			aWholePageBtn.Hide();
			break;

		default:
			DBG_ERROR( "Falsche Button-Nummer!!!" );
	}
}

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

void SvxZoomDialog::SetLimits( USHORT nMin, USHORT nMax )
{
	DBG_ASSERT( nMin < nMax, "invalid limits" );
    aUserEdit.SetMin( nMin );
	aUserEdit.SetFirst( nMin );
    aUserEdit.SetMax( nMax );
	aUserEdit.SetLast( nMax );
}

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

void SvxZoomDialog::SetSpinSize( USHORT nNewSpin )
{
	aUserEdit.SetSpinSize( nNewSpin );
}

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

#if TEST_LAYOUT
SvxZoomDialog::SvxZoomDialog( Window* pParent ) :
#else /* !TEST_LAYOUT */
SvxZoomDialog::SvxZoomDialog( Window* pParent, const SfxItemSet& rCoreSet ) :
#endif /* !TEST_LAYOUT */

	SfxModalDialog( pParent, SVX_RES( RID_SVXDLG_ZOOM ) ),

    aZoomFl         ( this, SVX_RES( FL_ZOOM ) ),
    aOptimalBtn     ( this, SVX_RES( BTN_OPTIMAL ) ),
    aWholePageBtn   ( this, SVX_RES( BTN_WHOLE_PAGE ) ),
    aPageWidthBtn   ( this, SVX_RES( BTN_PAGE_WIDTH ) ),
    a100Btn         ( this, SVX_RES( BTN_100 ) ),
    aUserBtn        ( this, SVX_RES( BTN_USER ) ),
	aUserEdit       ( this, SVX_RES( ED_USER ) ),

    aViewLayoutFl   ( this, SVX_RES( FL_VIEWLAYOUT ) ),
    aAutomaticBtn   ( this, SVX_RES( BTN_AUTOMATIC ) ),
    aSingleBtn      ( this, SVX_RES( BTN_SINGLE ) ),
    aColumnsBtn     ( this, SVX_RES( BTN_COLUMNS ) ),
    aColumnsEdit    ( this, SVX_RES( ED_COLUMNS ) ),
    aBookModeChk    ( this, SVX_RES( CHK_BOOK ) ),

    aBottomFl       ( this, SVX_RES( FL_BOTTOM ) ),
    aOKBtn          ( this, SVX_RES( BTN_ZOOM_OK ) ),
	aCancelBtn      ( this, SVX_RES( BTN_ZOOM_CANCEL ) ),
	aHelpBtn	    ( this, SVX_RES( BTN_ZOOM_HELP ) ),

#if !TEST_LAYOUT
	rSet		( rCoreSet ),
#endif /* !TEST_LAYOUT */
	pOutSet     ( NULL ),
	bModified	( FALSE )

{
#if ENABLE_LAYOUT
    SetHelpId (SID_ATTR_ZOOM);
#endif /* ENABLE_LAYOUT */
	Link aLink = LINK( this, SvxZoomDialog, UserHdl );
    a100Btn.SetClickHdl( aLink );
    aOptimalBtn.SetClickHdl( aLink );
	aPageWidthBtn.SetClickHdl( aLink );
	aWholePageBtn.SetClickHdl( aLink );
	aUserBtn.SetClickHdl( aLink );

    Link aViewLayoutLink = LINK( this, SvxZoomDialog, ViewLayoutUserHdl );
    aAutomaticBtn.SetClickHdl( aViewLayoutLink );
    aSingleBtn.SetClickHdl( aViewLayoutLink );
    aColumnsBtn.SetClickHdl( aViewLayoutLink );

    Link aViewLayoutSpinLink = LINK( this, SvxZoomDialog, ViewLayoutSpinHdl );
    aColumnsEdit.SetModifyHdl( aViewLayoutSpinLink );

    Link aViewLayoutCheckLink = LINK( this, SvxZoomDialog, ViewLayoutCheckHdl );
    aBookModeChk.SetClickHdl( aViewLayoutCheckLink );

    aOKBtn.SetClickHdl( LINK( this, SvxZoomDialog, OKHdl ) );
	aUserEdit.SetModifyHdl( LINK( this, SvxZoomDialog, SpinHdl ) );

	// Default-Werte
	USHORT nValue = 100;
	USHORT nMin = 10;
	USHORT nMax = 1000;

#if !TEST_LAYOUT
	// ggf. erst den alten Wert besorgen
	const SfxUInt16Item* pOldUserItem = 0;
	SfxObjectShell* pSh = SfxObjectShell::Current();

	if ( pSh )
		pOldUserItem = (const SfxUInt16Item*)pSh->GetItem( SID_ATTR_ZOOM_USER );

	if ( pOldUserItem )
		nValue = pOldUserItem->GetValue();

	// UserEdit initialisieren
	if ( nMin > nValue )
		nMin = nValue;
	if ( nMax < nValue )
		nMax = nValue;
#endif /* !TEST_LAYOUT */
    aUserEdit.SetMin( nMin );
	aUserEdit.SetFirst( nMin );
    aUserEdit.SetMax( nMax );
	aUserEdit.SetLast( nMax );
	aUserEdit.SetValue( nValue );

#if TEST_LAYOUT
    USHORT nZoom = 100;
    SetFactor( nZoom );
#else /* !TEST_LAYOUT */
	const SfxPoolItem& rItem = rSet.Get( rSet.GetPool()->GetWhich( SID_ATTR_ZOOM ) );
	const SvxZoomItem* pZoomItem = dynamic_cast< const SvxZoomItem *>(&rItem);

	if ( pZoomItem )
	{
        const USHORT nZoom = pZoomItem->GetValue();
        const SvxZoomType eType = pZoomItem->GetType();
        const USHORT nValSet = pZoomItem->GetValueSet();
		USHORT nBtnId = 0;

		switch ( eType )
		{
			case SVX_ZOOM_OPTIMAL:
				nBtnId = ZOOMBTN_OPTIMAL;
				break;
			case SVX_ZOOM_PAGEWIDTH:
				nBtnId = ZOOMBTN_PAGEWIDTH;
				break;
			case SVX_ZOOM_WHOLEPAGE:
				nBtnId = ZOOMBTN_WHOLEPAGE;
				break;
			case SVX_ZOOM_PERCENT:
				break;
            case SVX_ZOOM_PAGEWIDTH_NOBORDER:
                break;
		}

        if ( !(SVX_ZOOM_ENABLE_100 & nValSet) )
			a100Btn.Disable();
        if ( !(SVX_ZOOM_ENABLE_OPTIMAL & nValSet) )
			aOptimalBtn.Disable();
		if ( !(SVX_ZOOM_ENABLE_PAGEWIDTH & nValSet) )
			aPageWidthBtn.Disable();
		if ( !(SVX_ZOOM_ENABLE_WHOLEPAGE & nValSet) )
			aWholePageBtn.Disable();
        SetFactor( nZoom, nBtnId );
	}
	else
	{
        const USHORT nZoom = ( (const SfxUInt16Item&)rItem ).GetValue();
        SetFactor( nZoom );
	}

    const SfxPoolItem* pViewLayoutItem = 0;
    if ( SFX_ITEM_SET == rSet.GetItemState( SID_ATTR_VIEWLAYOUT, FALSE, &pViewLayoutItem ) )
    {
        const USHORT nColumns = static_cast<const SvxViewLayoutItem*>(pViewLayoutItem)->GetValue();
        const bool bBookMode  = static_cast<const SvxViewLayoutItem*>(pViewLayoutItem)->IsBookMode();

        if ( 0 == nColumns )
        {
            aAutomaticBtn.Check();
            aColumnsEdit.SetValue( 2 );
            aColumnsEdit.Disable();
            aBookModeChk.Disable();
        }
        else if ( 1 == nColumns)
        {
            aSingleBtn.Check();
            aColumnsEdit.SetValue( 2 );
            aColumnsEdit.Disable();
            aBookModeChk.Disable();
        }
        else
        {
            aColumnsBtn.Check();
            if ( !bBookMode )
            {
                aColumnsEdit.SetValue( nColumns );
                if ( 0 != nColumns % 2 )
                    aBookModeChk.Disable();
            }
            else
            {
                aColumnsEdit.SetValue( nColumns );
                aBookModeChk.Check();
            }
        }
    }
    else
    {
        // hide view layout related controls:
        aViewLayoutFl.Disable();
        aAutomaticBtn.Disable();
        aSingleBtn.Disable();
        aColumnsBtn.Disable();
        aColumnsEdit.Disable();
        aBookModeChk.Disable();
    }
#endif /* !TEST_LAYOUT */

	FreeResource();
}

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

SvxZoomDialog::~SvxZoomDialog()
{
	delete pOutSet;
	pOutSet = 0;
}

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

USHORT* SvxZoomDialog::GetRanges()
{
	return pRanges;
}

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

IMPL_LINK( SvxZoomDialog, UserHdl, RadioButton *, pBtn )
{
#if TEST_LAYOUT
    fprintf( stderr, "SvxZoomDialog::UserHdl\n" );
#endif /* TEST_LAYOUT */
	bModified |= TRUE;

	if ( pBtn == &aUserBtn )
	{
		aUserEdit.Enable();
		aUserEdit.GrabFocus();
	}
	else
		aUserEdit.Disable();
	return 0;
}

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

IMPL_LINK( SvxZoomDialog, SpinHdl, MetricField *, EMPTYARG )
{
	if ( !aUserBtn.IsChecked() )
		return 0;
	bModified |= TRUE;
	return 0;
}

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

IMPL_LINK( SvxZoomDialog, ViewLayoutUserHdl, RadioButton *, pBtn )
{
    bModified |= TRUE;

    if ( pBtn == &aAutomaticBtn )
    {
        aColumnsEdit.Disable();
        aBookModeChk.Disable();
    }
    else if ( pBtn == &aSingleBtn )
    {
        aColumnsEdit.Disable();
        aBookModeChk.Disable();
    }
    else if ( pBtn == &aColumnsBtn )
    {
        aColumnsEdit.Enable();
        aColumnsEdit.GrabFocus();
        if ( 0 == aColumnsEdit.GetValue() % 2 )
            aBookModeChk.Enable();
    }
    else
    {
        DBG_ERROR( "Wrong Button" );
        return 0;
    }

    return 0;
}

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

IMPL_LINK( SvxZoomDialog, ViewLayoutSpinHdl, MetricField *, pEdt )
{
    if ( pEdt == &aColumnsEdit && !aColumnsBtn.IsChecked() )
        return 0;

    if ( 0 == aColumnsEdit.GetValue() % 2 )
        aBookModeChk.Enable();
    else
    {
        aBookModeChk.Check( sal_False );
        aBookModeChk.Disable();
    }

    bModified |= TRUE;

    return 0;
}

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

IMPL_LINK( SvxZoomDialog, ViewLayoutCheckHdl, CheckBox *, pChk )
{
    if ( pChk == &aBookModeChk && !aColumnsBtn.IsChecked() )
        return 0;

    bModified |= TRUE;

    return 0;
}

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

IMPL_LINK( SvxZoomDialog, OKHdl, Button *, pBtn )
{
	if ( bModified || &aOKBtn != pBtn )
	{
#if TEST_LAYOUT
		SvxZoomItem aZoomItem;
		SvxViewLayoutItem aViewLayoutItem;
#else /* !TEST_LAYOUT */
        SvxZoomItem aZoomItem( SVX_ZOOM_PERCENT, 0, rSet.GetPool()->GetWhich( SID_ATTR_ZOOM ) );
        SvxViewLayoutItem aViewLayoutItem( 0, false, rSet.GetPool()->GetWhich( SID_ATTR_VIEWLAYOUT ) );
#endif /* !TEST_LAYOUT */

		if ( &aOKBtn == pBtn )
		{
			USHORT nFactor = GetFactor();

			if ( SPECIAL_FACTOR == nFactor )
			{
				if ( aOptimalBtn.IsChecked() )
                    aZoomItem.SetType( SVX_ZOOM_OPTIMAL );
				else if ( aPageWidthBtn.IsChecked() )
                    aZoomItem.SetType( SVX_ZOOM_PAGEWIDTH );
				else if ( aWholePageBtn.IsChecked() )
                    aZoomItem.SetType( SVX_ZOOM_WHOLEPAGE );
			}
			else
                aZoomItem.SetValue( nFactor );

            if ( aAutomaticBtn.IsChecked() )
            {
                aViewLayoutItem.SetValue( 0 );
                aViewLayoutItem.SetBookMode( false );
            }
            if ( aSingleBtn.IsChecked() )
            {
                aViewLayoutItem.SetValue( 1 );
                aViewLayoutItem.SetBookMode( false );
            }
            else if ( aColumnsBtn.IsChecked() )
            {
                aViewLayoutItem.SetValue( static_cast<USHORT>(aColumnsEdit.GetValue()) );
                aViewLayoutItem.SetBookMode( aBookModeChk.IsChecked() );
            }
        }
		else
		{
			DBG_ERROR( "Wrong Button" );
			return 0;
		}
#if !TEST_LAYOUT
		pOutSet = new SfxItemSet( rSet );
        pOutSet->Put( aZoomItem );

        // don't set attribute in case the whole viewlayout stuff is disabled:
        if ( aViewLayoutFl.IsEnabled() )
            pOutSet->Put( aViewLayoutItem );

		// Wert aus dem UserEdit "uber den Dialog hinaus merken
		SfxObjectShell* pSh = SfxObjectShell::Current();

		if ( pSh )
			pSh->PutItem( SfxUInt16Item( SID_ATTR_ZOOM_USER,
										 (UINT16)aUserEdit.GetValue() ) );
#endif /* !TEST_LAYOUT */
		EndDialog( RET_OK );
	}
	else
		EndDialog( RET_CANCEL );
	return 0;
}


