#include <origin.h>
#include <GetNBox.h>
#include <xfutils.h>
enum{
	index_folder,
	index_recursive,
	index_open,
	index_embed,
	index_project,
	index_page,
	index_layer,
};
enum{
	sm_off,
	sm_low,
	sm_med,
	sm_high,
	sm_custom,
};
//put additional include files here
#include <getnbox.h>
#include <..\Originlab\graph_utils.h>
//put your own support static functions here



/////Sandy 2007-1-4 add for detecting what type of dataplot in gl and decide the factor
//#define PLOT_BASE_ON_WKS 0
//#define PLOT_BASE_ON_MAT 1

//int get_lowest_speed_plot_type_in_gl(GraphLayer& gl, int nPlotBase)
//{
	//int nLowestPlotID;
	//int nTypeID;
	//if(PLOT_BASE_ON_WKS == nPlotBase)
	//{
		//foreach(DataPlot dp in gl.DataPlots)
		//{
			//nTypeID = dp.GetPlotType();
			//if(nTypeID == IDM_PLOT_3D_LINE)
			//{
				//nLowestPlotID = IDM_PLOT_3D_LINE;
				//break;
			//}
			//else if(nTypeID == IDM_PLOT_SCATTER)
				//nLowestPlotID = IDM_PLOT_SCATTER;
		//}
		//
	//}
	//
	//if(PLOT_BASE_ON_MAT == nPlotBase)
	//{
		//
		//foreach(DataPlot dp in gl.DataPlots)
		//{
			//if(nTypeID == IDM_PLOT_MATRIX_IMAGE)
			//{
				//nLowestPlotID = IDM_PLOT_MATRIX_IMAGE;
				//break;
			//}
			//else if(nTypeID == IDM_PLOT_3D_MESH)
				//nLowestPlotID = IDM_PLOT_3D_MESH;
			//else
				//nLowestPlotID = IDM_PLOT_CONTOUR;
		//}
	//}
	//
	//return nLowestPlotID;
//
//}


//int get_gl_plot_data_base(GraphLayer& gl)// 0 for wks, 1 for matrix
//{
	//int nPlotBase = 0;
	//int nTypeID;
	//foreach(DataPlot dp in gl.DataPlots)
	//{
		//nTypeID = dp.GetPlotType();
		//if(nTypeID == IDM_PLOT_3D_MESH || nTypeID == IDM_PLOT_CONTOUR || nTypeID == IDM_PLOT_MATRIX_IMAGE )
		//{
			//nPlotBase = PLOT_BASE_ON_MAT;
		//}
		//else
			//nPlotBase = PLOT_BASE_ON_WKS;
//
	//}		
	//return nPlotBase;
//}
//
//double get_factor_by_dataplot_type(int nTypeID)
//{
	//double dFactor = 1.0;
	//switch(nTypeID)
	//{
	//case IDM_PLOT_SCATTER:
		//dFactor = 1/100.0;
		//break;
	//case IDM_PLOT_3D_LINE:
		//dFactor = 1/50.0;
		//break;
	//case IDM_PLOT_MATRIX_IMAGE:
		//dFactor = 1/100.0;
		//break;
		//
	//case IDM_PLOT_3D_MESH:
		//dFactor = 1/50.0;
		//break;
		//
	//case IDM_PLOT_LINE:		
	//case IDM_PLOT_CONTOUR:
	//default:
		//break;
		//
	//}
	//return dFactor;
