/**************************************************************
 *
 * 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_forms.hxx"
#include "Date.hxx"
#include <tools/debug.hxx>
#include <tools/date.hxx>
#include <connectivity/dbconversion.hxx>
#include <com/sun/star/sdbc/DataType.hpp>

using namespace dbtools;

//.........................................................................
namespace frm
{
//.........................................................................

using namespace ::com::sun::star;
using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::sdb;
using namespace ::com::sun::star::sdbc;
using namespace ::com::sun::star::sdbcx;
using namespace ::com::sun::star::beans;
using namespace ::com::sun::star::util;
using namespace ::com::sun::star::container;
using namespace ::com::sun::star::form;
using namespace ::com::sun::star::awt;
using namespace ::com::sun::star::io;
using namespace ::com::sun::star::lang;

//------------------------------------------------------------------
ODateControl::ODateControl(const Reference<XMultiServiceFactory>& _rxFactory)
			   :OBoundControl(_rxFactory, VCL_CONTROL_DATEFIELD)
{
}

//------------------------------------------------------------------
InterfaceRef SAL_CALL ODateControl_CreateInstance(const Reference<XMultiServiceFactory>& _rxFactory)
{
	return *(new ODateControl(_rxFactory));
}

//------------------------------------------------------------------------------
Sequence<Type> ODateControl::_getTypes()
{
	return OBoundControl::_getTypes();
}

//------------------------------------------------------------------------------
StringSequence SAL_CALL ODateControl::getSupportedServiceNames() throw()
{
	StringSequence aSupported = OBoundControl::getSupportedServiceNames();
	aSupported.realloc(aSupported.getLength() + 1);

	::rtl::OUString*pArray = aSupported.getArray();
	pArray[aSupported.getLength()-1] = FRM_SUN_CONTROL_DATEFIELD;
	return aSupported;
}

/*************************************************************************/
//------------------------------------------------------------------
InterfaceRef SAL_CALL ODateModel_CreateInstance(const Reference<XMultiServiceFactory>& _rxFactory)
{
	return *(new ODateModel(_rxFactory));
}

//------------------------------------------------------------------------------
Sequence<Type> ODateModel::_getTypes()
{
	return OEditBaseModel::_getTypes();
}

//------------------------------------------------------------------
DBG_NAME( ODateModel )
//------------------------------------------------------------------
ODateModel::ODateModel(const Reference<XMultiServiceFactory>& _rxFactory)
			:OEditBaseModel( _rxFactory, VCL_CONTROLMODEL_DATEFIELD, FRM_SUN_CONTROL_DATEFIELD, sal_True, sal_True )
						// use the old control name for compytibility reasons
			,OLimitedFormats( _rxFactory, FormComponentType::DATEFIELD )
{
	DBG_CTOR( ODateModel, NULL );

	m_nClassId = FormComponentType::DATEFIELD;
	initValueProperty( PROPERTY_DATE, PROPERTY_ID_DATE );

	setAggregateSet(m_xAggregateFastSet, getOriginalHandle(PROPERTY_ID_DATEFORMAT));

    osl_incrementInterlockedCount( &m_refCount );
    try
    {
        if ( m_xAggregateSet.is() )
            m_xAggregateSet->setPropertyValue( PROPERTY_DATEMIN, makeAny( (sal_Int32)( ::Date( 1, 1, 1800 ).GetDate() ) ) );
    }
    catch( const Exception& )
    {
    	OSL_ENSURE( sal_False, "ODateModel::ODateModel: caught an exception!" );
    }
    osl_decrementInterlockedCount( &m_refCount );
}

//------------------------------------------------------------------------------
ODateModel::ODateModel( const ODateModel* _pOriginal, const Reference<XMultiServiceFactory>& _rxFactory )
	:OEditBaseModel( _pOriginal, _rxFactory )
	,OLimitedFormats( _rxFactory, FormComponentType::DATEFIELD )
{
	DBG_CTOR( ODateModel, NULL );

	setAggregateSet( m_xAggregateFastSet, getOriginalHandle( PROPERTY_ID_DATEFORMAT ) );
}

