/**************************************************************

proc_classes.h (C-Munipack project)
Process helper classes
Copyright (C) 2010 David Motl, dmotl@volny.cz

This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.

This program 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 General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.

**************************************************************/

#ifndef MUNIWIN_PROC_CLASSES_H
#define MUNIWIN_PROC_CLASSES_H

#include <gtk/gtk.h>

#include "progress_dlg.h"
#include "helper_classes.h"
#include "frameset_class.h"
#include "table_class.h"
#include "ccdfile_class.h"

//
// Frame conversion context
//
class CConvertProc
{
public:
	// Constructor
	CConvertProc();

	// Destructor
	~CConvertProc();

	// Initialization
	void Init(CConsole *pCon);

	// Convert file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	CmpackKonv		*m_Konv;
	CmpackBitpix	m_Bitpix;
	CmpackBorder	m_Border;
	CmpackChannel	m_Channel;
	int 			m_FlipV, m_FlipH, m_Binning, m_TimeOffset;
};


//
// Time correction context
//
class CTimeCorrProc
{
public:
	// Constructor
	CTimeCorrProc():m_Progress(NULL), m_Seconds(0), m_Reset(false) {}

	// Initialization
	// If reset is true, the time correction is added to the original date and time
	//		the corrections applied previously are ignored
	// If reset is false, the time correction is added to current date and time
	//		the effect is cumulative
	void Init(CConsole *pCon, double seconds, bool reset);

	// Process file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	double			m_Seconds;
	bool			m_Reset;
};


//
// Bias correction context
//
class CBiasCorrProc
{
public:
	// Constructor
	CBiasCorrProc();

	// Destructor
	~CBiasCorrProc();

	// Initialization
	bool Init(CConsole *pCon, const gchar *bias, GError **error);

	// Process file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	CmpackBiasCorr	*m_Bias;
	gchar			*m_BiasFile;

	// Check temporary bias file
	bool CheckBiasFile(const gchar *orig_file);

	// Convert bias frame
	bool ConvertBiasFrame(CConsole *pCon, const gchar *orig_filepath, const gchar *temp_filename, GError **error);
};


//
// Dark correction context
//
class CDarkCorrProc
{
public:
	// Constructor
	CDarkCorrProc();

	// Destructor
	~CDarkCorrProc();

	// Initialization
	bool Init(CConsole *pCon, const gchar *dark, GError **error);

	// Process file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	CmpackDarkCorr	*m_Dark;
	gchar			*m_DarkFile;

	// Check temporary dark file
	bool CheckDarkFile(const gchar *orig_file);

	// Convert bias frame
	bool ConvertDarkFrame(CConsole *pCon, const gchar *orig_filepath, const gchar *temp_filename, GError **error);
};


//
// Flat correction context
//
class CFlatCorrProc
{
public:
	// Constructor
	CFlatCorrProc();

	// Destructor
	~CFlatCorrProc();

	// Initialization
	bool Init(CConsole *pCon, const gchar *flat, GError **error);

	// Process file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	CmpackFlatCorr	*m_Flat;
	gchar			*m_FlatFile;

	// Check temporary dark file
	bool CheckFlatFile(const gchar *orig_file);

	// Convert bias frame
	bool ConvertFlatFrame(CConsole *pCon, const gchar *orig_filepath, const gchar *temp_filename, GError **error);
};


//
// Photometry context
//
class CPhotometryProc
{
public:
	// Constructor
	CPhotometryProc();

	// Destructor
	~CPhotometryProc();

	// Initialization
	void Init(CConsole *pCon);

	// Process file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	CmpackPhot		*m_Phot;
};


//
// Photometry and matching (aligned frames)
//
class CPhotometry2Proc
{
public:
	// Constructor
	CPhotometry2Proc();

	// Destructor
	~CPhotometry2Proc();

	// Initialization, change reference frame
	void Init(CConsole *pCon);
	void InitWithObjects(CConsole *pCon, int length, const CmpackPhotObject *list);

	// Match file
	bool Execute(GtkTreePath *pPath, GError **error);

	// Read image file and prepare it for processing
	bool Read(CCCDFile &file, GError **error);

	// Find position of an object
	bool Pos(double *x, double *y);

	// Star detection and enumeration
	bool FindFirst();
	bool FindNext();
	bool GetData(unsigned mask, CmpackPhotObject &data);
	void FindClose();
	
private:
	CConsole		*m_Progress;
	CmpackPhot		*m_Phot;
};


//
// Matching context (stationary targets)
//
class CMatchingProc
{
public:
	// Constructor
	CMatchingProc();

	// Destructor
	~CMatchingProc();

	// Initialization, change reference frame
	bool InitWithReferenceFrame(CConsole *pCon, GtkTreePath *path, GError **error);

	// Initialization, change reference frame
	bool InitWithCatalogFile(CConsole *pCon, const gchar *cat_file, GError **error);

	// Reinitialization, use current settings
	bool Reinitialize(CConsole *pCon, GError **error);

	// Match file
	bool Execute(GtkTreePath *pPath, GError **error);

private:
	CConsole		*m_Progress;
	CmpackMatch		*m_Match;

	// Check temporary catalogue file
	bool CheckCatalogFile(const gchar *orig_file);

	// Copy catalog photometry and image file
	void ConvertCatFile(const gchar *orig_file, const gchar *temp_file);
};

