/*------------------------------------------------------------------------------*
 * File Name: ReportTreeBrowser.c				 													*
 * Creation: 																	*
 * Purpose: OriginC Source C file												*
 * Copyright (c) ABCD Corp.	2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010		*
 * All Rights Reserved															*
 * 																				*
 * Modification Log:															*
 * Jasmine 01/17/07 GET_POLYNOMIAL_ORDER										*
 * Jasmine 01/18/07 ADD_REPORT_TREE_FILTER_STRING								*
 * Jasmine 01/22/07 ONLY_ACCEPT_SPECIFIED_CLASSES								*
 * Jasmine 01/22/07 REMOVE_SELECTION_IF_CANCEL									*
 * Jasmine 01/22/07 ERR_MSG_NO_REPORT_TREE										*
 * Jasmine 03/27/06 DLG_RESIZE_PAINT_MESS										*
 * Jasmine 03/30/07 REMOVE_ONLY_ONE_EQUATION_OR_DATASET							* 
 *	Hong 02/24/09 FIX_RUNTIME_ERROR_BORWSER_NLFIT_REPORT_CRATED_BY_NLEND		*
 *	Folger 05/20/09 QA80-13638 FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT
 *	Kenny 10/19/2009 REPORT_TREE_BROWSER_SHOWS_UNWANTED_INSERT_MODE_COMBO		*
 *------------------------------------------------------------------------------*/
 
#include <Origin.h>
#include <operation.h>
#include <ocu.h> /// Hong 11/06/07 v8.0741 MORE_LOCALIZATION
#include "nlsf_utils.h"
#include "DialogEx.h"

#define STR_DLG_NAME 					_L("Report Tree Browser")
enum{	//report tree list columns
	RLC_UID,//hide
	RLC_WKS,
	RLC_CLASS,
	RLC_DESC,
	RLC_EQUATION,
	RLC_INPUT_DATA,
	RLC_INPUT_DATA_WEIGHT_INFO,///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
	RLC_TIME,
	
	RLC_LAST
};
enum{
	FILTER_NONE,
	FILTER_SAME_EQUATION,
	FILTER_SAME_INPUT_DATA,
	FILTER_ALL
};

///------ Folger 05/20/09 QA80-13638 FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT
static	bool	_check_get_gui_node(TreeNode& tr, Worksheet& wks)
{
	vector<uint>	vUIDs;
	if( !wks.FindIncomingOperations(vUIDs) || 0 >= vUIDs.GetSize() )
		return false;
	
	Operation&		op = (Operation &) Project.GetOperationObject(vUIDs[0]);
	if ( !op )
		return false;
	
	Tree			trOp;
	op.GetTree(trOp);
	if ( !trOp.GUI )
		return false;
	
	tr = trOp.GUI;
	return true;
}
///------ End FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT

class ReportTrBrowser : public MultiPaneDlg
{
public:
	///Jasmine 01/18/07 ADD_REPORT_TREE_FILTER_STRING
	ReportTrBrowser(int nSelMode = 0, LPCSTR lpcszFilter = NULL) : MultiPaneDlg(IDD_REPORT_TREE_DLG, "ODlg8")
	{
		m_nSelMode = nSelMode;
		if(lpcszFilter)
			m_strFilter = lpcszFilter;
	}
	///End ADD_REPORT_TREE_FILTER_STRING
	~ReportTrBrowser()
	{
	}
	int  DoModalEx(HWND hParent = NULL) 
	{
		InitMsgMap();
		int nRet = MultiPaneDlg::DoModal(hParent);
		return nRet;
	}
	int GetSelection(string& strResults, vector<uint>& vuIDs)
	{
		vuIDs.RemoveAll();
		if(1 == m_nSelMode)			
		{	///Jasmine 01/22/07 REMOVE_SELECTION_IF_CANCEL
			if(m_ReportList.GetSelectedRow() < m_ReportList.GetRowOffset())
				return 0;
			///End REMOVE_SELECTION_IF_CANCEL
			vuIDs.Add(atoi(m_ReportList.GetCell(m_ReportList.GetSelectedRow(), RLC_UID)));
			strResults = m_ReportList.GetCell(m_ReportList.GetSelectedRow(), RLC_WKS);
			return 1;
		}
		vector<string> vsResults;
		for(int ii = m_SelList.GetRowOffset(); ii < m_SelList.GetRows(); ii++)
		{
			vuIDs.Add(atoi(m_SelList.GetCell(ii, RLC_UID)));
			vsResults.Add(m_SelList.GetCell(ii, RLC_WKS));
		}
		strResults.SetTokens(vsResults, STR_PAGE_LIST_SEPARATOR);
		return vuIDs.GetSize();
	}
	
protected :	
EVENTS_BEGIN
	ON_INIT(OnInitDialog) 
	ON_DESTROY(OnDestroy)
	ON_READY(OnReady)
	ON_SIZE(OnDlgResize)
	ON_INIT_SIZE(OnInitSize)		///Jasmine 07/20/07 MAKE_A_GOOD_SIZE
	ON_RESTORESIZE(OnRestoreSize)
	ON_SYSCOMMAND(OnSystemCommand)//make min button to rollup dialog
	ON_OK(OnClickOK)
	ON_CANCEL(OnClickCancel)
	ON_BN_CLICKED(IDC_SHOW_HIDE_BTN, OnShowBottomPane)
	ON_BN_CLICKED(IDC_ADD_BTN, OnAdd)
	ON_BN_CLICKED(IDC_REMOVE_BTN, OnRemove)
	ON_GRID_DBLCLICK(IDC_REPORT_TREE_LIST, OnDblClick)
EVENTS_END