//}
//#define SPEED_MODE_OFF 0
//#define SPEED_MODE_LOW 1
//#define SPEED_MODE_MEDIAM 2
//#define SPEED_MODE_HIGH 3
//#define SPEED_MODE_CUSTOM 4
//
//#define SPEED_MODE_LOW_WKS_MAX 5000
//#define SPEED_MODE_LOW_MAT_XYMAX 48
//
//#define SPEED_MODE_MEDIAM_WKS_MAX 3000
//#define SPEED_MODE_MEDIAM_MAT_XYMAX 32
//
//#define SPEED_MODE_HIGH_WKS_MAX 800
//#define SPEED_MODE_HIGH_MAT_XYMAX 16
/////end add by Sandy
//
//bool apply_speed_mode( GraphLayer& gl, int nSpeedMode, int nWks, int nMax, int nMatrix, int nX, int nY )
//{
	//if( !gl )
		//return false;
	//
	/////Sandy 2007-1-4 add for detecting what type of dataplot in gl and decide the factor
	//int nWksPlotID = get_lowest_speed_plot_type_in_gl(gl, PLOT_BASE_ON_WKS);
	//int nMatPlotID = get_lowest_speed_plot_type_in_gl(gl, PLOT_BASE_ON_MAT);
	//double dWksFactor = get_factor_by_dataplot_type(nWksPlotID);
	//double dMatFactor = get_factor_by_dataplot_type(nMatPlotID);
	/////end 
	//
	//Tree 	tr;
	//tr.Root.Speed.Worksheet.nVal = 1;
	//tr.Root.Speed.Matrix.nVal = 1;
	////trSpeed.Worksheet.nVal = 1;
	////trSpeed.Matrix.nVal = 1;
	//switch(nSpeedMode)
	//{
	//case SPEED_MODE_OFF://0:
		//tr.Root.Speed.Worksheet.nVal = 0;
		//tr.Root.Speed.Matrix.nVal = 0;
		////trSpeed.Worksheet.nVal = 0;
		////trSpeed.Matrix.nVal = 0;
		//break;
	//case SPEED_MODE_LOW://1:
		//tr.Root.Speed.Max.nVal = SPEED_MODE_LOW_WKS_MAX * dWksFactor;
		//tr.Root.Speed.XMax.nVal = SPEED_MODE_LOW_MAT_XYMAX * dMatFactor;
		//tr.Root.Speed.YMax.nVal = SPEED_MODE_LOW_MAT_XYMAX * dMatFactor;
		////trSpeed.Max.nVal = SPEED_MODE_LOW_WKS_MAX * dWksFactor;
		////trSpeed.XMax.nVal = SPEED_MODE_LOW_MAT_XYMAX * dMatFactor;
		////trSpeed.YMax.nVal = SPEED_MODE_LOW_MAT_XYMAX * dMatFactor;
		//break;
	//case SPEED_MODE_MEDIAM://2:
		//tr.Root.Speed.Max.nVal = SPEED_MODE_MEDIAM_WKS_MAX * dWksFactor;
		//tr.Root.Speed.XMax.nVal = SPEED_MODE_MEDIAM_MAT_XYMAX * dMatFactor;
		//tr.Root.Speed.YMax.nVal = SPEED_MODE_MEDIAM_MAT_XYMAX * dMatFactor;
		////trSpeed.Max.nVal = SPEED_MODE_MEDIAM_WKS_MAX * dWksFactor;
		////trSpeed.XMax.nVal = SPEED_MODE_MEDIAM_MAT_XYMAX * dMatFactor;
		////trSpeed.YMax.nVal = SPEED_MODE_MEDIAM_MAT_XYMAX * dMatFactor;
		//break;
	//case SPEED_MODE_HIGH://3:
		////trSpeed.Max.nVal = SPEED_MODE_HIGH_WKS_MAX * dWksFactor;
		////trSpeed.XMax.nVal = SPEED_MODE_HIGH_MAT_XYMAX * dMatFactor;
		////trSpeed.YMax.nVal = SPEED_MODE_HIGH_MAT_XYMAX * dMatFactor;
		//tr.Root.Speed.Max.nVal = SPEED_MODE_HIGH_WKS_MAX * dWksFactor;
		//tr.Root.Speed.XMax.nVal = SPEED_MODE_HIGH_MAT_XYMAX * dMatFactor;
		//tr.Root.Speed.YMax.nVal = SPEED_MODE_HIGH_MAT_XYMAX * dMatFactor;
		//break;
	//case SPEED_MODE_CUSTOM://4:
		//tr.Root.Speed.Worksheet.nVal = nWks;
		////trSpeed.Worksheet.nVal = nWks;
		//if( 1 == nWks )
		//{
			//tr.Root.Speed.Max.nVal = nMax; 
			////trSpeed.Max.nVal = nMax * dWksFactor; 
		//}
		//
		//tr.Root.Speed.Matrix.nVal = nMatrix;
		////trSpeed.Matrix.nVal = nMatrix;
		//if( 1 == nMatrix )
		//{
			//tr.Root.Speed.XMax.nVal = nX ;
			//tr.Root.Speed.YMax.nVal = nY ; 
			////trSpeed.XMax.nVal = nX * dMatFactor;
			////trSpeed.YMax.nVal = nY * dMatFactor; 
		//}
		//break;
	//}
	//
	//
	//
	//gl.UpdateThemeIDs(tr.Root);
	//bool bRet = gl.ApplyFormat(tr, true, true);	
	//
	//return true;
