/**************************************************************
 * 
 * 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.
 * 
 *************************************************************/



// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_toolkit.hxx"
#include <toolkit/controls/formattedcontrol.hxx>
#include <toolkit/helper/unopropertyarrayhelper.hxx>
#include <toolkit/helper/property.hxx>

#include <com/sun/star/awt/XVclWindowPeer.hpp>
#include <com/sun/star/util/XNumberFormatsSupplier.hpp>

#include <tools/diagnose_ex.h>
#include <comphelper/processfactory.hxx>
#include <osl/diagnose.h>

//........................................................................
namespace toolkit
{
//........................................................................

	using namespace ::com::sun::star::uno;
	using namespace ::com::sun::star::awt;
	using namespace ::com::sun::star::lang;
	using namespace ::com::sun::star::beans;
	using namespace ::com::sun::star::util;

	// -------------------------------------------------------------------
    namespace
    {
	    // ...............................................................
        ::osl::Mutex& getDefaultFormatsMutex()
        {
            static ::osl::Mutex s_aDefaultFormatsMutex;
            return s_aDefaultFormatsMutex;
        }

        // ...............................................................
        Reference< XNumberFormatsSupplier >& lcl_getDefaultFormatsAccess_nothrow()
        {
            static Reference< XNumberFormatsSupplier > s_xDefaultFormats;
            return s_xDefaultFormats;
        }

        // ...............................................................
        bool& lcl_getTriedCreation()
        {
            static bool s_bTriedCreation = false;
            return s_bTriedCreation;
        }

	    // ...............................................................
        const Reference< XNumberFormatsSupplier >& lcl_getDefaultFormats_throw()
        {
            ::osl::MutexGuard aGuard( getDefaultFormatsMutex() );
            
            bool& rbTriedCreation = lcl_getTriedCreation();
            Reference< XNumberFormatsSupplier >& rDefaultFormats( lcl_getDefaultFormatsAccess_nothrow() );
            if ( !rDefaultFormats.is() && !rbTriedCreation )
            {
                rbTriedCreation = true;
                rDefaultFormats = Reference< XNumberFormatsSupplier >(
                    ::comphelper::createProcessComponent(
                        ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.util.NumberFormatsSupplier" ) ) ),
                    UNO_QUERY_THROW
                );
            }
            if ( !rDefaultFormats.is() )
                throw RuntimeException();

            return rDefaultFormats;
        }

        // ...............................................................
        static oslInterlockedCount  s_refCount(0);

        // ...............................................................
        void    lcl_registerDefaultFormatsClient()
        {
            osl_incrementInterlockedCount( &s_refCount );
        }

        // ...............................................................
        void    lcl_revokeDefaultFormatsClient()
        {
            ::osl::ClearableMutexGuard aGuard( getDefaultFormatsMutex() );
            if ( 0 == osl_decrementInterlockedCount( &s_refCount ) )
            {
                Reference< XNumberFormatsSupplier >& rDefaultFormats( lcl_getDefaultFormatsAccess_nothrow() );
                Reference< XNumberFormatsSupplier > xReleasePotentialLastReference( rDefaultFormats );
                rDefaultFormats.clear();
                lcl_getTriedCreation() = false;

                aGuard.clear();
                xReleasePotentialLastReference.clear();
            }
        }
    }