	BOOL OnInitDialog()
	{
		///Jasmine 07/20/07 MAKE_A_GOOD_SIZE
		m_strDlgName = STR_DLG_NAME;
		if(1 == m_nSelMode)
			m_strDlgName += "(single)";
		///End MAKE_A_GOOD_SIZE
		vector<string>  vstrTipsUpDown;
		vstrTipsUpDown.Add(_L("Show Selected Items"));
		vstrTipsUpDown.Add(_L("Hide Selected Items"));
		MultiPaneDlg::OnInitDialog(IDC_REPORT_TREE_LIST, IDC_SHOW_HIDE_BTN, IDC_SELECTED_LIST, vstrTipsUpDown, m_strDlgName, 0, NULL, 150);	///Jasmine 07/20/07 MAKE_A_GOOD_SIZE
		if(1 == m_nSelMode)//singe select
		{
			uint nButtonIDs[] = {IDC_SHOW_HIDE_BTN, IDC_REMOVE_BTN, IDC_ADD_BTN, IDC_SHOW_ONLY_TEXT, 0};
			for(int ii = 0; nButtonIDs[ii]; ii++)
				GetItem(nButtonIDs[ii]).Visible = false;
			ShowBottomPane(false);		
		}
		else
		{
			//GetItem(IDC_FILTER_COMBO).Visible = false;//temp, doing...
			InitSelList();
			GetItem(IDOK).Enable = GetItem(IDC_REMOVE_BTN).Enable = false;
			if(2 == m_nSelMode)
			{
				//Button chk = GetItem(IDC_CHECK_SHOW_ONLY);
				//chk.Check = true;
				//chk.Enable = false;
				GetItem(IDC_SHOW_ONLY_TEXT).Visible = true;//temp
				/// Hong 11/06/07 v8.0741 MORE_LOCALIZATION
				//GetItem(IDC_SHOW_ONLY_TEXT).Text = "Please select report trees with same equation or input data.";
				string strText;
				ocu_load_msg_str(REPORT_TREE_SEL_REPORT_TREE, &strText);
				GetItem(IDC_SHOW_ONLY_TEXT).Text = strText;
				/// end MORE_LOCALIZATION
			}
		}
		InitReportList();

		/// Kenny 10/19/2009 REPORT_TREE_BROWSER_SHOWS_UNWANTED_INSERT_MODE_COMBO
		GetItem(IDC_COMBO_INSERT_MODE).Visible	= FALSE;
		GetItem(IDC_STATIC_INSERT_MODE).Visible	= FALSE;
		/// End REPORT_TREE_BROWSER_SHOWS_UNWANTED_INSERT_MODE_COMBO
		return true;
	}
	BOOL OnDestroy()
	{
		return MultiPaneDlg::OnDestroy();
	}
	BOOL OnReady()
	{
		UpdateDlgSize();
		UpdateDlgShow();
		SetInitReady();
		return TRUE;
	}
	BOOL OnDlgResize(int nType, int cx, int cy)
	{	
		if(!IsInitReady())
			return TRUE;
		MoveControlsHelper	_temp(this);	///Jasmine 03/27/06 DLG_RESIZE_PAINT_MESS
		vector<uint> nButtonIDs = {IDCANCEL, IDOK};
		if(1 != m_nSelMode)
		{
			vector<uint> nIDs = {IDC_REMOVE_BTN, IDC_ADD_BTN};
			nButtonIDs.Append(nIDs);
		}
		nButtonIDs.Add(0);
		MultiPaneDlg::OnDlgResize(nButtonIDs, cx, cy, false);
		
		RECT rCheck, rOK;
		GetClientRect(GetItem(IDC_SHOW_ONLY_TEXT), rCheck);
		GetClientRect(GetItem(IDOK), rOK);
		int nH = RECT_HEIGHT(rCheck);
		rCheck.top = rOK.top;
		rCheck.bottom = rCheck.top + nH;
		MoveControl(GetItem(IDC_SHOW_ONLY_TEXT), rCheck); 
		return TRUE;
	}
	///Jasmine 07/20/07 MAKE_A_GOOD_SIZE
	BOOL OnInitSize()
	{
		return FALSE;
	}
	BOOL OnRestoreSize(DWORD dwSizeInfo)
	{
		void * p = (void*)dwSizeInfo;
		DLGSIZEINFO *pSz = (DLGSIZEINFO*)p;
		
		lstrcpyn(pSz->szDialogName, m_strDlgName, MAXLINE);
		
		SIZE sz;
		GetDlgOptimalSize(sz);
		pSz->top = -1;
		pSz->left = -1;
		pSz->width = 600;//sz.cx, hard code, temp
		pSz->height = 1 == m_nSelMode? 250 : 500;//sz.cy
		return TRUE;
	}
	///End MAKE_A_GOOD_SIZE
	BOOL OnClickOK(){return true;}
	BOOL OnClickCancel()
	{
		if(m_bCloseOnDBClick)		
			return true;
		if(m_nSelMode == 1)
			m_ReportList.ClearAll();	///Jasmine 01/22/07 REMOVE_SELECTION_IF_CANCEL
		else
			m_SelList.ClearAll();
		return true;
	}
	//BOOL OnShowBottomPane(Control cntrl)
	//{
		//MultiPaneDlg::OnShowBottomPane(cntrl);
		//return TRUE;
	//}
	BOOL OnAdd(Control cntrl)
	{
		vector<uint> vuSelRows;
		m_ReportList.GetSelRows(vuSelRows);	
		vector<string> vsUID;
		for(int nRow = m_SelList.GetRowOffset(); nRow < m_SelList.GetRows(); nRow++)
			vsUID.Add(m_SelList.GetCell(nRow, RLC_UID));
		for(int ii = 0; ii < vuSelRows.GetSize(); ii++)
		{
			vector<string> vsVals;
			m_ReportList.GetRowValues(vuSelRows[ii], vsVals);
			if(!vsUID.GetSize() || vsUID.Find(vsVals[RLC_UID]) < 0)
				m_SelList.SetRowValues(m_SelList.GetRows() - m_SelList.GetRowOffset(), vsVals, 0, true);
			if(m_nSelMode && m_SelList.GetRows() - m_SelList.GetRowOffset() >= m_nSelMode)//keep m_SelList's row number <= m_nSelMode if m_nSelMode > 0
			{
				GetItem(IDC_ADD_BTN).Enable = false;
				break;
			}
		}
		m_SelList.ResizeCols();	
		if(m_SelList.GetRows() - m_SelList.GetRowOffset())
		{
			GetItem(IDOK).Enable = GetItem(IDC_REMOVE_BTN).Enable = true;
			m_SelList.SelRow(m_SelList.GetRows() - m_SelList.GetRowOffset());
		}
		return TRUE;
	}
	BOOL OnRemove(Control cntrl)
	{
		vector<uint> vuSelRows;
		m_SelList.GetSelRows(vuSelRows);
		for(int ii = vuSelRows.GetSize() - 1; ii > -1; ii--)
			m_SelList.DeleteRow(vuSelRows[ii]);
		if(m_nSelMode && m_SelList.GetRows() - m_SelList.GetRowOffset() < m_nSelMode)//keep m_SelList's row number <= m_nSelMode if m_nSelMode > 0
			GetItem(IDC_ADD_BTN).Enable = true;
		if(m_SelList.GetRows() - m_SelList.GetRowOffset() < 1)
			GetItem(IDOK).Enable = GetItem(IDC_REMOVE_BTN).Enable = false;
		else
			m_SelList.SelRow(m_SelList.GetRows() - m_SelList.GetRowOffset());
		return TRUE;
	}
	bool OnDblClick(Control ctrl)
	{
		if(m_nSelMode != 1)
		{
			Control cntrl;
			return OnAdd(cntrl);
		}		
		m_bCloseOnDBClick = true;//select and close dlg
		PostMessage( WM_CLOSE );
		return true;
	}
public:
	void InitReportList()
	{
		m_ReportList.Init(IDC_REPORT_TREE_LIST, *this);
		m_ReportList.SetExplorerBar(flexExSortShow);
		m_ReportList.SetAllowSelection(m_nSelMode != 1);
		m_ReportList.SetSelection(flexSelectionListBox);
		//--- Iris 01/16/2007 YErr is same as ED
		//vector<string> vsColHeading = {"UID", "Worksheet", "Class", "Description", "Equation", "Input Data(X, Y, ED, YErr)", "Operation Time"};
		/// Hong 11/06/07 v8.0741 MORE_LOCALIZATION
		//vector<string> vsColHeading = {"UID", "Worksheet", "Class", "Description", "Equation", "Input Data(X, Y, YErr)", "Operation Time"};
		vector<string> vsColHeading;
		initColHeader(vsColHeading);
		/// end MORE_LOCALIZATION
		//---
		m_ReportList.SetupRowsCols(1, 0, -1, vsColHeading.GetSize());		
		for(int ii = 0; ii < vsColHeading.GetSize(); ii++)
			m_ReportList.SetColHeading(ii, vsColHeading[ii]);
		m_ReportList.HideCol(RLC_UID);
		UpdateReportList();
		m_ReportList.ResizeCols();//resize column to content
	}
	void InitSelList()
	{
		m_SelList.Init(IDC_SELECTED_LIST, *this);
		m_SelList.SetExplorerBar(flexExSort);
		m_SelList.SetAllowSelection(m_nSelMode != 1);
		m_SelList.SetSelection(flexSelectionListBox);
		/// Hong 11/06/07 v8.0741 MORE_LOCALIZATION
		//vector<string> vsColHeading = {"UID", "Worksheet", "Class", "Description", "Equation", "Input Data(X, Y, YErr)", "Operation Time"};
		vector<string> vsColHeading;
		initColHeader(vsColHeading);
		/// end MORE_LOCALIZATION
		m_SelList.SetupRowsCols(1, 0, -1, vsColHeading.GetSize());		
		for(int ii = 0; ii < vsColHeading.GetSize(); ii++)
			m_SelList.SetColHeading(ii, vsColHeading[ii]);
		m_SelList.HideCol(RLC_UID);	
	}
	void UpdateReportList()
	{
		//vector<uint>	vuIDs;
		vector<string> 	vsIDs, vsBookSheet, vsClass, vsDesc, vsEquation, vsInputData, vsTime;	
		vector<string> vsWeightInfo;
		///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
		//int nRow = getProjectReports(vsIDs, vsBookSheet, vsClass, vsDesc, vsEquation, vsInputData, vsTime);
		int nRow = getProjectReports(vsIDs, vsBookSheet, vsClass, vsDesc, vsEquation, vsInputData, vsWeightInfo, vsTime);
		///end TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
		///Jasmine 01/18/07 ADD_REPORT_TREE_FILTER_STRING
		int nFilter = atoi(m_strFilter.GetToken(1, ':'));
		if(FILTER_NONE != nFilter)//sort the row
		{
			vector<uint> vnIndeces;
			if(FILTER_SAME_EQUATION == nFilter || FILTER_ALL == nFilter)//sort by equation
			{
				vsEquation.Sort(SORT_ASCENDING, TRUE, vnIndeces);
				if(vnIndeces.GetSize())
					_reorder(vsInputData, vnIndeces);
			}
			else//sort by input data
			{
				vsInputData.Sort(SORT_ASCENDING, TRUE, vnIndeces);
				if(vnIndeces.GetSize())
					_reorder(vsEquation, vnIndeces);				
			}
			if(vnIndeces.GetSize())
			{
				_reorder(vsIDs, vnIndeces);
				_reorder(vsBookSheet, vnIndeces);
				_reorder(vsClass, vnIndeces);
				_reorder(vsDesc, vnIndeces);
				_reorder(vsWeightInfo, vnIndeces);///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
				_reorder(vsTime, vnIndeces);				
			}
			///Jasmine 03/30/07 REMOVE_ONLY_ONE_EQUATION_OR_DATASET
			string strWks = m_strFilter.GetToken(0, ':');
			Worksheet wks(strWks);
			if(!wks)
			{
				for(int ii = nRow - 1; ii >= 0; ii--)
				{	//remove the equation with only one dataset or the dataset with only one equation
					int nFind;
					string strFind;
					if(FILTER_SAME_EQUATION == nFilter)
						nFind = vsEquation.Find(vsEquation[ii]);
					else if(FILTER_SAME_INPUT_DATA == nFilter)
					///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
						//nFind = vsInputData.Find(vsInputData[ii])
					{
						nFind = vsInputData.Find(vsInputData[ii]);
						if( nFind != ii )
							nFind = vsWeightInfo.Find( vsWeightInfo[ii] );
					}
					///end TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
					if(nFind != ii)
					{	
						ii = nFind;//after sort, the same elements are put together, so can skip to the first found one
						continue;
					}
					vsIDs.RemoveAt(ii);
					vsBookSheet.RemoveAt(ii);
					vsClass.RemoveAt(ii);
					vsDesc.RemoveAt(ii);
					vsEquation.RemoveAt(ii);
					vsInputData.RemoveAt(ii);
					vsWeightInfo.RemoveAt(ii);///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
					vsTime.RemoveAt(ii);
				}
			}
			///End REMOVE_ONLY_ONE_EQUATION_OR_DATASET
		}
		///End ADD_REPORT_TREE_FILTER_STRING
		m_ReportList.SetColValues(RLC_UID, vsIDs, 0, true);
		m_ReportList.SetColValues(RLC_WKS, vsBookSheet, 0, true);
		m_ReportList.SetColValues(RLC_CLASS, vsClass, 0, true);
		m_ReportList.SetColValues(RLC_DESC, vsDesc, 0, true);
		m_ReportList.SetColValues(RLC_EQUATION, vsEquation, 0, true);
		m_ReportList.SetColValues(RLC_INPUT_DATA, vsInputData, 0, true);

		m_ReportList.SetColValues(RLC_INPUT_DATA_WEIGHT_INFO, vsWeightInfo, 0, true);	///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
		m_ReportList.SetColValues(RLC_TIME, vsTime, 0, true);
		if(vsIDs.GetSize())
		{
			m_ReportList.SelRow(m_ReportList.GetRowOffset());
			GetItem(IDOK).Enable = true;
		}
		///Jasmine 01/22/07 ERR_MSG_NO_REPORT_TREE
		else
		{
			/// Hong 11/06/07 v8.0741 MORE_LOCALIZATION
			//GetItem(IDC_SHOW_ONLY_TEXT).Text = "No report sheet, Fit tools must be run first. ";
			string strText;
			ocu_load_msg_str(REPORT_TREE_NO_REPORT_SHEET, &strText);
			GetItem(IDC_SHOW_ONLY_TEXT).Text = strText;
			/// end MORE_LOCALIZATION
			GetItem(IDC_SHOW_ONLY_TEXT).Visible = true;
		}
		///End ERR_MSG_NO_REPORT_TREE
	}
	int GetMinTopPaneHeight() {return 50;}
	int GetMinBottomPaneHeight() { return 50;}
	
private :
	/// Hong 11/06/07 v8.0741 MORE_LOCALIZATION
	void initColHeader(vector<string>& vsColHeading)
	{
		///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
		/*
		vsColHeading.SetSize(7);
		vsColHeading[0] = _L("UID");
		vsColHeading[1] = _L("Worksheet");
		vsColHeading[2] = _L("Class");
		vsColHeading[3] = _L("Description");
		vsColHeading[4] = _L("Equation");
		vsColHeading[5] = _L("Input Data(X, Y, YErr)");
		vsColHeading[6] = _L("Operation Time");
		*/
		vsColHeading.SetSize(8);
		vsColHeading[0] = _L("UID");
		vsColHeading[1] = _L("Worksheet");
		vsColHeading[2] = _L("Class");
		vsColHeading[3] = _L("Description");
		vsColHeading[4] = _L("Equation");
		vsColHeading[5] = _L("Input Data(X, Y, YErr)");
		vsColHeading[6] = _L("Weight Info(Method, Params)");
		vsColHeading[7] = _L("Operation Time");
		///end TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
	}	
	/// end MORE_LOCALIZATION
	string getInput(Worksheet& wks)
	{
		uint uid;
		Tree tr;
		///------ Folger 05/20/09 QA80-13638 FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT
		/// call GetReportTree directly to get GUI tree will fails to update input data node, which is done inside WksReportOperation::GetTree
		//if(!wks.GetReportTree(tr, &uid, 0, GRT_TYPE_GUI))
		if ( !_check_get_gui_node(tr, wks) )
		///------ End FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT
			return "";
		string strInput;
		TreeNode trInput = tree_get_node_by_tagname(tr, "InputData", true);
		if(!trInput.IsValid())
			return strInput;
		/// Iris 01/16/2007
		//vector<string> vs = {"X", "Y", "ED", "YErr"};
		vector<string> vs = {"X", "Y", "ED"};
		///Iris
		for(int ii = 0; ii < vs.GetSize(); ii++)
		{
			string strRange;
			TreeNode trRange = tree_get_node_by_tagname(trInput, vs[ii], true);
			if(trRange.IsValid())
				strRange = trRange.strVal;
			strRange.TrimLeft(); strRange.TrimRight(); 
			if(strRange.IsEmpty())
				strRange = "--";
			strInput += strRange + ",";
		}
		strInput.TrimRight(',');
		return strInput;		
	}
	