//}



void speedmode(const int& index, const int& sm, const int& wks, const int& max, const int& mat, const int& x, const int& y)
{
	vector<string> vsGraphs;
	GraphLayer gl;
	GraphPage gp;
	int nLayers;
	
	
	
	vector<int> vSelectLayersOption = {OPTION_ALL_IN_ACTIVE_FOLDER, OPTION_ALL_RECURSIVE_IN_ACTIVE_FOLDER,
									   OPTION_ALL_OPEN_IN_ACTIVE_FOLDER, OPTION_ALL_EMBEDDED_IN_ACTIVE_FOLDER, 
									   OPTION_ALL_IN_OPJ, OPTION_ACTIVE_PAGE};
	
	switch(index)
	{
	case 0:
	case 1:
	case 2:
	case 3:
	case 4:
		//get_folder_pages_name(vsGraphs, sm);
		get_folder_pages_name(vsGraphs, vSelectLayersOption[index],  0, NULL, NULL, EXIST_PLOT, false);
		
		int nSize = vsGraphs.GetSize();
		for(int ii=0; ii < nSize; ii++)
		{
			GraphPage gp2(vsGraphs[ii]);
			if( !gp2 )
				XF_THROW(CER_INVALID_PAGE);
			
			nLayers = gp2.Layers.Count();
			for(int ii=0; ii < nLayers; ii++)
			{
				gl = gp2.Layers(ii);				
				if( !gl )
					XF_THROW(CER_INVALID_GRAPH);
				
				apply_speed_mode( gl, sm, wks, max, mat, x, y );
			}
		}
		break;
	case 5:
		gp = Project.Pages();
		if( !gp )
			XF_THROW(CER_INVALID_PAGE);
		
		nLayers = gp.Layers.Count();
		for(int ii=0; ii < nLayers; ii++)
		{
			gl = gp.Layers(ii);
			if( !gl )
				XF_THROW(CER_INVALID_GRAPH);
			
			apply_speed_mode( gl, sm, wks, max, mat, x, y );
		}
		break;
	case 6:
		gl = Project.ActiveLayer();
		if( !gl )
			XF_THROW(CER_INVALID_GRAPH);
		
		apply_speed_mode( gl, sm, wks, max, mat, x, y );
		break;
	}
}