	// ===================================================================
	// = UnoControlFormattedFieldModel
	// ===================================================================
	// -------------------------------------------------------------------
	UnoControlFormattedFieldModel::UnoControlFormattedFieldModel( const Reference< XMultiServiceFactory >& i_factory )
        :UnoControlModel( i_factory )
        ,m_bRevokedAsClient( false )
        ,m_bSettingValueAndText( false )
	{
		ImplRegisterProperty( BASEPROPERTY_ALIGN );
		ImplRegisterProperty( BASEPROPERTY_BACKGROUNDCOLOR );
		ImplRegisterProperty( BASEPROPERTY_BORDER );
		ImplRegisterProperty( BASEPROPERTY_BORDERCOLOR );
		ImplRegisterProperty( BASEPROPERTY_DEFAULTCONTROL );
		ImplRegisterProperty( BASEPROPERTY_EFFECTIVE_DEFAULT );
		ImplRegisterProperty( BASEPROPERTY_EFFECTIVE_VALUE );
		ImplRegisterProperty( BASEPROPERTY_EFFECTIVE_MAX );
		ImplRegisterProperty( BASEPROPERTY_EFFECTIVE_MIN );
		ImplRegisterProperty( BASEPROPERTY_ENABLED );
		ImplRegisterProperty( BASEPROPERTY_ENABLEVISIBLE );
		ImplRegisterProperty( BASEPROPERTY_FONTDESCRIPTOR );
		ImplRegisterProperty( BASEPROPERTY_FORMATKEY );
		ImplRegisterProperty( BASEPROPERTY_FORMATSSUPPLIER );
		ImplRegisterProperty( BASEPROPERTY_HELPTEXT );
		ImplRegisterProperty( BASEPROPERTY_HELPURL );
		ImplRegisterProperty( BASEPROPERTY_MAXTEXTLEN );
		ImplRegisterProperty( BASEPROPERTY_PRINTABLE );
    	ImplRegisterProperty( BASEPROPERTY_REPEAT );
        ImplRegisterProperty( BASEPROPERTY_REPEAT_DELAY );
		ImplRegisterProperty( BASEPROPERTY_READONLY );
		ImplRegisterProperty( BASEPROPERTY_SPIN );
		ImplRegisterProperty( BASEPROPERTY_STRICTFORMAT );
		ImplRegisterProperty( BASEPROPERTY_TABSTOP );
		ImplRegisterProperty( BASEPROPERTY_TEXT );
		ImplRegisterProperty( BASEPROPERTY_TEXTCOLOR );
    	ImplRegisterProperty( BASEPROPERTY_HIDEINACTIVESELECTION );
		ImplRegisterProperty( BASEPROPERTY_ENFORCE_FORMAT );
		ImplRegisterProperty( BASEPROPERTY_VERTICALALIGN );
		ImplRegisterProperty( BASEPROPERTY_WRITING_MODE );
        ImplRegisterProperty( BASEPROPERTY_CONTEXT_WRITING_MODE );
        ImplRegisterProperty( BASEPROPERTY_MOUSE_WHEEL_BEHAVIOUR );

		Any aTreatAsNumber;
		aTreatAsNumber <<= (sal_Bool) sal_True;
		ImplRegisterProperty( BASEPROPERTY_TREATASNUMBER, aTreatAsNumber );

        lcl_registerDefaultFormatsClient();
	}

	// -------------------------------------------------------------------
    UnoControlFormattedFieldModel::~UnoControlFormattedFieldModel()
    {
    }

	// -------------------------------------------------------------------
	::rtl::OUString UnoControlFormattedFieldModel::getServiceName() throw(RuntimeException)
	{
		return ::rtl::OUString::createFromAscii( szServiceName_UnoControlFormattedFieldModel );
	}

	// -------------------------------------------------------------------
    void SAL_CALL UnoControlFormattedFieldModel::setFastPropertyValue_NoBroadcast( sal_Int32 nHandle, const Any& rValue ) throw (Exception)
    {
        UnoControlModel::setFastPropertyValue_NoBroadcast( nHandle, rValue );

        switch ( nHandle )
        {
        case BASEPROPERTY_EFFECTIVE_VALUE:
            if ( !m_bSettingValueAndText )
                impl_updateTextFromValue_nothrow();
            break;
        case BASEPROPERTY_FORMATSSUPPLIER:
            impl_updateCachedFormatter_nothrow();
            impl_updateTextFromValue_nothrow();
            break;
        case BASEPROPERTY_FORMATKEY:
            impl_updateCachedFormatKey_nothrow();
            impl_updateTextFromValue_nothrow();
            break;
        }
    }

	// -------------------------------------------------------------------
    void UnoControlFormattedFieldModel::impl_updateTextFromValue_nothrow()
    {
        if ( !m_xCachedFormatter.is() )
            impl_updateCachedFormatter_nothrow();
        if ( !m_xCachedFormatter.is() )
            return;

        try
        {
            Any aEffectiveValue;
            getFastPropertyValue( aEffectiveValue, BASEPROPERTY_EFFECTIVE_VALUE );

            ::rtl::OUString sStringValue;
            if ( !( aEffectiveValue >>= sStringValue ) )
            {
                double nDoubleValue(0);
                if ( aEffectiveValue >>= nDoubleValue )
                {
                    sal_Int32 nFormatKey( 0 );
                    if ( m_aCachedFormat.hasValue() )
                        m_aCachedFormat >>= nFormatKey;
                    sStringValue = m_xCachedFormatter->convertNumberToString( nFormatKey, nDoubleValue );
                }
            }

            Reference< XPropertySet > xThis( *this, UNO_QUERY );
            xThis->setPropertyValue( GetPropertyName( BASEPROPERTY_TEXT ), makeAny( sStringValue ) );
        }
        catch( const Exception& )
        {
        	DBG_UNHANDLED_EXCEPTION();
        }
    }