//------------------------------------------------------------------------------
ODateModel::~ODateModel( )
{
	setAggregateSet(Reference< XFastPropertySet >(), -1);
	DBG_DTOR( ODateModel, NULL );
}

// XCloneable
//------------------------------------------------------------------------------
IMPLEMENT_DEFAULT_CLONING( ODateModel )

// XServiceInfo
//------------------------------------------------------------------------------
StringSequence SAL_CALL ODateModel::getSupportedServiceNames() throw()
{
	StringSequence aSupported = OBoundControlModel::getSupportedServiceNames();

    sal_Int32 nOldLen = aSupported.getLength();
	aSupported.realloc( nOldLen + 8 );
	::rtl::OUString* pStoreTo = aSupported.getArray() + nOldLen;

    *pStoreTo++ = BINDABLE_CONTROL_MODEL;
    *pStoreTo++ = DATA_AWARE_CONTROL_MODEL;
    *pStoreTo++ = VALIDATABLE_CONTROL_MODEL;

    *pStoreTo++ = BINDABLE_DATA_AWARE_CONTROL_MODEL;
    *pStoreTo++ = VALIDATABLE_BINDABLE_CONTROL_MODEL;

    *pStoreTo++ = FRM_SUN_COMPONENT_DATEFIELD;
    *pStoreTo++ = FRM_SUN_COMPONENT_DATABASE_DATEFIELD;
    *pStoreTo++ = BINDABLE_DATABASE_DATE_FIELD;

    return aSupported;
}

//------------------------------------------------------------------------------
::rtl::OUString SAL_CALL ODateModel::getServiceName() throw ( ::com::sun::star::uno::RuntimeException)
{
	return FRM_COMPONENT_DATEFIELD;	// old (non-sun) name for compatibility !
}

// XPropertySet
//------------------------------------------------------------------------------
void ODateModel::describeFixedProperties( Sequence< Property >& _rProps ) const
{
	BEGIN_DESCRIBE_PROPERTIES( 4, OEditBaseModel )
		DECL_PROP3(DEFAULT_DATE,			sal_Int32,				BOUND, MAYBEDEFAULT, MAYBEVOID);
		DECL_PROP1(TABINDEX,				sal_Int16,				BOUND);
		DECL_PROP1(FORMATKEY,				sal_Int32,				TRANSIENT);
		DECL_IFACE_PROP2(FORMATSSUPPLIER,	XNumberFormatsSupplier,	READONLY, TRANSIENT);
	END_DESCRIBE_PROPERTIES();
}

//------------------------------------------------------------------------------
void SAL_CALL ODateModel::getFastPropertyValue(Any& _rValue, sal_Int32 _nHandle ) const
{
	switch (_nHandle)
	{
		case PROPERTY_ID_FORMATKEY:
			getFormatKeyPropertyValue(_rValue);
			break;
		case PROPERTY_ID_FORMATSSUPPLIER:
			_rValue <<= getFormatsSupplier();
			break;
		default:
			OEditBaseModel::getFastPropertyValue(_rValue, _nHandle);
			break;
	}
}

//------------------------------------------------------------------------------
sal_Bool SAL_CALL ODateModel::convertFastPropertyValue(Any& _rConvertedValue, Any& _rOldValue,
		sal_Int32 _nHandle, const Any& _rValue ) throw(IllegalArgumentException)
{
	if (PROPERTY_ID_FORMATKEY == _nHandle)
		return convertFormatKeyPropertyValue(_rConvertedValue, _rOldValue, _rValue);
	else
		return OEditBaseModel::convertFastPropertyValue(_rConvertedValue, _rOldValue, _nHandle, _rValue );
}

//------------------------------------------------------------------------------
void SAL_CALL ODateModel::setFastPropertyValue_NoBroadcast(sal_Int32 _nHandle, const Any& _rValue) throw ( ::com::sun::star::uno::Exception)
{
	if (PROPERTY_ID_FORMATKEY == _nHandle)
		setFormatKeyPropertyValue(_rValue);
	else
		OEditBaseModel::setFastPropertyValue_NoBroadcast(_nHandle, _rValue);
}