//
// Matching context (moving targets)
//
class CTrackingProc
{
public:
	// Constructor
	CTrackingProc();

	// Destructor
	~CTrackingProc();

	// Initialization, change reference frame
	bool InitWithReferenceFrame(CConsole *pCon, GtkTreePath *path, GError **error);

	// Reinitialization, use current settings
	bool Reinitialize(CConsole *pCon, GError **error);

	// Match file
	bool Execute(GtkTreePath *pPath, GError **error);

	// Track moving object
	bool MBTrack(GError **error);

private:
	struct tTrackPoint
	{
		int frame_id;			/* Frame ID */
		double jd;				/* Time of observation */
		int obj_index;			/* Minor body object index */
		double src_x, src_y;	/* Position of the object on the source frame */
		double ref_x, ref_y;	/* Position of the object transformed to the reference frame coordinates */
	};

	CConsole		*m_Progress;
	CmpackMatch		*m_Match;
	CTrackingData	m_MBData;
	int				m_refId;	/* Reference ID of the tracked object */
	GSList			*m_keys;	/* List of tTrackPoint - key frames */

	// Clear tracking, reset parameters related to tracking
	void ClearTracking(void);
};

//
// Master bias context
//
class CMasterBiasProc
{
public:
	// Constructor
	CMasterBiasProc();

	// Destructor
	~CMasterBiasProc();

	// Initialization
	bool Open(CConsole *pCon, const gchar *out_file, GError **error);

	// Read file
	bool Add(GtkTreePath *pPath, GError **error);

	// Finalization
	bool Close(GError **error);

private:
	gchar				*m_Path;
	CmpackCcdFile		*m_File;
	CmpackMasterBias	*m_MBias;
};


//
// Master dark context
//
class CMasterDarkProc
{
public:
	// Constructor
	CMasterDarkProc();

	// Destructor
	~CMasterDarkProc();

	// Initialization
	bool Open(CConsole *pCon, const gchar *out_file, GError **error);

	// Read file
	bool Add(GtkTreePath *pPath, GError **error);

	// Finalization
	bool Close(GError **error);

private:
	gchar				*m_Path;
	CmpackCcdFile		*m_File;
	CmpackMasterDark	*m_MDark;
};


//
// Master flat context
//
class CMasterFlatProc
{
public:
	// Constructor
	CMasterFlatProc();

	// Destructor
	~CMasterFlatProc();

	// Initialization
	bool Open(CConsole *pCon, const gchar *out_file, GError **error);

	// Read file
	bool Add(GtkTreePath *pPath, GError **error);

	// Finalization
	bool Close(GError **error);

private:
	gchar				*m_Path;
	CmpackCcdFile		*m_File;
	CmpackMasterFlat	*m_MFlat;
};


//
// Master flat context
//
class CCombineProc
{
public:
	// Constructor
	CCombineProc();

	// Destructor
	~CCombineProc();

	// Initialization
	bool Open(CConsole *pCon, const gchar *out_file, int out_index, bool noAlign, GError **error);

	// Read file
	bool Add(GtkTreePath *pPath, GError **error);

	// Finalization
	bool Close(GError **error);

private:
	CmpackKombine	*m_Kombine;
	CmpackCcdFile	*m_File;
	int				m_OutIndex;
	gchar			*m_Path;
	bool			m_NoAlign;
};

//
// Magnitude-deviation curve (Munifind)
//
CTable *CmpackMagDevCurve(CConsole *pCon, const CFrameSet &fset, int aperture, 
	const CSelection &objs, double *jdmin, double *jdmax, double *magrange, int *auto_comp, GError **error);

//
// Light curve
//
CTable *CmpackLightCurve(CConsole *pCon, CFrameSet &fset, int aperture, 
	const CSelection &sel, const CObjectCoords &obj, const CLocation &loc, 
	CmpackLCurveFlags flags, GError **error);

//
// Aperture-deviation curve
//
CTable *CmpackApDevCurve(CConsole *pCon, const CFrameSet &fset, 
	const CSelection &sel, GError **error);

//
// Track curve (frame offsets)
//
CTable *CmpackTrackCurve(CConsole *pCon, const CFrameSet &fset, 
	GError **error); 

//
// Air mass curve
//
CTable *CmpackAirMassCurve(CConsole *pCon, const CFrameSet &fset, 
	const CObjectCoords &obj, const CLocation &loc, GError **error);

//
// CCD temperature curve
//
CTable *CmpackTemperatureCurve(CConsole *pCon, const CFrameSet &fset,
	GError **error);

//
// Object properties table
//
CTable *CmpackObjectProperties(CConsole *pCon, const CFrameSet &fset, 
	int objectId, int apertureId, GError **error);

//
// Complete reduction of a file
//
class CUpdateProc
{
public:
	// Constructor
	CUpdateProc();

	// Destructor
	~CUpdateProc();

	// Initialization
	bool Init(CConsole *pCon, GError **error);

	// Execute
	bool Execute(GtkTreePath *pPath, bool &try_again, GError **error);

private:
	CConsole		*m_Progress;
	CConvertProc	*m_Konv;
	CTimeCorrProc	*m_TCor;
	CBiasCorrProc	*m_Bias;
	CDarkCorrProc	*m_Dark;
	CFlatCorrProc	*m_Flat;
	CPhotometryProc *m_Phot;
	CMatchingProc	*m_Match;
	CTrackingProc	*m_Track;
};

#endif