//nEventID < 0 on event, like GETNE_ON_INIT, GETNE_ON_OK etc, >0 on change from control
//return 0 to do nothing, return PEVENT_GETN_RET_TO_CLOSE to close dialog
//dwEnables = bOKEnable, bBTN1Enable, bBTN2Enable, bBTN3Enable, , can set to false to disable OK/Apply buttons
//lpcszNodeName = the trGetN TreeNode tag name that generates the event, or is  if GETNE_ON_OK etc
//strAux = optional string for XF Wizard Bar, like DLG_NEED_CHANGE_GRID etc, it will be invalid if from internal node value change event
//strErrMsg = allowing messages to be shown
int speedmode_event1(TreeNode& trGetN, int nRow, int nEventID, DWORD& dwEnables, LPCSTR lpcszNodeName, WndContainer& DynaCntrlContainer, string& strAux, string& strErrMsg)
{
	if( xf_is_extended_event(nEventID) )
		return speedmode_event1_ex(trGetN, nRow, nEventID, dwEnables, lpcszNodeName, DynaCntrlContainer, strAux, strErrMsg);
	DECLARE_BUTTON_ENABLES
	trGetN.wks.Show = (trGetN.sm.nVal == SPEED_MODE_CUSTOM ? true : false);
	
	
	if ( 0 == lstrcmp(lpcszNodeName, "sm") )
	{
		if( 4 == trGetN.sm.nVal )
			trGetN.wks.Show = 1;
	
		else
			trGetN.wks.Show = 0;
	
		return true;
	}
	if ( 0 == lstrcmp(lpcszNodeName, "wks") )
	{
		if( 1 == trGetN.wks.nVal )
			trGetN.max.Enable = 1;
		else
			trGetN.max.Enable = 0;
		
		return true;
	}
	if ( 0 == lstrcmp(lpcszNodeName, "mat") )
	{
		if( 1 == trGetN.mat.nVal )
		{
			trGetN.x.Enable = 1;
			trGetN.y.Enable = 1;
		}
		else
		{
			trGetN.x.Enable = 0;
			trGetN.y.Enable = 0;
		}
		
		return true;
	}
	return false;

}

int speedmode_make_tree(TreeNode& tr, LPCSTR lpcszVarName)
{
	if ( 0 == lstrcmp(lpcszVarName, "setting") )
	{
		GETN_USE(tr)
		GETN_OPTION_BRANCH(GETNBRANCH_OPEN)
		GETN_BEGIN_BRANCH(Worksheet, "Worksheet data, maximum points per curve")
			GETN_OPTION_BRANCH(GETNBRANCH_OPEN)
			GETN_CHECKBOX_BRANCH(1)
			GETN_NUM(Max, "", 3000)
		GETN_END_BRANCH(Worksheet)
		GETN_BEGIN_BRANCH(Matrix, "Matrix data, maximum points per dimension")
			GETN_OPTION_BRANCH(GETNBRANCH_OPEN)
			GETN_CHECKBOX_BRANCH(1)
			GETN_NUM(XMax, "X", 32)
			GETN_NUM(YMax, "Y", 32)
		GETN_END_BRANCH(Matrix)
		
		return 0;
	}
	return false;
}
//nGetNDialog = 0,1,2, corresponding to the XF GetN dropdown, 0 = dialog is not used
//you can change nRet to be one of XFEVT_PROCEED (defualt), XFEVT_ABORT, XFEVT_PROCEED_NO_DLG or XFEVT_PROCEED_WITH_DLG(when nGetNDialog = 0)
//nGetNDialog = -1 when Ok on GetN dialog to allow handler to preocess <auto> etc variables
//dwCntrl is combination of bits
//LTXF_FROM_GUI_MENU, LTXF_FROM_GUI_PROMPT, LTXF_FROM_AUTO_UPDATE, LTXF_FROM_FUNCTION, LTXF_THEME_USED, LTXF_CHANGE_PARAM
void speedmode_before_execute(TreeNode& trGetN, int nGetNDialog, int& nRet, int dwCntrl)
{
	//if(nGetNDialog > 0)
	//{
		//trGetN.wks.Show = 0;
	//}
}
//nEventID < 0 on event, like GETNE_ON_INIT, GETNE_ON_OK etc, >0 on change from control
//return 0 to do nothing, return PEVENT_GETN_RET_TO_CLOSE to close dialog
//dwEnables = bOKEnable, bBTN1Enable, bBTN2Enable, bBTN3Enable, , can set to false to disable OK/Apply buttons
//lpcszNodeName = the trGetN TreeNode tag name that generates the event, or is  if GETNE_ON_OK etc
//strAux = optional string for XF Wizard Bar, like DLG_NEED_CHANGE_GRID etc, it will be invalid if from internal node value change event
//strErrMsg = allowing messages to be shown
int speedmode_event1_ex(TreeNode& trGetN, int nRow, int nEventID, DWORD& dwEnables, LPCSTR lpcszNodeName, WndContainer& DynaCntrlContainer, string& strAux, string& strErrMsg)
{
	return false;
}