// XLoadListener
//------------------------------------------------------------------------------
void ODateModel::onConnectedDbColumn( const Reference< XInterface >& _rxForm )
{
	OBoundControlModel::onConnectedDbColumn( _rxForm );
	Reference<XPropertySet> xField = getField();
	if (xField.is())
	{
		m_bDateTimeField = sal_False;
		try
		{
			sal_Int32 nFieldType = 0;
			xField->getPropertyValue(PROPERTY_FIELDTYPE) >>= nFieldType;
			m_bDateTimeField = (nFieldType == DataType::TIMESTAMP);
		}
		catch(Exception&)
		{
		}
	}
}

//------------------------------------------------------------------------------
sal_Bool ODateModel::commitControlValueToDbColumn( bool /*_bPostReset*/ )
{
	Any aControlValue( m_xAggregateFastSet->getFastPropertyValue( getValuePropertyAggHandle() ) );
	if ( !compare( aControlValue, m_aSaveValue ) )
	{
		if ( !aControlValue.hasValue() )
			m_xColumnUpdate->updateNull();
		else
		{
			try
			{
				util::Date aDate;
				if ( !( aControlValue >>= aDate ) )
				{
					sal_Int32 nAsInt(0);
					aControlValue >>= nAsInt;
					aDate = DBTypeConversion::toDate(nAsInt);
				}

				if ( !m_bDateTimeField )
					m_xColumnUpdate->updateDate( aDate );
				else
				{
					util::DateTime aDateTime = m_xColumn->getTimestamp();
					aDateTime.Day = aDate.Day;
					aDateTime.Month = aDate.Month;
					aDateTime.Year = aDate.Year;
					m_xColumnUpdate->updateTimestamp( aDateTime );
				}
			}
			catch(Exception&)
			{
				return sal_False;
			}
		}
		m_aSaveValue = aControlValue;
	}
	return sal_True;
}

//------------------------------------------------------------------------------
void ODateModel::impl_translateControlValueToUNODate( Any& _rUNOValue ) const
{
    _rUNOValue = getControlValue();
    if ( _rUNOValue.hasValue() )
    {
        sal_Int32 nDate = 0;
        OSL_VERIFY( _rUNOValue >>= nDate );
        _rUNOValue <<= DBTypeConversion::toDate( nDate );
    }
}

//------------------------------------------------------------------------------
Any ODateModel::translateControlValueToExternalValue( ) const
{
    Any aExternalValue;
    impl_translateControlValueToUNODate( aExternalValue );
    return aExternalValue;
}

//------------------------------------------------------------------------------
Any ODateModel::translateExternalValueToControlValue( const Any& _rExternalValue ) const
{
    Any aControlValue;
    if ( _rExternalValue.hasValue() )
    {
        util::Date aDate;
        OSL_VERIFY( _rExternalValue >>= aDate );
        aControlValue <<= DBTypeConversion::toINT32( aDate );
    }
    return aControlValue;
}

//------------------------------------------------------------------------------
Any ODateModel::translateControlValueToValidatableValue( ) const
{
    Any aValidatableValue;
    impl_translateControlValueToUNODate( aValidatableValue );
    return aValidatableValue;
}

//------------------------------------------------------------------------------
Any ODateModel::translateDbColumnToControlValue()
{
	util::Date aDate = m_xColumn->getDate();
	if (m_xColumn->wasNull())
		m_aSaveValue.clear();
	else
		// the aggregated set expects an Int32 as value ...
		m_aSaveValue <<= DBTypeConversion::toINT32(aDate);

    return m_aSaveValue;
}

//------------------------------------------------------------------------------
Any ODateModel::getDefaultForReset() const
{
    return m_aDefault;
}

//------------------------------------------------------------------------------
void ODateModel::resetNoBroadcast()
{
    OEditBaseModel::resetNoBroadcast();
    m_aSaveValue.clear();
}

//------------------------------------------------------------------------------
Sequence< Type > ODateModel::getSupportedBindingTypes()
{
    return Sequence< Type >( &::getCppuType( static_cast< util::Date* >( NULL ) ), 1 );
}

//.........................................................................
}	// namespace frm
//.........................................................................