	///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
	string	getWeightInfo( Worksheet& wks )// current deal with input with only one range
	{
		uint	uid;
		Tree	trGUI;
		string	strWeightInfo = "";
		string	strClassName;
		string	strAttrib;
		/// Hong 02/24/09 FIX_RUNTIME_ERROR_BORWSER_NLFIT_REPORT_CRATED_BY_NLEND
		//int		nWeightMethod, nAttrib;
		int		nWeightMethod(0), nAttrib;
		/// end FIX_RUNTIME_ERROR_BORWSER_NLFIT_REPORT_CRATED_BY_NLEND
		string	strCombo;
		
		if(!wks.GetReportTree(trGUI, &uid, 0, GRT_TYPE_GUI))
			return "";
		
		
		TreeNode trInput = tree_get_node_by_tagname(trGUI, "InputData", true);
		if(!trInput.IsValid())
			return strWeightInfo;
		
		///Sophy 7/16/2008 FIX_FAIL_TO_GET_TREE_FROM_NLFIT
		//ASSERT( trGUI.GetAttribute( STR_CLASS_NAME, strClassName ) );
		bool	bRet = trGUI.GetAttribute( STR_CLASS_NAME, strClassName );
		///------ Folger 05/20/09 QA80-13638 FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT
		//ASSERT( bRet );
		if ( !bRet )
		{
			string		strClassOption;
			trGUI.GetAttribute( STR_CLASS_OPTION_NAME_ATTRIB, strClassOption );
			okutil_theme_separate_class_option(strClassOption, &strClassName);
			ASSERT(!strClassName.IsEmpty());
		}
		///------ End FIT_COMPARE_DIALOG_FAILS_TO_OPEN_TO_DISPLAY_CORRECT_RESULT
		///end FIX_FAIL_TO_GET_TREE_FROM_NLFIT
		
		if( 0 == strClassName.CompareNoCase( STR_FITTEROPERATION_CLASS_FITNL) || 0 == strClassName.CompareNoCase( "fitsigmoidal") || 0 == strClassName.CompareNoCase( "fitexp") )
		{
			ASSERT( trInput.Range1.W );
			/// Hong 02/24/09 FIX_RUNTIME_ERROR_BORWSER_NLFIT_REPORT_CRATED_BY_NLEND, clean need wait for #13154
			if ( trInput.Range1.W )
			/// end FIX_RUNTIME_ERROR_BORWSER_NLFIT_REPORT_CRATED_BY_NLEND
				trInput.Range1.W.GetAttribute( STR_FITTER_WEIGHT_METHOD_ATTRIB, nWeightMethod );

			strWeightInfo += nlsf_get_weight_method_name ( nWeightMethod );
			if( 0 == nWeightMethod ) //if No Weighting ,no need to get parameter information
				return strWeightInfo;
			if( 1 == nWeightMethod || 3 == nWeightMethod || 4 == nWeightMethod )//instrumental, arbitrary dataset, direct weighting have weight data on InputData.Range1.W
			{
				strWeightInfo += ", " + trInput.Range1.W.strVal;
				return strWeightInfo;
			}
			trInput.Range1.W.GetAttribute( STR_FITTER_WEIGHT_A_ATTRIB, nAttrib );
			strWeightInfo += ", " + nAttrib;
			trInput.Range1.W.GetAttribute( STR_FITTER_WEIGHT_B_ATTRIB, nAttrib );
			strWeightInfo += ", " + nAttrib;
			trInput.Range1.W.GetAttribute( STR_FITTER_WEIGHT_C_ATTRIB, nAttrib );
			strWeightInfo += ", " + nAttrib;
			strWeightInfo.TrimRight(", 0");//trim unuseful parameters
		}
		else if( 0 == strClassName.CompareNoCase(STR_FITTEROPERATION_CLASS_FITLINEAR) )//fit linear
		{
			TreeNode trFit = tree_get_node_by_tagname( trGUI, "Fit", true );
			ASSERT( trFit );
			/// YuI 09/24/08 QA70-12278 RUNTIME_OC_ERROR_IN_COMPARE_DATASETS
			if( trInput.Range1 && trInput.Range1.ED )
			/// end RUNTIME_OC_ERROR_IN_COMPARE_DATASETS
				strAttrib = trInput.Range1.ED.strVal;
				
			if( strAttrib.IsEmpty() )
			{
				strWeightInfo += "No Weighting";
				return strWeightInfo;
			}
			else
			{
				nWeightMethod = trFit.ErrBarWeight.nVal;
				trFit.ErrBarWeight.GetAttribute(STR_COMBO_ATTRIB, strCombo );
				strAttrib = strCombo.GetToken( nWeightMethod, '|' );
				strWeightInfo += strAttrib;
				strWeightInfo += ", " + trInput.Range1.ED.strVal;
			}
		}
		else//surfacefit matrixfit
		{
			strWeightInfo = "No Weighting";
		}
		return strWeightInfo;
	}
	///end TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
	