	// -------------------------------------------------------------------
    void UnoControlFormattedFieldModel::impl_updateCachedFormatter_nothrow()
    {
        Any aFormatsSupplier;
        getFastPropertyValue( aFormatsSupplier, BASEPROPERTY_FORMATSSUPPLIER );
        try
        {
            Reference< XNumberFormatsSupplier > xSupplier( aFormatsSupplier, UNO_QUERY );
            if ( !xSupplier.is() )
                xSupplier = lcl_getDefaultFormats_throw();

            if ( !m_xCachedFormatter.is() )
            {
                m_xCachedFormatter = Reference< XNumberFormatter >(
                    ::comphelper::createProcessComponent( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.util.NumberFormatter" ) ) ),
                    UNO_QUERY_THROW
                );
            }
            m_xCachedFormatter->attachNumberFormatsSupplier( xSupplier );
        }
        catch( const Exception& )
        {
        	DBG_UNHANDLED_EXCEPTION();
        }
    }

	// -------------------------------------------------------------------
    void UnoControlFormattedFieldModel::impl_updateCachedFormatKey_nothrow()
    {
        Any aFormatKey;
        getFastPropertyValue( aFormatKey, BASEPROPERTY_FORMATKEY );
        m_aCachedFormat = aFormatKey;
    }

	// -------------------------------------------------------------------
	void UnoControlFormattedFieldModel::dispose(  ) throw(RuntimeException)
    {
        UnoControlModel::dispose();

        ::osl::MutexGuard aGuard( GetMutex() );
        if ( !m_bRevokedAsClient )
        {
            lcl_revokeDefaultFormatsClient();
            m_bRevokedAsClient = true;
        }
    }

    // -------------------------------------------------------------------
    void UnoControlFormattedFieldModel::ImplNormalizePropertySequence( const sal_Int32 _nCount, sal_Int32* _pHandles,
	    Any* _pValues, sal_Int32* _pValidHandles ) const SAL_THROW(())
    {
        ImplEnsureHandleOrder( _nCount, _pHandles, _pValues, BASEPROPERTY_EFFECTIVE_VALUE, BASEPROPERTY_TEXT );

        UnoControlModel::ImplNormalizePropertySequence( _nCount, _pHandles, _pValues, _pValidHandles );
    }

    // -------------------------------------------------------------------
    namespace
    {
        class ResetFlagOnExit
        {
        private:
            bool&   m_rFlag;

        public:
            ResetFlagOnExit( bool& _rFlag )
                :m_rFlag( _rFlag )
            {
            }
            ~ResetFlagOnExit()
            {
                m_rFlag = false;
            }
        };
    }

    // -------------------------------------------------------------------
	void SAL_CALL UnoControlFormattedFieldModel::setPropertyValues( const Sequence< ::rtl::OUString >& _rPropertyNames, const Sequence< Any >& _rValues ) throw(PropertyVetoException, IllegalArgumentException, WrappedTargetException, RuntimeException)
    {
        bool bSettingValue = false;
        bool bSettingText = false;
        for (   const ::rtl::OUString* pPropertyNames = _rPropertyNames.getConstArray();
                pPropertyNames != _rPropertyNames.getConstArray() + _rPropertyNames.getLength();
                ++pPropertyNames
            )
        {
            if ( BASEPROPERTY_EFFECTIVE_VALUE == GetPropertyId( *pPropertyNames ) )
                bSettingValue = true;

            if ( BASEPROPERTY_TEXT == GetPropertyId( *pPropertyNames ) )
                bSettingText = true;
        }

        m_bSettingValueAndText = ( bSettingValue && bSettingText );
        ResetFlagOnExit aResetFlag( m_bSettingValueAndText );
        UnoControlModel::setPropertyValues( _rPropertyNames, _rValues );
    }

    // -------------------------------------------------------------------
	sal_Bool UnoControlFormattedFieldModel::convertFastPropertyValue(
				Any& rConvertedValue, Any& rOldValue, sal_Int32 nPropId,
				const Any& rValue ) throw (IllegalArgumentException)
	{
		if ( BASEPROPERTY_EFFECTIVE_DEFAULT == nPropId && rValue.hasValue() )
		{
			double dVal = 0;
			sal_Int32  nVal = 0;
			::rtl::OUString sVal;
			sal_Bool bStreamed = (rValue >>= dVal);
			if ( bStreamed )
            {
				rConvertedValue <<= dVal;
            }
			else
            {
                bStreamed = (rValue >>= nVal);
                if ( bStreamed )
                {
                    rConvertedValue <<= static_cast<double>(nVal);
                }
                else
                {
                    bStreamed = (rValue >>= sVal);
                    if ( bStreamed )
                    {
                        rConvertedValue <<= sVal;
                    }
                }
            }

			if ( bStreamed )
			{
				getFastPropertyValue( rOldValue, nPropId );
				return !CompareProperties( rConvertedValue, rOldValue );
			}

			throw IllegalArgumentException(
						( ::rtl::OUString::createFromAscii("Unable to convert the given value for the property ")
					+=	GetPropertyName((sal_uInt16)nPropId) )
					+=  ::rtl::OUString::createFromAscii(" (double, integer, or string expected)."),
				static_cast< XPropertySet* >(this),
				1);
		}

		return UnoControlModel::convertFastPropertyValue( rConvertedValue, rOldValue, nPropId, rValue );
	}

	// -------------------------------------------------------------------
	Any UnoControlFormattedFieldModel::ImplGetDefaultValue( sal_uInt16 nPropId ) const
	{
		Any aReturn;
		switch (nPropId)
		{
			case BASEPROPERTY_DEFAULTCONTROL: aReturn <<= ::rtl::OUString( ::rtl::OUString::createFromAscii( szServiceName_UnoControlFormattedField ) ); break;

			case BASEPROPERTY_TREATASNUMBER: aReturn <<= (sal_Bool)sal_True; break;

			case BASEPROPERTY_EFFECTIVE_DEFAULT:
			case BASEPROPERTY_EFFECTIVE_VALUE:
			case BASEPROPERTY_EFFECTIVE_MAX:
			case BASEPROPERTY_EFFECTIVE_MIN:
			case BASEPROPERTY_FORMATKEY:
			case BASEPROPERTY_FORMATSSUPPLIER:
				// (void)
				break;

			default : aReturn = UnoControlModel::ImplGetDefaultValue( nPropId ); break;
		}

		return aReturn;
	}

	// -------------------------------------------------------------------
	::cppu::IPropertyArrayHelper& UnoControlFormattedFieldModel::getInfoHelper()
	{
		static UnoPropertyArrayHelper* pHelper = NULL;
		if ( !pHelper )
		{
			Sequence<sal_Int32>	aIDs = ImplGetPropertyIds();
			pHelper = new UnoPropertyArrayHelper( aIDs );
		}
		return *pHelper;
	}

	// beans::XMultiPropertySet
	// -------------------------------------------------------------------
	Reference< XPropertySetInfo > UnoControlFormattedFieldModel::getPropertySetInfo(  ) throw(RuntimeException)
	{
		static Reference< XPropertySetInfo > xInfo( createPropertySetInfo( getInfoHelper() ) );
		return xInfo;
	}

	// ===================================================================
	// = UnoFormattedFieldControl
	// ===================================================================
	// -------------------------------------------------------------------
	UnoFormattedFieldControl::UnoFormattedFieldControl( const Reference< XMultiServiceFactory >& i_factory )
        :UnoSpinFieldControl( i_factory )
	{
	}

	// -------------------------------------------------------------------
	::rtl::OUString UnoFormattedFieldControl::GetComponentServiceName()
	{
		return ::rtl::OUString::createFromAscii( "FormattedField" );
	}

	// -------------------------------------------------------------------
	void UnoFormattedFieldControl::textChanged(const TextEvent& e) throw(RuntimeException)
	{
		Reference< XVclWindowPeer >  xPeer(getPeer(), UNO_QUERY);
		OSL_ENSURE(xPeer.is(), "UnoFormattedFieldControl::textChanged : what kind of peer do I have ?");

        Sequence< ::rtl::OUString > aNames( 2 );
        aNames[0] = GetPropertyName( BASEPROPERTY_EFFECTIVE_VALUE );
        aNames[1] = GetPropertyName( BASEPROPERTY_TEXT );

        Sequence< Any > aValues( 2 );
        aValues[0] = xPeer->getProperty( aNames[0] );
        aValues[1] = xPeer->getProperty( aNames[1] );

        ImplSetPropertyValues( aNames, aValues, sal_False );
		
		if ( GetTextListeners().getLength() )
			GetTextListeners().textChanged( e );
	}

//........................................................................
}	// namespace toolkit
//........................................................................
