//=============================================================================
//
// file :        MCCE2Electrometers.h
//
// description : Include for the MCCE2Electrometers class.
//
// project :	Novelec MCCE-2 Electrometers
//
// $Author: xavela $
//
// $Revision: 1.16 $
//
// $Log: not supported by cvs2svn $
// Revision 1.14  2010/06/10 15:12:05  xavela
// TEST : control two channels with different MCCE2
//
//
// copyleft :    European Synchrotron Radiation Facility
//               BP 220, Grenoble 38043
//               FRANCE
//
//=============================================================================
//
//  		This file is generated by POGO
//	(Program Obviously used to Generate tango Object)
//
//         (c) - Software Engineering Group - ESRF
//=============================================================================
#ifndef _MCCE2ELECTROMETERS_H
#define _MCCE2ELECTROMETERS_H

#include <tango.h>
//using namespace Tango;
#include "AbstractElectrometerClass.h"
#include "ElectrometerException.h"

/**
 * @author	$Author: xavela $
 * @version	$Revision: 1.16 $
 */

 //	Add your own constants definitions here.
 //-----------------------------------------------


namespace MCCE2Electrometers_ns
{

/**
 * Class Description:
 * This class allows you to control all MCCE-2 Novelec electrometers
 *	through a Serial bus.
 *	<br> Supported types :
 *	<br> Novelec Electrometers : MCCE2
 */

/*
 *	Device States Description:
*  Tango::ON :       Device up and ready
*  Tango::ALARM :    Device initialisation not complete or a bad channel number is set.
*  Tango::FAULT :    Internal electrometer interface is not built or a Serial communication error occurred.
*  Tango::DISABLE :  No electrometer conected!
 */


class MCCE2Electrometers: public Tango::Device_4Impl
{
public :
	//	Add your own data members here
	//-----------------------------------------