	///Jasmine 01/17/07 GET_POLYNOMIAL_ORDER	
	string getOrder(Worksheet& wks)
	{
		uint uid;
		Tree tr;
		if(!wks.GetReportTree(tr, &uid, 0, GRT_TYPE_GUI))
			return "";
		string strOrder;
		TreeNode trOrder = tree_get_node_by_tagname(tr, "Order", true);
		if(trOrder.IsValid())
			strOrder = "Order = " + trOrder.nVal;
		return strOrder;
	}
	///End GET_POLYNOMIAL_ORDER
	///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
	//int getProjectReports(vector<string>& vsIDs, vector<string>& vsBookSheet, vector<string>& vsClass, vector<string>& vsDesc, vector<string>& vsEquation, vector<string>& vsInputData, vector<string>& vsTime)
	int getProjectReports(vector<string>& vsIDs, vector<string>& vsBookSheet, vector<string>& vsClass, vector<string>& vsDesc, vector<string>& vsEquation, vector<string>& vsInputData, vector<string>& vsWeightInfo, vector<string>& vsTime)
	///end TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
	{
		///Jasmine 01/18/07 ADD_REPORT_TREE_FILTER_STRING
		string strWks, strE, strI;//equation and input data
		int nFilter;
		vector<string> vs;
		///------------Jasmine 02/16/07 add more classes
		//vector<string> vsClasses = {"FitNL", "FitPolynomial", "FitLinear"};///Jasmine 01/22/07 ONLY_ACCEPT_SPECIFIED_CLASSES
		vector<string> vsClasses = {STR_FITTEROPERATION_CLASS_FITNL, STR_FITTEROPERATION_CLASS_FITPOLYNOMIAL, STR_FITTEROPERATION_CLASS_FITLINEAR, "fitexp", "fitpeak", "fitsigmoidal", "fitsurface", "fitmatrix"};	///Sophy QA80-11724 ADD_COMPARE_DATASET_MODEL_FOR_MATRIX_FIT ,add "fitmatrix" to string array
		///------------end
		if(m_strFilter.GetTokens(vs, ':'))
		{
			strWks = vs[0];
			nFilter = atoi(vs[1]);
			uint uid;
			Tree tr;
			Worksheet wks(strWks);
			if(wks && wks.GetReportTree(tr, &uid))
			{
				if(FILTER_SAME_EQUATION == nFilter || FILTER_ALL == nFilter)
				{
					TreeNode trEquation = tree_get_node_by_tagname(tr, "Equation", true);
					if(trEquation.IsValid() )
						strE = trEquation.strVal;	
					strE.TrimLeft(); strE.TrimRight();
				}
				if(FILTER_SAME_INPUT_DATA == nFilter || FILTER_ALL == nFilter)
				{
					strI = getInput(wks);
					strI.TrimLeft(); strI.TrimRight();
				}
			}
		}
		foreach(WorksheetPage wp in Project.WorksheetPages)
		{
			foreach(Layer lay in wp.Layers)
			{
				string strRange;
				lay.GetRangeString(strRange);
				strRange.Delete(strRange.ReverseFind('!'));
				if(!strRange.CompareNoCase(strWks))
					continue;
				Worksheet wks(lay);
				if(!wks)
					continue;
				uint uid;
				Tree tr;
				if(wks.GetReportTree(tr, &uid, 0, GRT_TYPE_GUI) && wks.GetReportTree(tr, &uid))///Jasmine 02/16/07 only lists those fits which have operation 
				{					
					string strClass, strDesc, strEquation, strInputData, strTime;
					strInputData = getInput(wks);
					string strWeightInfo = getWeightInfo(wks);///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT

					if(!strI.IsEmpty() && strI.CompareNoCase(strInputData))
						continue;
					tr.GetAttribute(STR_ANALYSIS_ATTRIB, strClass);
					///Jasmine 01/22/07 ONLY_ACCEPT_SPECIFIED_CLASSES
					if(0 > vsClasses.Find(strClass))
						continue;
					///End ONLY_ACCEPT_SPECIFIED_CLASSES
					TreeNode trNotes = tr.Notes;
					if(trNotes.IsValid())
					{
						//--- Iris 01/16/2007 v8.0542 Description is unuseful here, should use Model to get function name
						//if(trNotes.Description)
						//	strDesc = trNotes.Description.strVal;
						if(trNotes.Model)
							strDesc = trNotes.Model.strVal;
						//---
						if(trNotes.Equation)
							strEquation = trNotes.Equation.strVal;
						if(!strE.IsEmpty() && strE.CompareNoCase(strEquation))
							continue;
		///End ADD_REPORT_TREE_FILTER_STRING
						if(trNotes.Time)
							strTime = trNotes.Time.strVal;
					}
					if(!strClass.CompareNoCase(STR_FITTEROPERATION_CLASS_FITPOLYNOMIAL))///Jasmine 01/17/07 GET_POLYNOMIAL_ORDER	
						strDesc = getOrder(wks);
					vsBookSheet.Add(wks_get_book_sheet_name(wks));			
					vsIDs.Add((string)uid);
					vsClass.Add(strClass);
					vsDesc.Add(strDesc);
					vsEquation.Add(strEquation);
					vsInputData.Add(strInputData);
					vsWeightInfo.Add(strWeightInfo);///Sophy 6/19/2008 QA80-10686 TREATE_DIFFERENT_WEIGHT_AS_DIFFERENT_INPUTDATA_ON_COMPARE_FIT_RESULT
					vsTime.Add(strTime);
				}
			}
		}
		return vsIDs.GetSize();
	}
private :
	int				m_nSelMode;
	GridListControl m_ReportList;
	GridListControl m_SelList;
	bool			m_bCloseOnDBClick;
///Jasmine 01/18/07 ADD_REPORT_TREE_FILTER_STRING
	string			m_strFilter;	
	string			m_strDlgName;
};

static void _reorder(vector<string>& vs, const vector<uint> vnIndeces)
{
	vector<string> vsTemp;
	int nCount = vnIndeces.GetSize();
	for(int ii = 0; ii < nCount; ii++)
		vsTemp.Add(vs[vnIndeces[ii]]);
	vs = vsTemp;
}

BOOL ReportTreeBrowser(string& strResults, vector<uint>& vuIDs, int nSelMode = 0, LPCSTR lpcszFilter = NULL, HWND hParent = NULL)
{
	ReportTrBrowser myDlg(nSelMode, lpcszFilter);
///End ADD_REPORT_TREE_FILTER_STRING
	Window winExDlg = myDlg.GetWindow();
	if(winExDlg)
	{
		out_str("Report Tree Browser already open");
		return false;
	}
	Window winNewDlg(hParent);
	HWND hWnd = GetWindow();
	if(winNewDlg)
		hWnd = hParent;
	if(hWnd)
	{
		int nRet = myDlg.DoModalEx(hWnd);
		return myDlg.GetSelection(strResults, vuIDs);
	}
	return false;
}

void test_RB()
{
	vector<uint> vuIDs;
	string strRet;
	out_str((string)ReportTreeBrowser(strRet, vuIDs, 1));
}