	//	Here is the Start of the automatic code generation part
	//-------------------------------------------------------------
/**
 *	@name attributes
 *	Attributs member data.
 */
//@{
		Tango::DevUShort	*attr_electrometerChannel_read;
		Tango::DevUShort	attr_electrometerChannel_write;
		Tango::DevString	*attr_range1_read;
		Tango::DevString	*attr_range2_read;
//@}

/**
 *	@name Device properties
 *	Device properties member data.
 */
//@{
/**
 *	The name of the device which manage the communication.
 */
	string	communicationLinkName;
/**
 *	The first electrometer address configured. <br />
 *	Note : if not connected, push 0 or let empty the property.
 */
	Tango::DevUShort	electrometer1Address;
/**
 *	The second electrometer address configured. <br />
 *	Note : if not connected, push 0 or let empty the property.
 */
	Tango::DevUShort	electrometer2Address;
//@}

/**@name Constructors
 * Miscellaneous constructors */
//@{
/**
 * Constructs a newly allocated Command object.
 *
 *	@param cl	Class.
 *	@param s 	Device Name
 */
	MCCE2Electrometers(Tango::DeviceClass *cl,string &s);
/**
 * Constructs a newly allocated Command object.
 *
 *	@param cl	Class.
 *	@param s 	Device Name
 */
	MCCE2Electrometers(Tango::DeviceClass *cl,const char *s);
/**
 * Constructs a newly allocated Command object.
 *
 *	@param cl	Class.
 *	@param s 	Device name
 *	@param d	Device description.
 */
	MCCE2Electrometers(Tango::DeviceClass *cl,const char *s,const char *d);
//@}

/**@name Destructor
 * Only one desctructor is defined for this class */
//@{
/**
 * The object desctructor.
 */
	~MCCE2Electrometers() {delete_device();};
/**
 *	will be called at device destruction or at init command.
 */
	void delete_device();
//@}


/**@name Miscellaneous methods */
//@{
/**
 *	Initialize the device
 */
	virtual void init_device();
/**
 *	Always executed method befor execution command method.
 */
	virtual void always_executed_hook();

//@}

/**
 * @name MCCE2Electrometers methods prototypes
 */

//@{
/**
 *	Hardware acquisition for attributes.
 */
	virtual void read_attr_hardware(vector<long> &attr_list);
/**
 *	Extract real attribute values for electrometerChannel acquisition result.
 */
	virtual void read_electrometerChannel(Tango::Attribute &attr);
/**
 *	Write electrometerChannel attribute values to hardware.
 */
	virtual void write_electrometerChannel(Tango::WAttribute &attr);
/**
 *	Extract real attribute values for range1 acquisition result.
 */
	virtual void read_range1(Tango::Attribute &attr);
/**
 *	Extract real attribute values for range2 acquisition result.
 */
	virtual void read_range2(Tango::Attribute &attr);
/**
 *	Read/Write allowed for electrometerChannel attribute.
 */
	virtual bool is_electrometerChannel_allowed(Tango::AttReqType type);
/**
 *	Read/Write allowed for range1 attribute.
 */
	virtual bool is_range1_allowed(Tango::AttReqType type);
/**
 *	Read/Write allowed for range2 attribute.
 */
	virtual bool is_range2_allowed(Tango::AttReqType type);
/**
 *	Execution allowed for RangeUP command.
 */
	virtual bool is_RangeUP_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for RangeDOWN command.
 */
	virtual bool is_RangeDOWN_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetZeroVFFunction command.
 */
	virtual bool is_SetZeroVFFunction_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetOffsetZeroV1Function command.
 */
	virtual bool is_SetOffsetZeroV1Function_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetLeakageZeroV2Function command.
 */
	virtual bool is_SetLeakageZeroV2Function_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetTestFunction command.
 */
	virtual bool is_SetTestFunction_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetMeasureFunction command.
 */
	virtual bool is_SetMeasureFunction_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for MCCE2_ON command.
 */
	virtual bool is_MCCE2_ON_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for MCCE2_OFF command.
 */
	virtual bool is_MCCE2_OFF_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for Local command.
 */
	virtual bool is_Local_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for Remote command.
 */
	virtual bool is_Remote_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for Reset command.
 */
	virtual bool is_Reset_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for ClearRegisters command.
 */
	virtual bool is_ClearRegisters_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for GetRange command.
 */
	virtual bool is_GetRange_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetRange command.
 */
	virtual bool is_SetRange_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for GetMode command.
 */
	virtual bool is_GetMode_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for GetPolarity command.
 */
	virtual bool is_GetPolarity_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetPolarity command.
 */
	virtual bool is_SetPolarity_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for GetHzFilter command.
 */
	virtual bool is_GetHzFilter_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetHzFilter command.
 */
	virtual bool is_SetHzFilter_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for GetGain command.
 */
	virtual bool is_GetGain_allowed(const CORBA::Any &any);
/**
 *	Execution allowed for SetGain command.
 */
	virtual bool is_SetGain_allowed(const CORBA::Any &any);
/**
 * This command gets the device state (stored in its <i>device_state</i> data member) and returns it to the caller.
 *	@return	State Code
 *	@exception DevFailed
 */
	virtual Tango::DevState	dev_state();
/**
 * This command gets the device status (stored in its <i>device_status</i> data member) and returns it to the caller.
 *	@return	Status description
 *	@exception DevFailed
 */
	virtual Tango::ConstDevString	dev_status();
/**
 * Up the range of the electrometer.
 *	Throw :
 *	- electrometer::ElectrometerException if the range limit is reached
 *	- Tango::DevFailed if the command cannot be performed
 *	@exception DevFailed
 */
	void	range_up();
/**
 * Down the range of the electrometer.
 *	Throw :
 *	- electrometer::ElectrometerException if the range is negative
 *	- Tango::DevFailed if the command cannot be performed
 *	@exception DevFailed
 */
	void	range_down();
/**
 * Enable the Zero V/F MCCE2 mode.
 *	@exception DevFailed
 */
	void	set_zero_vffunction();
/**
 * Enable the Offset or Zero V1 MCCE2 mode.
 *	@exception DevFailed
 */
	void	set_offset_zero_v1_function();
/**
 * Enable the Leakage or Zero V2 MCCE2 mode.
 *	@exception DevFailed
 */
	void	set_leakage_zero_v2_function();
/**
 * Enable theTest MCCE2 mode.
 *	@exception DevFailed
 */
	void	set_test_function();
/**
 * Enable the Measure MCCE2 mode.
 *	@exception DevFailed
 */
	void	set_measure_function();
/**
 * Enables the function set. Parameters cannot be set (read only mode).
 *	@exception DevFailed
 */
	void	mcce2__on();
/**
 * Disables the function set. Parameters can be changed.
 *	@exception DevFailed
 */
	void	mcce2__off();
/**
 * Enable local keyboard and Key
 *	@exception DevFailed
 */
	void	local();
/**
 * Disable \"MODIFY\" and the \"ON-OFF\" keys
 *	@exception DevFailed
 */
	void	remote();
/**
 * Restart the MCCE-2
 *	@exception DevFailed
 */
	void	reset();
/**
 * Clear error(s)
 *	@exception DevFailed
 */
	void	clear_registers();
/**
 * Returns the electrometer range.
 *	@return	The actual electrometer range
 *	@exception DevFailed
 */
	Tango::DevString	get_range();
/**
 * Apply the specified argin range, on the electrometer, if well formatted.
 *	Else an exception is thrown.
 *	@param	argin	The range to apply on the electrometer
 *	@exception DevFailed
 */
	void	set_range(Tango::DevString);
/**
 * Returns the electrometer mode which can be one of the following values :
 *	MEASURE, V/F Zero, OFFSET, LEAKAGE or TEST.
 *	@return	The electrometer mode (MEASURE, LEAKAGE ...)
 *	@exception DevFailed
 */
	Tango::DevString	get_mode();
/**
 * Returns the electrometer polarity, which can be POSITIVE or NEGATIVE.
 *	@return	The electrometer polarity
 *	@exception DevFailed
 */
	Tango::DevString	get_polarity();
/**
 * Sets the new electrometer polarity. <Br>
 *	NOTE : <Br>
 *	Value must be set in UPPER case !!!
 *	@param	argin	POSITIVE or NEGATIVE
 *	@exception DevFailed
 */
	void	set_polarity(Tango::DevString);
/**
 * Returns the Cut-off frequency in Hz
 *	@return	The MCCE2 cut-off frequency in Hz
 *	@exception DevFailed
 */
	Tango::DevShort	get_hz_filter();
/**
 * The Cut-off frequency in Hz
 *	@param	argin	The MCCE2 cut-off frequency in Hz
 *	@exception DevFailed
 */
	void	set_hz_filter(Tango::DevShort);
/**
 * Returns the MCCE-2 gain
 *	@return	The MCCE2 gain
 *	@exception DevFailed
 */
	Tango::DevShort	get_gain();
/**
 * Sets the new MCCE-2 gain value.
 *	@param	argin	The new MCCE-2 gain
 *	@exception DevFailed
 */
	void	set_gain(Tango::DevUShort);

/**
 *	Read the device properties from database
 */
	 void get_device_property();
//@}

	//	Here is the end of the automatic code generation part
	//-------------------------------------------------------------



protected :
	//	Add your own data members here
	//-----------------------------------------
	AbstractElectrometerClass*	_electrometer;

	std::string _statusStr;

	bool _init_done;		//- used to allow device to start !!
  bool _missing_property;
  bool _updateRange1FromHW;
  bool _updateRange2FromHW;

  std::string read_range_from_hw();

  //- Method to convert all electrometer exceptions on Tango exception
	Tango::DevFailed electrometer_to_tango_exception(const electrometer::ElectrometerException& de);

private :
	AbstractElectrometerClass*	_electrometerCH1; //- electrometer on channel 1
	AbstractElectrometerClass*	_electrometerCH2; //- electrometer on channel 2

  //- instanciate electrometer(s) obj
  void create_electrometers_obj();

};

}	// namespace_ns

#endif	// _MCCE2ELECTROMETERS_H