/*------------------------------------------------------------------------------*
 * File Name:				 													*
 * Creation: 																	*
 * Purpose: OriginC Source C file												*
 * Copyright (c) ABCD Corp.	2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010		*
 * All Rights Reserved															*
 * 																				*
 * Modification Log:															*
 *	CPY 9/2/05	CHECK_EMPTY_HELP_NODES											*
 *  DG 9/5/05 ADD_NEW_XF_NODE													*
 *  DG 9/12/05 MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN								*
 *	CPY 9/20/05 XF_WORD_DOC_LOCATION_ADD_XF_CATEGORY							*
 *  DG 9/26/05 v8.0311 REMOVE_CHECKBOX_OPTIONLIST								*
 *  Iris 10/09/05 ADD_MODIFICATION_LOG											*
 *	DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT										*
 *  Iris 12/15/05 ADD_PROCESSBAR_FOR_ALL_XF										*
 *  Iris 5/10/06 ADD_TIP_FOR_AUTO_CREATED_USAGE									*
 *  Iris 06/06/06 MOVE_EXPORT_DESCRIPTION_OUTSIDE_XF_VAR_FUNC					*
 *  Iris 06/19/06 QA70-8767 MORE_CONDITION_TO_CHECK_OP_BASED					*
 *  Iris 06/26/06 QA70-8249-P10 MOVE_DISPLAY_NAME_COL_TO_LEFT_MOST				*
 *  Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW 			*
 *	AW 09/15/06 MAKE_HELP_ID_FOR_XF_CHM											*
 *  Joseph 09/21/06 DOCTOXF_VAR_LABEL_CORRENT									*
 *  Joseph 09/21/06 QA70-8349 	MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE			*
 *  Joseph 09/27/06  LABEL_CANNOT_CONTAIN_ENTER									*
 *  Joseph 09/28/06  FIND_FILE_IN_SUBFOLDER										*
 *  Joseph 10/09/06  ADD_MENU_INFO												*
 *	Joseph 10/13/06  NOT_SHOW_SLIDER_TABLE										*
 *	Joseph 11/06/06	 SUPPORT_FOLDER_AND_MATCH_ON_CREATE_DOC						*
 *  Joseph 11/14/06  NOT_OVERWRITHE_WHEN_NAME_IS_DIFFERENT						*
 *	Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE						*
 *	Justin 03/09/07 TO_SUPPORT_OTHER_LANGUIGES_FOR_COMMAND_LINE_USAGE			*
 *	justin 03/09/07 FIX_THE_BUG_THAT_DOES_NOT_GET_MENU_INFO_FROM_DOC			*
 *	justin 03/29/07 qa70-9548 v8.0592 XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC    *
 *	AW 04/03/07 QA80-9548 v8.0597 XF_LOCALIZATION								*
 *	Justin 2007-04-04 CORRECT_NODE_INDEX										*
 *	Justin 2007-04-10 v8.0597b qa-9585 SKIP_DOCUMENT_IF_NO_NEED					*
 *  Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE   *
 *  Justin 2007-04-18 DROP_COMMENT_FROM_COMMAND_LINE_USAGE						*
 *	Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE						*
 *	Joseph 06/06/07 MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE*
 *  Justin 2007-06-07 DISABLE_AUTO_MAKE_USAGE_AS_ECHO_REQUIRED					*
 *  Iris 07/24/2007 JUST_CHECK_LABTALK_IS_UNCHECED_FOR_OP_CLASS					*
 *	Hong 08/09/07 v8.0678 GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC					*
 *	Joseph 08/28/07 ADD_ORIGIN_PRO_INFO_IN_DOCUMENT								*
 *	Joseph 08/28/07 NOT_SHOW_SPECIFIED_OPTION_LIST								*
 *	Hong 08/29/07 b8.0691 XFDOC_NEED_NO_LT_SUPPORT_INDICATE						*
 *	Hong 08/29/07 QA80-0548 v8.0691 MORE_BETTER_STRING_FOR_REFER_MORE_DETAIL	*
 *	Hong 08/31/07 QA80-9548 v8.0693 XFDOC_TO_CHM_SUPPORT_ORIGINPRO_IN_TITLE		*
 *	Hong 09/03/07 QA80-9548 v8.0694 NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY*
 *	Hong 09/25/07 v8.0708 XFDOC_REDUCE_SIZE_BY_REMOVE_NONGUI_HELP_INFO			*
 *	Hong 10/09/07 v8.0720 FIX_REDUNDANT_XFHELPID								*
 *	CPY 11/20/07 FORCE_LOAD_XF_WIHTOUT_VALDATA_LOCALIZATION						*
 *	Hong 12/14/07 v8.0768 SIMPLE_FIX_RUNTIME_ERROR								*
 *	Hong 12/18/07 COMBOSTR_CHANGED_INTO_J_IN_XF_BUILDER_AND_LATER_SAVED_INTO_XF	*
 *	Hong 03/08/08 v8.0820 FIX_XF2DOC_LOST_COMBO_DESCRIPTION						*
 *	Hong 20/05/08 v8.0867 IMPROVE_CODE											*
 *	Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS			*
 *	Fisher 12/04/08 QA-10236 KEEP_MENU_INFORMATION_AND_BRIEF_INFORMATION_IN_DOC2XF 
 *	Folger 08/12/09 QA80-14112 NEED_OPTION_STRING_TO_HIDE_XF_VARIABLE_FROM_LT	*
 *------------------------------------------------------------------------------*/
 
////////////////////////////////////////////////////////////////////////////////////
// Including the system header file Origin.h should be sufficient for most Origin
// applications and is recommended. Origin.h includes many of the most common system
// header files and is automatically pre-compiled when Origin runs the first time.
// Programs including Origin.h subsequently compile much more quickly as long as
// the size and number of other included header files is minimized. All NAG header
// files are now included in Origin.h and no longer need be separately included.
//
// Right-click on the line below and select 'Open "Origin.h"' to open the Origin.h
// system header file.
#include <Origin.h>
////////////////////////////////////////////////////////////////////////////////////
#include <..\originlab\xfunctionEx.h>
#include "XFDocument.h"
/// AW 09/15/06 MAKE_HELP_ID_FOR_XF_CHM
#include <..\originlab\OCHelpID.h>   
#include <..\originlab\HelpID.h>
/// END MAKE_HELP_ID_FOR_XF_CHM
#include <tree_utils.h>	///Joseph 03/28/07 ADD_COMBO_NAMES_LIST_FOR_TREE_NODE fix bug about type dis match
//#define _XFTX_DISPLAY_H

#ifdef	_XFTX_DISPLAY_H	///DG 9/14/05 only for compiling
//#include "XFTXDisplay.h"
#endif //_XFTX_DISPLAY_H
#define STR_DOC_LANGUAGE_SECTION			"Language:\t"

///Joseph 06/06/07 MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE
/*
#define STR_LANGUAGE_ENGLISH				"English"
#define STR_LANGUAGE_JAPANESE				"Japanese"
#define STR_LANGUAGE_GERMAN					"German"
#define STR_LANGUAGE_CHINESE				"Chinese"
*/
///End MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE

#define STR_DOC_DEFAULT_SAVE_PATH			okutil_get_origin_path(ORIGIN_PATH_USER, "XFDocument")

#define STR_SLIDER	"Slider"			///Joseph 10/13/06  NOT_SHOW_SLIDER_TABLE

/// AW 04/03/07 QA80-9548 v8.0597 XF_LOCALIZATION 
#define TREE_ATTR_NAME_SPECAL_DATATYPE "dt:dt"  
#define TREE_ATTR_DATATYPE_BIN_64 		"bin.base64"
/// END XF_LOCALIZATION

///Joseph 08/28/07 ADD_ORIGIN_PRO_INFO_IN_DOCUMENT
#define STR_PRO_INFO "Pro"
//#define STR_PRO_VERSION_ONLY " (OriginPro Only)"
/// Hong 09/03/07 QA80-9548 v8.0694 NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY 
//#define STR_PRO_VERSION_ONLY "(OriginPro)" /// Hong 08/31/07 QA80-9548 v8.0693 XFDOC_TO_CHM_SUPPORT_ORIGINPRO_IN_TITLE
/// end NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY
///End ADD_ORIGIN_PRO_INFO_IN_DOCUMENT

///Joseph 08/28/07 NOT_SHOW_SPECIFIED_OPTION_LIST
static bool _show_combo_optionlist(const TreeNode& trV, string& str)
{
	if( !trV )
		return false;
	
	bool bCheckBox = false, bShowOptionList = true;
	

	str = get_var_combolist(trV, bCheckBox);
	
	if(0 == trV.type.strVal.Compare("int") && 0 == trV.name.strVal.Compare("sysparam") && trV.io.nVal == 0)
		bShowOptionList = false;
	
	if(!bCheckBox && !str.IsEmpty() && bShowOptionList)
		return true;
}
///End NOT_SHOW_SPECIFIED_OPTION_LIST


#define MaxSubFolderLevel 6         ///Joseph 09/28/06  FIND_FILE_IN_SUBFOLDER
///Joseph 06/06/07 MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE
/*
enum 
{
	LANG_ALL = 0,
	LANG_ENGLISH,
	LANG_JAPANESE,
	LANG_GERMAN,
	LANG_CHINESE
};
*/
///End MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE

///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT added IDV_HELP_PARAMETERS, STR_XF_BOOKMARK_PARAMETERS below
//summary, example, reference and algorithm and parameters
/// Hong 20/05/08 v8.0867 IMPROVE_CODE
//static vector<int> vnHelpIDs={IDV_HELP_SUMMARY, IDV_HELP_EXAMPLE, IDV_HELP_REF, IDV_HELP_ALGORITHM, IDV_HELP_PARAMETERS};
//static vector<string> vsHelpBookMarks={STR_XF_BOOKMARK_SUMMARY, STR_XF_BOOKMARK_EXAMPLE, STR_XF_BOOKMARK_REF, STR_XF_BOOKMARK_ALGORITHM, STR_XF_BOOKMARK_PARAMETERS};
static vector<int>		s_vnHelpIDs = {IDV_HELP_SUMMARY, IDV_HELP_EXAMPLE, IDV_HELP_REF, IDV_HELP_ALGORITHM, IDV_HELP_PARAMETERS};
static vector<string>	s_vsHelpBookMarks = {STR_XF_BOOKMARK_SUMMARY, STR_XF_BOOKMARK_EXAMPLE, STR_XF_BOOKMARK_REF, STR_XF_BOOKMARK_ALGORITHM, STR_XF_BOOKMARK_PARAMETERS};
/// end IMPROVE_CODE
///end ADD_PARAMETERS_NODE_TO_XFT
///DG MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN
static bool _is_file_read_only(const string& strFile)
{
	WIN32_FILE_ATTRIBUTE_DATA	fileInfo;
	
	if(!GetFileAttributesEx(strFile, 0, &fileInfo))
		return false;
	
	return FILE_ATTRIBUTE_READONLY & fileInfo.dwFileAttributes ? true : false;
}
static bool _check_xfdoc_checked_out(const string& strXFName, const string& strFolder, const string& strLanguage)
{
	string strDocFile(get_xf_doc_filename(strFolder, strXFName, strLanguage));
	if(_is_file_read_only(strDocFile))
	{
		printf("\*\nThis file fail to execute\n");
		printf("Please check out it before using: %s\n", strDocFile);
		printf("*\\\n");
		return false;
	}
	return true;
}
///end MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN

//---- CPY 9/2/05	CHECK_EMPTY_HELP_NODES
/*
try
{
	vcRemarkVals=trVhelp.remark.bVals;			//remark, run time error in old xf
}
catch(int nError)
{
	printf("%s:Can not get variable %s help info for %s\n", strXFname, vsLang[jj], trV.name.strVal);
}
*/
///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
CODE_PAGE_TYPE _get_code_page(int nLang)
{
	CODE_PAGE_TYPE nCP;
	switch(nLang)
	{
	case IDRS_HELP_J:
		nCP = CP_Japanese;
		break; 
	case IDRS_HELP_C:
		nCP = CP_Simplified_Chinese; 
		break;
	default:
		nCP = CP_US_ANSI;		
	}
	return nCP;
}
///End COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE

///justin 03/29/07 qa70-9548 v8.0592 XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
//static bool _is_consistent_combstr(const string& strComb1, const string& strComb2, bool bJapanese)
static bool _is_consistent_combstr(const string& strComb1, const string& strComb2, int nLang)
///End COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
{
//	if(!strComb1 || strComb1.IsEmpty() || !strComb2 || strComb2.IsEmpty() )
//		return false;


	///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE
	//should care more for multi languages.
	//int nCurrentCP = set_code_page_for_string_process( _get_code_page(nLang) ); ///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
	//int nSize1 = strComb1.GetNumTokens('|');
	//int nSize2 = strComb2.GetNumTokens('|');

	vector<string> vsCombo1, vsCombo2;
	int nCurrentCP = set_code_page_for_string_process( CP_US_ANSI ); ///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
	int nSize1 = strComb1.GetTokens(vsCombo1, '|');
	set_code_page_for_string_process( _get_code_page(nLang) ); ///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
	int nSize2 = strComb2.GetTokens(vsCombo2, '|');
	set_code_page_for_string_process(nCurrentCP);  ///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
	///End SHOULD_SUPPORT_MULTI_LANGUAGE
	
	if(nSize1 != nSize2) 
		return false;
	
	///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE
	//should match prefix
	int nn = 0;
	for(; nn < nSize1; nn++)
	{
		int nIndex1 = vsCombo1[nn].Find(':');
		int nIndex2 = vsCombo2[nn].Find(':');
		string strPre1, strPre2;
		strPre1 = vsCombo1[nn].Left(nIndex1);
		strPre2 = vsCombo2[nn].Left(nIndex2);
		if(0 != strPre1.Compare(strPre2))
			break;
	}
	
	if(nn != nSize1)
		return false;
	///End SHOULD_SUPPORT_MULTI_LANGUAGE
	return true;	
}

static string _create_new_compbstr(const string& strTemplate, const vector<string>& vsList, int nLang)
{
	vector<string> vsTemplate;
	string strCombStr; 
	int nCurrentCP = set_code_page_for_string_process( CP_US_ANSI );	///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE
	int nSize = strTemplate.GetTokens(vsTemplate, '|');
	if(nSize == vsList.GetSize())
	{
		set_code_page_for_string_process( _get_code_page(nLang) );	///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE

		for(int ii = 0; ii< nSize; ii++)
		{
			string strTmp = vsList[ii].Right( vsList[ii].GetLength() - (vsList[ii].Find(':')+1));
			if(! strTmp.IsEmpty())
			{
				vsTemplate[ii] = vsTemplate[ii].Left( vsTemplate[ii].Find(':') + 1 ) + strTmp;
			}
		}
		strCombStr.SetTokens(vsTemplate, '|');
	}
	else
	{
		strCombStr = strTemplate;
	}
	
	set_code_page_for_string_process( nCurrentCP );	///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE
	
	return strCombStr;	
}
///end XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
static bool _get_help_text(vector<char>& vc, const TreeNode& tr, string& str)
{
	vc.SetSize(0);
	if(!tr || tr.IsEmpty())
		return false;
	if(tr.TypeID != TNVAL_TYPE_CHAR_VECTOR)
	{
		str = tr.strVal;
		if(str.GetLength() < 10000)// it seems that Word doc has a min size of about 20k, and typical text is very small
		{
			printf("failed to get vector<char> from %s node(typeid = %d), using string instead\n", tr.tagName, tr.TypeID);
			return false;
		}
	}
	try {
		vc = tr.bVals;	
	}
	catch(int nErr)
	{
		out_int("_get_help_text err = ", nErr);
		return false;
	}
	return true;	
}

static bool _set_help_text(TreeNode& tr, const vector<char>& vc)
{
	/// Hong 20/05/08 v8.0867 IMPROVE_CODE
	if ( !tr )
		return false;
	/// end IMPROVE_CODE
	//printf("before set help text, %s typeID = %d\n", tr.tagName, tr.TypeID);
	tr.Reset(true);
	try {
		tr.bVals = vc;
	}
	catch(int nErr)
	{
		out_int("_set_help_text err = ", nErr);
		return false;
	}
	if(TNVAL_TYPE_CHAR_VECTOR != tr.TypeID)
		printf("after set help text, %s typeID = %d\n", tr.tagName, tr.TypeID);
	return true;
}
//-----

bool _get_combolist_text(vector<string>& vs, const TreeNode& tr)
{
	vs.SetSize(0);
	if(!tr || tr.IsEmpty())
		return false;
	if(tr.TypeID != TNVAL_TYPE_CSTRING_VECTOR)
		out_str("Err combolist node");
	
	try
	{
		vs=tr.strVals;
	}
	catch(int nError)
	{
		//out_int("_get_combolist_text err = ", nError);
		return false;
	}
	return true;
}

static string get_xf_doc_filename(const string& strPath, const string& strFileName, const string& strLanguage)
{
	string str;
	str = strPath+strFileName+"_"+strLanguage+".doc";
	return str;	
}
//get xf file name by doc file name, get language id by doc file name if pnLanguage is specified
static string get_xf_name(const string& strDocFileName, int* pnLangID=NULL)
{
	string strFileName, strXFName;
	strFileName=GetFileName(strDocFileName, true);
	int nn=strFileName.ReverseFind('_');
	if(0>nn)
		return strFileName;
	
	strXFName = strFileName.Left(nn);
	if(NULL != pnLangID)
	{
		string strLangName;
		//----CPY 9/2/05 SINGLE_LANGUAGE_FOR_EASIER_TESTING
		//strLangName=strFileName.Right(nn-2);
		strLangName=strFileName.Mid(nn+1);
		//----
		
		vector<int> vnLangIDs;
		vector<string> vsLangNames;
		get_xf_language_info(vnLangIDs, vsLangNames);
		
		nn = vsLangNames.Find(strLangName);
		//----CPY 9/2/05 SINGLE_LANGUAGE_FOR_EASIER_TESTING
		if(nn < 0)
		{
			*pnLangID = LANG_ENGLISH;
			printf("Word doc filename err:%s\n", strDocFileName);
		}
		else
		{
			*pnLangID = nn + LANG_ENGLISH;
		}
		//----
	}
	return strXFName;
}
static int get_xf_language_info(vector<int>& vnLangIDs, vector<string>& vsLangNames, int nSpecifyLangIndex = LANG_ALL)
{
	vector<int> vnLang = {IDRS_HELP_E, IDRS_HELP_J, IDRS_HELP_G, IDRS_HELP_C};
	vector<string> vsLang = {STR_LANGUAGE_ENGLISH, STR_LANGUAGE_JAPANESE, STR_LANGUAGE_GERMAN, STR_LANGUAGE_CHINESE};
	
	vnLangIDs.SetSize(0);
	vsLangNames.SetSize(0);
	if( nSpecifyLangIndex != LANG_ALL)
	{
		int nIndex = nSpecifyLangIndex - LANG_ENGLISH;
		if(vnLang.GetSize()>nIndex)
		{
			vnLangIDs.Add(vnLang[nIndex]);
			vsLangNames.Add(vsLang[nIndex]);
		}
		else
			out_int("error with langauge id = ", nSpecifyLangIndex);
	}
	else	//get all
	{
		vnLangIDs=vnLang;
		vsLangNames=vsLang;
	}
	return vnLangIDs.GetSize();
}
///Joseph 06/06/07 MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE
//move this function to xfunction.c
/*
static string _get_language_string(int nIDLang)
{
	switch(nIDLang)
	{
	case IDRS_HELP_E:
		return STR_LANGUAGE_ENGLISH;
	case IDRS_HELP_J:
		return STR_LANGUAGE_JAPANESE;
	case IDRS_HELP_G:
		return STR_LANGUAGE_GERMAN;
	case IDRS_HELP_C:
		return STR_LANGUAGE_CHINESE;
	default:
		return "";
	}
	return "";
}
*/
///End MOVE_SOME_FUNCTIONS_AND_DEFINITIONS_TO_XFUNCTION_HEADER_FILE

static string get_var_combolist(TreeNode& trV, bool& bIsCheckBox)
{
	bIsCheckBox=false;
	
	string str;
	str=trV.comboString.strVal;
	vector<string> vs;
	str.GetTokens(vs, '|');	//no editable empty item
	///Joseph 10/13/06  NOT_SHOW_SLIDER_TABLE
	//if("int"==trV.type.strVal && 1<vs.GetSize() && -1==vs.Find("")) //combolist is not editable
	if("int"==trV.type.strVal && 1<vs.GetSize() && -1==vs.Find("") && vs[0].Find( STR_SLIDER ) < 0) //combolist is not editable
	///End NOT_SHOW_SLIDER_TABLE
	{
		if("0|1"==str || "1|0"==str)	//checkbox is "0|1" or "1|0", 
		{
			bIsCheckBox=true;
			return str;
		}
		else
		{
			for(int ii=0; ii<vs.GetSize(); ii++)	//skip all list is number
			{
				if(!is_numeric(vs[ii]))
				{
					return str;
				}
			}
		}
	}
	return "";
}

static bool _create_help_text(BaseDocument& oDoc, TreeNode& trInfo, LPCSTR lpcszLabel, LPCSTR lpcszBookMark, bool bClearEmpty=false)
{
	//---------CPY 9/2/05	CHECK_EMPTY_HELP_NODES
	string strValOnErr;
	vector<char> vcVals;
	if(_get_help_text(vcVals, trInfo, strValOnErr))
	{
		if(bClearEmpty && 0 == vcVals.GetSize())
			oDoc.DeleteSection(lpcszBookMark);
		else
			oDoc.AddRichText(vcVals, lpcszLabel, lpcszBookMark);
	}
	else
	{
		if(bClearEmpty && strValOnErr.IsEmpty())
			oDoc.DeleteSection(lpcszBookMark);
		else
			oDoc.AddString(strValOnErr, lpcszLabel, lpcszBookMark);
	}
	//----------
	return true;
}

///Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
static bool _add_richedit_to_cell(BaseDocument& oDoc, TreeNode& trNode, LPCSTR lpcszBookMark)
{
	vector<char> vcVals;
	string strValOnErr;
	if(_get_help_text(vcVals, trNode, strValOnErr))
	{
		if(0 < vcVals.GetSize())
		{
			///---
			vcVals[0] = 'H';
			///---
			return	true;//oDoc.AddRichText(vcVals, "", lpcszBookMark, NULL, false);
		}
	}
}	
///End 	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
/// ----AW 11/03/05 ADD_HELP_SCREEN_SHOT
static bool _create_help_image(BaseDocument& oDoc, TreeNode& trInfo, LPCSTR lpcszLabel, LPCSTR lpcszBookMark)
{
	string strValOnErr;
	vector<char> vcVals;
	if(_get_help_text(vcVals, trInfo, strValOnErr))
	{
		if(0 < vcVals.GetSize())
			return oDoc.AddImage(vcVals, lpcszLabel, lpcszBookMark);
	}
	return true;
}
/// END ADD_HELP_SCREEN_SHOT


static void _add_more_expression_case(vector<string>& vsList, string strVarName)
{
	int nSize = vsList.GetSize();
	if(0 < nSize)
	{
		vsList.Add(strVarName+"="+vsList[0]);
		if(1 < nSize)
			vsList.Add(strVarName+":="+vsList[1]);
	}
}

/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
//	static bool _auto_make_syntax(XFunction& xf, TreeNode& trXF, string& strSyntax)
static bool _auto_make_syntax(TreeNode& trXF, string& strSyntax, BOOL bInternal)
/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
{
	/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	//	string strXFName(xf.GetFunctionName(false));
	string strXFName = okutil_xft_get_function_name(&trXF, false, bInternal);
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	vector<string> vsSyntaxs, vsVarVals;
	
	TreeNode trVars, trVar;
	trVars = trXF.vars;
	string str;
	bool bCheckBox;
	
	vector<string> vsNames, vsValData, vsValTypes;
	bool bVarTypesAddRef = false;
	vector<int> vnIO;
	
	/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	//xf.GetVariables(vsNames, vsValData, vsValTypes, bVarTypesAddRef, vnIO);
	xf_get_variables(trXF, vsNames, vsValData, vsValTypes, bVarTypesAddRef, vnIO, bInternal);
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	vsSyntaxs.SetSize(vsValTypes.GetSize()+2);	//two more, one for all default value, one for fully specify variables
	
	int ii, jj;
	for(ii=0; ii<vsSyntaxs.GetSize(); ii++)
	{
		vsSyntaxs[ii]=(string)(ii+1)+". "+strXFName+" ";
	}
	
	for(ii=0, jj=0; ii<vsValTypes.GetSize(); ii++)
	{
		if(IO_OUTPUT == vnIO[ii])
			continue;
		vsVarVals.SetSize(0);
		int nType = get_xvar_type_from_type_name(vsValTypes[ii]);
		switch( nType )
		{
		case XVT_DOUBLE:
			vector<string> vs={"1.0", "2.0", "0.1"};
			vsVarVals=vs;
			break;
		case XVT_STRING:
			vector<string> vs={"\"String As Input\""};
			vsVarVals=vs;
			break;
		case XVT_INT:
			str.Empty();
			//trVar = trVars.GetNode("v"+(string)(ii+1));
			/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			//	trVar = xf.GetVariableTreeNode(vsNames[ii]);
			trVar = xf_get_variable_tree_node(trXF, vsNames[ii]);
			/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			if(!trVar)
				break;
			
			str=get_var_combolist(trVar, bCheckBox);
			if(!bCheckBox && str.IsEmpty())
				break;
			
			if(bCheckBox)
			{
				vector<string> vs={"1", "true", "0", "false"};
				vsVarVals=vs;
			}
			else	//combolist
			{
				int nn=str.GetNumTokens('|');
				vsVarVals.SetSize(nn);
				for(int kk=0; kk<nn; kk++)
					vsVarVals[kk]=kk;
			}
			break;
		case XVT_DATARANGE:
		case XVT_VECTOR:
		case XVT_XYDATARANGE:
		case XVT_XYZDATARANGE:
			vector<string> vs={"1", "Col(1)", "Col(A)"};
			vsVarVals=vs;
			break;
		case XVT_MATRIX:
			break;
		case XVT_BUTTONINFO:
			break;
		case XVT_LINEINFO:
			break;
		case XVT_TEXTINFO:
			break;
		case XVT_EVENTINFO:
			break;
		case XVT_MARKERINFO:
			break;
		case XVT_ORIGINOBJECT:
			break;
		case XVT_COLUMN:
			break;
		case XVT_WORKSHEET:
			break;
		case XVT_MATRIXOBJECT:
			break;
		case XVT_DATAPLOT:
			break;
		case XVT_TREE:
			break;
		case XVT_FILELINK:
			break;
		default:
			break;
		}
		if(0 == vsVarVals.GetSize())
			continue;
		_add_more_expression_case(vsVarVals, vsNames[ii]);
		for(jj=ii+1;jj<vsSyntaxs.GetSize()-1;jj++)
		{
			vsSyntaxs[jj]+=vsVarVals[mod(jj-1, vsVarVals.GetSize())]+" ";
		}
	}
	//additional full variable case
	str.SetTokens(vsNames, ' ');
	vsSyntaxs[ii+1]+=str+" //specify all variables";
	
	vsSyntaxs.InsertAt(0, "(Following usage are auto-created, please update it as your needs)"); /// Iris 5/10/06 ADD_TIP_FOR_AUTO_CREATED_USAGE
	
	strSyntax.SetTokens(vsSyntaxs, '\n');
	return true;
}

//---CPY 10/25/05 ADD_RELATED_XF_NODE_FOR_XF_DOC
static void _add_node_to_doc(BaseDocument&oDoc, const TreeNode& trInfo, LPCSTR lpcszBookMark, bool bClearEmpty)
{
	if( trInfo )
	{
		string str = trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
			oDoc.DeleteSection(lpcszBookMark);
		else
			oDoc.AddString(str, "", lpcszBookMark);		
	}
	else
		printf("Fail to find node in x-function for adding to bookmark %s\n", lpcszBookMark);
}
//---	

///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT

/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
//	static bool create_xf_document_variables(BaseDocument& oDoc, XFunction& xf, TreeNode& trXF, int nLang, bool bEditableDoc, bool bClearEmpty)
static bool create_xf_document_variables(BaseDocument& oDoc, TreeNode& trXF, int nLang, bool bEditableDoc, bool bClearEmpty, BOOL bInternal)
/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
{
	string str;
	int ii=0;
	TreeNode trInfo;
	
	//variables
	vector<string> vsVals, vsComboLists;
	vector<int> vnComboListVar;
	//vector<bool> vbCheckBox;
	string strVarName;
	int nVar=1;
	///Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
	vector<char> vcVals;
	vector<int> vnTreeNode;
	///End SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
	
	/// Hong 08/09/07 v8.0678 GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC
	string strXFName = okutil_xft_get_function_name(&trXF, false, bInternal);
	XFBase xf(strXFName);
	/// end GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC
	foreach(TreeNode trV in trXF.vars.Children)
	{
		///------ Folger 08/12/09 QA80-14112 NEED_OPTION_STRING_TO_HIDE_XF_VARIABLE_FROM_LT
		XFVariable	var(trV);
		if ( !var.IsAccessibleFromLT() )
			continue;
		///------ End NEED_OPTION_STRING_TO_HIDE_XF_VARIABLE_FROM_LT

		TreeNode trVhelp;
		if(octree_find_node(&trV, &trVhelp, STR_DATAID_ATTRIB, IDV_VAR_LOCAL_HELP_BRANCH, false, 0, nLang))
		{
			strVarName = trV.name.strVal;
			/// Iris 06/26/06 QA70-8249-P10 MOVE_DISPLAY_NAME_COL_TO_LEFT_MOST
			//display name(tree description)
			/// Hong 08/09/07 v8.0678 GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC
			//str = trVhelp.description.strVal;	//description
			xf.GetVarLabel(strVarName, str, nLang);
			/// end GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC
			vsVals.Add(str);
			///End MOVE_DISPLAY_NAME_COL_TO_LEFT_MOST
			
			TreeNode trIO=trV.io;
			TreeNode trType = trV.type;			
			
			//vsVals.Add(strVarName);				//name
			trIO.GetAttribute(STR_COMBO_ATTRIB, str);
			//vsVals.Add(str.GetToken(trIO.nVal, '|') + "\n" + trType.strVal);	//io + data type
			str = str.GetToken(trIO.nVal, '|') + "\n" + trType.strVal;
			//DG 9/14/05 : Difference between normal doc and CHM doc, editable one combine name, io and type
			if(bEditableDoc)
				vsVals.Add(strVarName+"\n"+str);
			else
			{
				vsVals.Add(strVarName);
				vsVals.Add(str);
			}
			///Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
			if(trType.strVal == STR_TREENODE)
			{				
				vnTreeNode.Add(nVar);
			}
			///End 	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
			/// Iris 06/26/06 QA70-8249-P10 MOVE_DISPLAY_NAME_COL_TO_LEFT_MOST
			////display name(tree description)
			//str = trVhelp.description.strVal;	//description
			//vsVals.Add(str);
			///End MOVE_DISPLAY_NAME_COL_TO_LEFT_MOST
			
			if(bEditableDoc)
			{
				///DG 9/14/05 New brief description section
				str = trVhelp.hint.strVal;
				vsVals.Add(str);
				///end
			}
			
			//description(tree remarks)
			str = trVhelp.remark.strVal;
			vsVals.Add(str);
			
			/// Hong 03/08/08 v8.0820 FIX_XF2DOC_LOST_COMBO_DESCRIPTION
			// modify below should only remove code of comEx as CP only remove this node in VC
			/// Hong 12/18/07 COMBOSTR_CHANGED_INTO_J_IN_XF_BUILDER_AND_LATER_SAVED_INTO_XF
			/* we should not do anything to IDV_VAR_HELP_COMBOSTR as it is no longer used -- refer to oUtils.cpp of CP's change
			*/
			///Joseph 08/28/07 NOT_SHOW_SPECIFIED_OPTION_LIST
			//bool bCheckBox = false;
			//str = get_var_combolist(trV, bCheckBox);
			////if(!str.IsEmpty())	///DG REMOVE_CHECKBOX_OPTIONLIST
			//if(!bCheckBox && !str.IsEmpty())
			if(_show_combo_optionlist(trV, str))
			///End NOT_SHOW_SPECIFIED_OPTION_LIST
			{
				///justin 03/29/07 qa70-9548 v8.0592 XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
				string strLocalComb;
				//// ------------AW 04/03/07 QA80-9548 v8.0597 XF_LOCALIZATION
			/**/	/*
				vector<byte> vbTmp; 
				vbTmp = trVhelp.comboEx.bVals;
				strLocalComb.SetBytes(vbTmp);  
				*/
			/*	TreeNode trcomboEx;
				trcomboEx = trVhelp.comboEx;
				string strDataType;
				BOOL bOldway = trcomboEx.GetAttribute(TREE_ATTR_NAME_SPECAL_DATATYPE, strDataType);
				if ( bOldway && strDataType.CompareNoCase(TREE_ATTR_DATATYPE_BIN_64) == 0 )  
				{   // this is for old existing XF which already have been localizated
					vector<byte> vbTmp; 
					vbTmp = trVhelp.comboEx.bVals;
					strLocalComb.SetBytes(vbTmp);  
				}
				else
					strLocalComb = trVhelp.comboEx.strVal;
				//// ------------END XF_LOCALIZATION
			*/	
				///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE
				//if(_is_consistent_combstr(str, strLocalComb, nLang))
				if(_is_consistent_combstr(str, strLocalComb, nLang) && nLang != IDRS_HELP_E) ///Justin 2007-04-18 qa70-9548 v8.0603 COMPARE_COMBOSTRING_FOR_DIFF_LANGUAGE
				///End SHOULD_SUPPORT_MULTI_LANGUAGE
					str = strLocalComb;
				///End XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC

				vnComboListVar.Add(nVar);	
				vsComboLists.Add(str);
				//vbCheckBox.Add(bCheckBox);
				
				vector<string> vsTemp;
				_get_combolist_text(vsTemp, trVhelp.comboDescription);	///Joseph 03/28/07 ADD_COMBO_NAMES_LIST_FOR_TREE_NODE fix bug about type dis match
				///DG REMOVE_CHECKBOX_OPTIONLIST
			/**/	/*
				if(bCheckBox)
					vsTemp.SetSize(1);
				else
				*/
			/**/	///end REMOVE_CHECKBOX_OPTIONLIST
					vsTemp.SetSize(str.GetNumTokens('|'));
						
				vsComboLists.Append(vsTemp);	//Storage reuse, no idea on how to store it
			}
			/**/
			/// end COMBOSTR_CHANGED_INTO_J_IN_XF_BUILDER_AND_LATER_SAVED_INTO_XF
			/// end FIX_XF2DOC_LOST_COMBO_DESCRIPTION
		}
		else
			printf("####%s: invalid tree structure.\n", trV.tagName);
		
		nVar++;
	}
	//oDoc.AddTables(vsVals, NUM_VARS_COLS, NULL, STR_XF_BOOKMARK_VARIABLES, STR_XFV_BOOKMARK_TABLE_CELL, 1);	//variables tables, first row is title
	int nTableIndex;
	oDoc.FillTable(vsVals, NUM_VARS_COLS, nTableIndex, STR_XF_BOOKMARK_VARIABLES, 1, STR_XFV_BOOKMARK_TABLE_CELL);

	
	//add combolist table in description cell
	int nDescripCellIndex, nListPosition=0;
	///Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
	int nTreeNodeSize = vnTreeNode.GetSize(); 
	for(ii = 0 ; ii < nTreeNodeSize; ii++)
	{
		///Justin 2007-04-04 CORRECT_NODE_INDEX
		//TreeNode trV = trXF.vars.Children.Item(vnTreeNode[ii]);///Joseph 03/28/07 ADD_COMBO_NAMES_LIST_FOR_TREE_NODE fix bug about type dis match  
		TreeNode trV = trXF.vars.Children.Item(vnTreeNode[ii]-1);
		///End CORRECT_NODE_INDEX
		nDescripCellIndex = vnTreeNode[ii]*NUM_VARS_COLS;
		string str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nDescripCellIndex;		
		//oDoc.SplitCellTwoRows(str, STR_VARIABLES);
		oDoc.SplitCellTwoRows(str, STR_VAR_SEE_MORE_DETAIL); /// Hong 08/29/07 QA80-0548 v8.0691 MORE_BETTER_STRING_FOR_REFER_MORE_DETAIL
		string strVarDesp;
		////_create_help_text(oDoc, trV.help.comboString, "", _GET_NODE_VAR_DESPTION(str));
		///Joseph 03/28/07 ADD_COMBO_NAMES_LIST_FOR_TREE_NODE fix bug about type dis match
		//if(_get_help_text(vcVals, trV.help.comboString, strVarDesp))
		//{
			//_add_richedit_to_cell(oDoc, trV.help.comboString, _GET_NODE_VAR_DESPTION(str));
		//}
		//temp code, will remove later, for old xf, will show errmsg, skip it.
		//The node trV.help.comboEx is newly added.We store the variable(Treenode type)info is trV.help.comboDesciption before.
		//so we must move the info to new node(trV.help.comboEx)
		/// Hong 08/29/07 QA80-0548 v8.0691 MORE_BETTER_STRING_FOR_REFER_MORE_DETAIL
		/*
		bool bIsAddToCell = false;
		if(trV.help.comboDescription.TypeID != TNVAL_TYPE_CSTRING_VECTOR)
		{
			if(_get_help_text(vcVals, trV.help.comboDescription, strVarDesp))
			{
				_add_richedit_to_cell(oDoc, trV.help.comboDescription, _GET_NODE_VAR_DESPTION(str));
				bIsAddToCell = true;
			}
		}
		else
		{
			if(_get_help_text(vcVals, trV.help.comboEx, strVarDesp))
			{
				_add_richedit_to_cell(oDoc, trV.help.comboEx, _GET_NODE_VAR_DESPTION(str));
				bIsAddToCell = true;
			}
		}
		
		if(! bIsAddToCell)
			oDoc.AddString(STR_VARIABLES); 
		*/
		/// end MORE_BETTER_STRING_FOR_REFER_MORE_DETAIL
		oDoc.AddString(STR_VAR_SEE_MORE_DETAIL); 
		///End ADD_COMBO_NAMES_LIST_FOR_TREE_NODE
	}
	///End SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
	for(ii = 0; ii<vnComboListVar.GetSize(); ii++)
	{
		
		nDescripCellIndex = vnComboListVar[ii]*NUM_VARS_COLS;
		str = vsComboLists[nListPosition++];
		vsVals.SetSize(0);
		///DG REMOVE_CHECKBOX_OPTIONLIST
		/*
		if(vbCheckBox[ii])
		{
			vsVals.Add(str);	//Check box
			vsVals.Add(vsComboLists[nListPosition++]);
		}
		else
		*/
		///end REMOVE_CHECKBOX_OPTIONLIST
		{
			vector<string> vsTemp;
			str.GetTokens(vsTemp, '|');
			//insert the explanation from orginal storage : vsComboLists
			for(int jj=0; jj<vsTemp.GetSize(); jj++)
			{
				vsVals.Add(vsTemp[jj]);
				vsVals.Add(vsComboLists[nListPosition++]);
			}
		}
		
		str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nDescripCellIndex;
		string strCellBookMark(STR_XFV_BOOKMARK_LIST_CELL+(string)nDescripCellIndex);
		//oDoc.AddTables(vsVals, NUM_VAR_COMBOLIST_COLS, STR_XFV_OPTIONLIST, str, strCellBookMark, 0, STR_XFV_STYLE_GRID_TABLE);
		oDoc.SplitTableCell(nTableIndex, vnComboListVar[ii], -1, NUM_VARS_COLS, str, vsVals, NUM_VAR_COMBOLIST_COLS, STR_XFV_OPTIONLIST, strCellBookMark);
	}
	
	//info
	/// ----AW 11/02/05 Need display brief information
	//if(bEditableDoc)	//ingore this section for CHM  
	/// ----END 
	{
		/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//	trInfo = xf.GetHelp(IDV_HELP_BRIEF_INFO, nLang);
		
		/// Iris 06/06/06 MOVE_EXPORT_DESCRIPTION_OUTSIDE_XF_VAR_FUNC
		///// AW 05/11/06 MORE_ON_BRIEF_INFORMATION
		//// after talking with Barb and Easwar
		//// the new mapping is: in XF2Doc, XF.Description --> Doc.BriefInfo, in Doc2XF, Doc.BriefInfo -->Both XF.Description and XF.AutoCompleteHint
		//// by this way instead of rename some of nodes in both Doc and XF, we will not mass up the current systm
		////trInfo = xf_get_help_node(trXF, IDV_HELP_BRIEF_INFO, nLang);
		//trInfo = xf_get_help_node(trXF, IDV_HELP_DESCRIPTION, nLang);
		///// END MORE_ON_BRIEF_INFORMATION
		//
		///// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//str=trInfo.strVal;
		//if(bClearEmpty && str.IsEmpty())
			//oDoc.DeleteSection(STR_XF_BOOKMARK_BRIEF_INFO);
		//else
			//oDoc.AddString(str, "", STR_XF_BOOKMARK_BRIEF_INFO);
		///End MOVE_EXPORT_DESCRIPTION_OUTSIDE_XF_VAR_FUNC
	}
	
	/// ----AW 11/03/05 ADD_HELP_SCREEN_SHOT
	/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	//	trInfo = xf.GetHelp(IDV_HELP_SCREEN_SHOT, nLang);
	trInfo = xf_get_help_node(trXF, IDV_HELP_SCREEN_SHOT, nLang);
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	_create_help_image(oDoc, trInfo, "", STR_XF_BOOKMARK_SCREENSHOT); 
	/// ----END ADD_HELP_SCREEN_SHOT	
	return true;
}

bool	is_op_based(const TreeNode& trXF)
{
	/// Iris 07/24/2007 JUST_CHECK_LABTALK_IS_UNCHECED_FOR_OP_CLASS From Max's suggestion to fit DescStats_1 xfunction's requirement.
	/*
	TreeNode trParam;
	trParam = tree_find_node_by_dataID(trXF, IDXF_USGCTXT_CLASS_OP, IDXF_USGCTXT_MAIN_MENUS, -1, IDXF_USGCTXT);
	bool bIsOperationBased = trParam.nVal;
	
	/// Iris 06/19/06 QA70-8767 MORE_CONDITION_TO_CHECK_OP_BASED
	if(!bIsOperationBased)
	{
		TreeNode trUsageCtxt = tree_find_node_by_dataID(trXF, IDXF_USGCTXT);
		if(trUsageCtxt)
			bIsOperationBased = !trUsageCtxt.LabTalk.nVal && trUsageCtxt.mainmenu.Use;		
	}
	///End MORE_CONDITION_TO_CHECK_OP_BASED
	*/
	bool bIsOperationBased = false;
	TreeNode trUsageCtxt = tree_find_node_by_dataID(trXF, IDXF_USGCTXT);
	if(trUsageCtxt)
		bIsOperationBased = !trUsageCtxt.LabTalk.nVal;		
	///end JUST_CHECK_LABTALK_IS_UNCHECED_FOR_OP_CLASS
	
	return bIsOperationBased;
}
	
//dwOptions: such as skip the empty section, show remarks, and so on
/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
//	bool create_xf_document(BaseDocument& oDoc, XFunction& xf, TreeNode& trXF, const string& strStoredFolder, int nLang, DWORD dwOptions)
bool create_xf_document(BaseDocument& oDoc, TreeNode& trXF, const string& strStoredFolder, int nLang, DWORD dwOptions, BOOL bInternal)
/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
{
	bool bClearEmpty = XF2DOC_CLEAR_EMPTY & dwOptions;
	bool bEditableDoc = XF2DOC_EDITING_DOC & dwOptions;
	bool bDebugMode = XF2DOC_DEBUG_MODE & dwOptions;	
	
	/// Iris 06/19/06 QA70-8767 MORE_CONDITION_TO_CHECK_OP_BASED
	/////DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
	////bool bIsOperationBased = trXF.UsageCtxt.mainmenu.ClassOp.nVal; ///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
	//TreeNode trParam;
	//trParam = tree_find_node_by_dataID(trXF, IDXF_USGCTXT_CLASS_OP, IDXF_USGCTXT_MAIN_MENUS, -1, IDXF_USGCTXT);
	//bool bIsOperationBased = trParam.nVal;
	/////end ADD_PARAMETERS_NODE_TO_XFT
	bool bIsOperationBased = is_op_based(trXF);
	///End MORE_CONDITION_TO_CHECK_OP_BASED
	
	//if(bDebugMode)
		//oDoc.SetDebugMode(true);
	oDoc.SetDebugMode(bDebugMode);
	
	string strLang(xf_get_language_string(nLang));
	string str;
	/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	//	string strFileName(xf.GetFunctionName(false));
	string strFileName = okutil_xft_get_function_name(&trXF, false, bInternal);
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	
	/// ----AW 11/03/05 ADD_HELP_SCREEN_SHOT 
	str = oDoc.SetFileName(strStoredFolder + strFileName);
	/// ----END ADD_HELP_SCREEN_SHOT 
	
	TreeNode trInfo;
	///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	//If labtalk is not selected,mainmenu is selected and GetN is None,then show the Parameter table and not show the variable table and Usage table
	bool bSelectShow = false; 
	TreeNode trSelectLabtalk = trXF.UsageCtxt.LabTalk;
	//TreeNode trSelectMainmenu = trXF.UsageCtxt.mainmenu;
	//TreeNode trSelcteGetN = trSelectMainmenu.GetN;
	//if(trSelectLabtalk.nVal == 0 && trSelectMainmenu.Use == 1 && trSelcteGetN.nVal != 0)
	if(trSelectLabtalk.nVal == 0)
		bSelectShow = true;
	///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	//Open template
	if(bEditableDoc)
		str = STR_EDIT_TEMPLATE_FILE;
	else
		str = STR_CHM_TEMPLATE_FILE;
   	if(!oDoc.OpenTemplate(str)) {ASSERT(0);out_str("Fail to open template file.");return false;}
   	
	//------------------------------------------//
	//				Convertion begin			//
	//------------------------------------------//
	
	//title
	str=strFileName;
	
	bool bAddAdditionalInfo = false; /// Hong 09/03/07 QA80-9548 v8.0694 NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY
	///Joseph 08/28/07 ADD_ORIGIN_PRO_INFO_IN_DOCUMENT
	if(trXF.module)
	{
		string strPro = trXF.module.strVal;
		
		if(0 == strPro.Compare(STR_PRO_INFO))
		{			
			//str = str + STR_PRO_VERSION_ONLY;
			bAddAdditionalInfo  = true; /// Hong 09/03/07 QA80-9548 v8.0694 NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY
		}
		
	}
	///End ADD_ORIGIN_PRO_INFO_IN_DOCUMENT
	
	oDoc.AddString(str, NULL, STR_XF_BOOKMARK_TITLE);
	
	/// Hong 09/03/07 QA80-9548 v8.0694 NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY
	if ( bAddAdditionalInfo  )
	{
		string strProOnly;
		ocu_load_err_msg_str(XFDOC_PRO_ONLY, &strProOnly, nLang);
		oDoc.AddString(strProOnly, "", STR_XF_BOOKMARK_ADDITIONAL_INFO);
	}
	else
	{
		oDoc.DeleteSection(STR_XF_BOOKMARK_ADDITIONAL_INFO);
	}
	/// end NEW_TABLE_ADDITIONAL_INFO_FOR_ORIGINPRO_ONLY
	
	//description
	/// AW 01/26/06 REMOVE_DESCRIPTION
	// this is required by Erica as we can just use briefinfo
	//trInfo = xf.GetHelp(IDV_HELP_DESCRIPTION, nLang);
	//str = trInfo.strVal;
	//oDoc.AddString(str, "", STR_XF_BOOKMARK_DESCTIP);
	/// END REMOVE_DESCRIPTION
	
	///Iris 06/28/06 ADD_CATEGORY
	//category
	trInfo = trXF.category;
	if(trInfo)
	{
		str = trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
		{
			oDoc.DeleteSection(STR_XF_BOOKMARK_CATEGORY);
		}
		else
		{
			str.Replace('\\', ':');
			oDoc.AddString(str, NULL, STR_XF_BOOKMARK_CATEGORY);
		}
	}	
	///End ADD_CATEGORY
	
	//syntax
	trInfo = trXF.syntax;
	str = trInfo.strVal;
	/// Hong 08/29/07 b8.0691 XFDOC_NEED_NO_LT_SUPPORT_INDICATE
	if ( 0 == trSelectLabtalk.nVal )
		ocu_load_err_msg_str(XFDOC_NO_SUPPORT_LT_ACCESS, &str, nLang);
	/// end XFDOC_NEED_NO_LT_SUPPORT_INDICATE
	bool bEmptySyntax=str.IsEmpty();
	///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	//if(bClearEmpty && bEmptySyntax)
	/// Hong 08/29/07 b8.0691 XFDOC_NEED_NO_LT_SUPPORT_INDICATE
	//if(bClearEmpty && bEmptySyntax || bSelectShow)
	if( bClearEmpty && bEmptySyntax )
	/// end XFDOC_NEED_NO_LT_SUPPORT_INDICATE
	///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
		oDoc.DeleteSection(STR_XF_BOOKMARK_SYNTAX);
	else 
	{
		///Justin 2007-06-07 DISABLE_AUTO_MAKE_USAGE_AS_ECHO_REQUIRED
		/*
		if(bEmptySyntax && bEditableDoc)	//auto create syntax by variable info in User Editting Document
			/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			//	_auto_make_syntax(xf, trXF, str);
			_auto_make_syntax(trXF, str, bInternal);
			/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		*/
		///END DISABLE_AUTO_MAKE_USAGE_AS_ECHO_REQUIRED
		oDoc.AddString(str, "", STR_XF_BOOKMARK_SYNTAX);
	}
	
	//variables
	int ii=0;
	if(!bIsOperationBased)///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
	{
	/*
	vector<string> vsVals, vsComboLists;
	vector<int> vnComboListVar;
	//vector<bool> vbCheckBox;
	string strVarName;
	int nVar=1;
	foreach(TreeNode trV in trXF.vars.Children)
	{
		TreeNode trIO=trV.io;
		TreeNode trType = trV.type;
		
		strVarName=trV.name.strVal;
		//vsVals.Add(strVarName);				//name
		trIO.GetAttribute(STR_COMBO_ATTRIB, str);
		//vsVals.Add(str.GetToken(trIO.nVal, '|') + "\n" + trType.strVal);	//io + data type
		str = str.GetToken(trIO.nVal, '|') + "\n" + trType.strVal;
		//DG 9/14/05 : Difference between normal doc and CHM doc, editable one combine name, io and type
		if(bEditableDoc)
			vsVals.Add(strVarName+"\n"+str);
		else
		{
			vsVals.Add(strVarName);
			vsVals.Add(str);
		}
		
		TreeNode trVhelp;
		if(octree_find_node(&trV, &trVhelp, STR_DATAID_ATTRIB, IDV_VAR_LOCAL_HELP_BRANCH, false, 0, nLang))
		{
			//display name(tree description)
			str = trVhelp.description.strVal;	//description
			vsVals.Add(str);
			
			if(bEditableDoc)
			{
				///DG 9/14/05 New brief description section
				str = trVhelp.hint.strVal;
				vsVals.Add(str);
				///end
			}
			
			//description(tree remarks)
			str = trVhelp.remark.strVal;
			vsVals.Add(str);
			
			bool bCheckBox = false;
			str = get_var_combolist(trV, bCheckBox);
			//if(!str.IsEmpty())	///DG REMOVE_CHECKBOX_OPTIONLIST
			if(!bCheckBox && !str.IsEmpty())
			{
				vnComboListVar.Add(nVar);
				vsComboLists.Add(str);
				//vbCheckBox.Add(bCheckBox);
				
				vector<string> vsTemp;
				_get_combolist_text(vsTemp, trVhelp.comboString);
				///DG REMOVE_CHECKBOX_OPTIONLIST
				// if(bCheckBox)
				// 	vsTemp.SetSize(1);
				// else
				///end REMOVE_CHECKBOX_OPTIONLIST
					vsTemp.SetSize(str.GetNumTokens('|'));
				
				vsComboLists.Append(vsTemp);	//Storage reuse, no idea on how to store it
			}
		}
		else
			printf("####%s: invalid tree structure.\n", trV.tagName);
		
		nVar++;
	}
	//oDoc.AddTables(vsVals, NUM_VARS_COLS, NULL, STR_XF_BOOKMARK_VARIABLES, STR_XFV_BOOKMARK_TABLE_CELL, 1);	//variables tables, first row is title
	int nTableIndex;
	oDoc.FillTable(vsVals, NUM_VARS_COLS, nTableIndex, STR_XF_BOOKMARK_VARIABLES, 1, STR_XFV_BOOKMARK_TABLE_CELL);


	
	//add combolist table in description cell
	int nDescripCellIndex, nListPosition=0;
	for(ii=0; ii<vnComboListVar.GetSize(); ii++)
	{
		nDescripCellIndex = vnComboListVar[ii]*NUM_VARS_COLS;
		str = vsComboLists[nListPosition++];
		vsVals.SetSize(0);
		///DG REMOVE_CHECKBOX_OPTIONLIST
		// if(vbCheckBox[ii])
		// {
		// 	vsVals.Add(str);	//Check box
		// 	vsVals.Add(vsComboLists[nListPosition++]);
		// }
		// else
		///end REMOVE_CHECKBOX_OPTIONLIST
		{
			vector<string> vsTemp;
			str.GetTokens(vsTemp, '|');
			//insert the explanation from orginal storage : vsComboLists
			for(int jj=0; jj<vsTemp.GetSize(); jj++)
			{
				vsVals.Add(vsTemp[jj]);
				vsVals.Add(vsComboLists[nListPosition++]);
			}
		}
		
		str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nDescripCellIndex;
		string strCellBookMark(STR_XFV_BOOKMARK_LIST_CELL+(string)nDescripCellIndex);
		//oDoc.AddTables(vsVals, NUM_VAR_COMBOLIST_COLS, STR_XFV_OPTIONLIST, str, strCellBookMark, 0, STR_XFV_STYLE_GRID_TABLE);
		oDoc.SplitTableCell(nTableIndex, vnComboListVar[ii], -1, NUM_VARS_COLS, str, vsVals, NUM_VAR_COMBOLIST_COLS, STR_XFV_OPTIONLIST, strCellBookMark);
	}
	
	//info
	if(bEditableDoc)	//ingore this section for CHM
	{
		trInfo = xf.GetHelp(IDV_HELP_BRIEF_INFO, nLang);
		str=trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_BRIEF_INFO);
		else
			oDoc.AddString(str, "", STR_XF_BOOKMARK_BRIEF_INFO);
	}
	*/
	///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW	
		if(! bSelectShow)
		{
	///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	//	create_xf_document_variables(oDoc, xf, trXF, nLang, bEditableDoc, bClearEmpty);
			create_xf_document_variables(oDoc, trXF, nLang, bEditableDoc, bClearEmpty, bInternal);
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			/// Iris 06/26/06 QA70-8349 V8.0432 VARIABLE_FOR_BASIC_XF_PARAM_FOR_OP_BASED_XF
			oDoc.DeleteSection(STR_XF_BOOKMARK_PARAMETERS);
			///End VARIABLE_FOR_BASIC_XF_PARAM_FOR_OP_BASED_XF
		///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW	
		}
		else
		{
			oDoc.DeleteSection(STR_XF_BOOKMARK_VARIABLES);
		}
		///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
		/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY	
	}
	else
	{
		/// Iris 06/26/06 QA70-8349 V8.0432 VARIABLE_FOR_BASIC_XF_PARAM_FOR_OP_BASED_XF
		oDoc.DeleteSection(STR_XF_BOOKMARK_VARIABLES);
		///End VARIABLE_FOR_BASIC_XF_PARAM_FOR_OP_BASED_XF		
	}
	//end	if(!bIsOperationBased)
	
	/// Iris 06/06/06 MOVE_EXPORT_DESCRIPTION_OUTSIDE_XF_VAR_FUNC  --- Moved from create_xf_document_variables
	/// AW 05/11/06 MORE_ON_BRIEF_INFORMATION
	// after talking with Barb and Easwar
	// the new mapping is: in XF2Doc, XF.Description --> Doc.BriefInfo, in Doc2XF, Doc.BriefInfo -->Both XF.Description and XF.AutoCompleteHint
	// by this way instead of rename some of nodes in both Doc and XF, we will not mass up the current systm
	//trInfo = xf_get_help_node(trXF, IDV_HELP_BRIEF_INFO, nLang);
	trInfo = xf_get_help_node(trXF, IDV_HELP_DESCRIPTION, nLang);
	/// END MORE_ON_BRIEF_INFORMATION
	
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	str = trInfo.strVal;
	
	/// AW 04/03/07 QA80-9548 v8.0597 XF_LOCALIZATION
	if ( str.GetLength() < 3 ) // for unknown reason, in G/J/C, the node may be not empty
	{
		trInfo = xf_get_help_node(trXF, IDV_HELP_DESCRIPTION, IDRS_HELP_E);
		str = trInfo.strVal;
	}
	/// END XF_LOCALIZATION
		
	///Joseph 10/09/06  ADD_MENU_INFO
	//if(bClearEmpty && str.IsEmpty())
		//oDoc.DeleteSection(STR_XF_BOOKMARK_BRIEF_INFO);
	//else
		//oDoc.AddString(str, "", STR_XF_BOOKMARK_BRIEF_INFO);
	string strMenuInfo;
	string strBriefInfo;
	xf_seperate_description(str, strMenuInfo, strBriefInfo);
	strMenuInfo.Replace("&", "");  ///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	strBriefInfo.TrimLeft();
	strBriefInfo.TrimRight();
	if(bClearEmpty)
	{
		if(strMenuInfo.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_MENU_INFO);
		else
			oDoc.AddString(strMenuInfo, "", STR_XF_BOOKMARK_MENU_INFO);
		if(strBriefInfo.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_BRIEF_INFO);
		else
			oDoc.AddString(strBriefInfo, "", STR_XF_BOOKMARK_BRIEF_INFO);
	}
	else
	{
		oDoc.AddString(strBriefInfo, "", STR_XF_BOOKMARK_BRIEF_INFO);
		oDoc.AddString(strMenuInfo, "", STR_XF_BOOKMARK_MENU_INFO);
	}
	///End ADD_MENU_INFO
	///End MOVE_EXPORT_DESCRIPTION_OUTSIDE_XF_VAR_FUNC
	
	///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT added IDV_HELP_PARAMETERS, STR_XF_BOOKMARK_PARAMETERS below
	// //summary, example, reference and algorithm and parameters
	// vector<int> vnHelpIDs={IDV_HELP_SUMMARY, IDV_HELP_EXAMPLE, IDV_HELP_REF, IDV_HELP_ALGORITHM, IDV_HELP_PARAMETERS};
	// vector<string> vsHelpBookMarks={STR_XF_BOOKMARK_SUMMARY, STR_XF_BOOKMARK_EXAMPLE, STR_XF_BOOKMARK_REF, STR_XF_BOOKMARK_ALGORITHM, STR_XF_BOOKMARK_PARAMETERS};
	// end ADD_PARAMETERS_NODE_TO_XFT
	for(ii=0; ii<s_vnHelpIDs.GetSize(); ii++)
	{
		///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
		///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
		//if( IDV_HELP_PARAMETERS==vnHelpIDs[ii] && !bIsOperationBased )
		if( IDV_HELP_PARAMETERS==s_vnHelpIDs[ii] )
			if(! bSelectShow || !bIsOperationBased)
		///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
			continue;
		///end ADD_PARAMETERS_NODE_TO_XFT
		
		/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//	trInfo = xf.GetHelp(vnHelpIDs[ii], nLang);
		trInfo = xf_get_help_node(trXF, s_vnHelpIDs[ii], nLang);
		/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY	
		_create_help_text(oDoc, trInfo, "", s_vsHelpBookMarks[ii], bClearEmpty);
	}
	
	//see also
	
	/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	//	trInfo = xf.GetHelp(IDV_HELP_SEE_ALSO, nLang);
	trInfo = xf_get_help_node(trXF, IDV_HELP_SEE_ALSO, nLang);
	/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	if(trInfo)
	{
		str=trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_SEEALSO);
		else
			oDoc.AddString(str, "", STR_XF_BOOKMARK_SEEALSO);
	}
	else
		out_str("Fail to find node in x-function");
	
	///---Joseph 04/26/07 QA70-9678 ADD_SCRIPT_EXAMPLE_NODE
	trInfo = xf_get_help_node(trXF, IDV_HELP_LT_SCRIPT_SAMPLE, nLang);
	if(trInfo)
	{
		str=trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_LT_SCRIPT_EXAMPLE);
		else
			oDoc.AddString(str, "", STR_XF_BOOKMARK_LT_SCRIPT_EXAMPLE);
	}
	else
		out_str("Fail to find node in x-function");
	///---End ADD_SCRIPT_EXAMPLE_NODE
	
//---CPY 10/25/05 ADD_RELATED_XF_NODE_FOR_XF_DOC
/*	/// Iris 10/09/05 ADD_MODIFICATION_LOG
	//modification log
	trInfo = trXF.modificationLog;
	if( trInfo )
	{
		str = trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_MODIFICATION_LOG);
		else
			oDoc.AddString(str, "", STR_XF_BOOKMARK_MODIFICATION_LOG);		
	}
	else
		out_str("Fail to find Modification Log node in x-function");
	///End ADD_MODIFICATION_LOG */
	if(bEditableDoc)    // AW 11/29/05 no need modification log for help
		_add_node_to_doc(oDoc, trXF.modificationLog, STR_XF_BOOKMARK_MODIFICATION_LOG, bClearEmpty);
//----
	_add_node_to_doc(oDoc, trXF.relatedXF, STR_XF_BOOKMARK_RELATED_XF, bClearEmpty);//---CPY 10/25/05 ADD_RELATED_XF_NODE_FOR_XF_DOC
	
	
	//error string table
	if(bEditableDoc)
	{
		trInfo = trXF.errmsgCount;
		int nErrorCount = trInfo.nVal;
		if(nErrorCount>0)
		{
			///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT local scope
			vector<string> vsVals;
			int nTableIndex;
			///end ADD_PARAMETERS_NODE_TO_XFT
			
			/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			//	trInfo = xf.GetHelp(IDV_ERRMSG_LIST, nLang);
			trInfo = xf_get_help_node(trXF, IDV_ERRMSG_LIST, nLang);
			/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			vector<string> vs;
			_get_combolist_text(vs, trInfo);
			vsVals.SetSize(0);
			for(int jj=0; jj<nErrorCount; jj++)
			{
				vsVals.Add(jj+1);	//0 : succss
				if(jj<vs.GetSize())
					str=vs[jj];
				else
					str.Empty();
				vsVals.Add(str);
			}
			oDoc.FillTable(vsVals, NUM_ERRMSG_TABLE_COLS, nTableIndex, STR_XF_BOOKMARK_ERRMSG, 1, STR_XF_ERRMSG_TABLE_CELL);	//first line for header
		}
		else
		{
			oDoc.DeleteSection(STR_XF_BOOKMARK_ERRMSG);
		}
	}
	
	if(!bEditableDoc)
		strFileName+="_help";	//to prevent write chm format file back to xf
	str = get_xf_doc_filename(strStoredFolder, strFileName, strLang);
	
	if(!bDebugMode)
		oDoc.SetDebugMode(true);	//after running, enable document event

	if(!oDoc.SaveDoc(str))
		printf("Error, Fail to create document: %s \n", str);
	oDoc.CloseDoc();
	return true;
}
/*
#ifdef _XFTX_DISPLAY_H
bool diplay_xf_document(BaseDocument& oDoc, XFunction& xf, TreeNode& trXF, const string& strStoredFolder, int nLang, DWORD dwOptions)
{
	bool bClearEmpty = XF2DOC_CLEAR_EMPTY & dwOptions;
	bool bEditableDoc = XF2DOC_EDITING_DOC & dwOptions;
	
	string strLang(_get_language_string(nLang));
	string str, strFileName(xf.GetFunctionName(false));
	TreeNode trInfo;
	
	//Open template
	if(bEditableDoc)
		str = STR_EDIT_TEMPLATE_FILE;
	else
		str = STR_CHM_TEMPLATE_FILE;
   	if(!oDoc.OpenTemplate(str)) {ASSERT(0);out_str("Fail to open template file.");return false;}
   	
	//------------------------------------------//
	//				Convertion begin			//
	//------------------------------------------//
	
	//title
	str=strFileName;
	oDoc.AddString(str, NULL, STR_XF_BOOKMARK_TITLE);
	
	//description
	trInfo = xf.GetHelp(IDV_HELP_DESCRIPTION, nLang);
	str = trInfo.strVal;
	oDoc.AddString(str, "", STR_XF_BOOKMARK_DESCTIP);
	
	//syntax
	trInfo = trXF.syntax;
	str = trInfo.strVal;
	bool bEmptySyntax=str.IsEmpty();
	if(bClearEmpty && bEmptySyntax)
		oDoc.DeleteSection(STR_XF_BOOKMARK_SYNTAX);
	else 
	{
		if(bEmptySyntax && bEditableDoc)	//auto create syntax by variable info in User Editting Document
			_auto_make_syntax(xf, trXF, str);
		
		oDoc.AddString(str, "", STR_XF_BOOKMARK_SYNTAX);
	}
	
	//variables
	vector<string> vsVals, vsComboLists;
	vector<int> vnComboListVar;
	vector<bool> vbCheckBox;
	string strVarName;
	int nVar=1;
	foreach(TreeNode trV in trXF.vars.Children)
	{
		TreeNode trIO=trV.io;
		TreeNode trType = trV.type;
		
		strVarName=trV.name.strVal;
		//vsVals.Add(strVarName);				//name
		trIO.GetAttribute(STR_COMBO_ATTRIB, str);
		//vsVals.Add(str.GetToken(trIO.nVal, '|') + "\n" + trType.strVal);	//io + data type
		str = str.GetToken(trIO.nVal, '|') + "\n" + trType.strVal;
		//DG 9/14/05 : Difference between normal doc and CHM doc, editable one combine name, io and type
		if(bEditableDoc)
			vsVals.Add(strVarName+"\n"+str);
		else
		{
			vsVals.Add(strVarName);
			vsVals.Add(str);
		}
		
		TreeNode trVhelp;
		if(octree_find_node(&trV, &trVhelp, STR_DATAID_ATTRIB, IDV_VAR_LOCAL_HELP_BRANCH, false, 0, nLang))
		{
			//display name(tree description)
			str = trVhelp.description.strVal;	//description
			vsVals.Add(str);
			
			if(bEditableDoc)
			{
				///DG 9/14/05 New brief description section
				str = trVhelp.hint.strVal;
				vsVals.Add(str);
				///end
			}
			
			//description(tree remarks)
			str = trVhelp.remark.strVal;
			vsVals.Add(str);
			
			bool bCheckBox = false;
			str = get_var_combolist(trV, bCheckBox);
			if(!str.IsEmpty())
			{
				vnComboListVar.Add(nVar);
				vsComboLists.Add(str);
				vbCheckBox.Add(bCheckBox);
				
				vector<string> vsTemp;
				_get_combolist_text(vsTemp, trVhelp.comboString);
				if(bCheckBox)
					vsTemp.SetSize(1);
				else
					vsTemp.SetSize(str.GetNumTokens('|'));
				
				vsComboLists.Append(vsTemp);	//Storage reuse, no idea on how to store it
			}
		}
		else
			printf("####%s: invalid tree structure.\n", trV.tagName);
		
		nVar++;
	}
	
	
	
	//// AW_TX_DIFFF	
	//oDoc.AddTables(vsVals, NUM_VARS_COLS, NULL, STR_XF_BOOKMARK_VARIABLES, STR_XFV_BOOKMARK_TABLE_CELL, 1);	//variables tables, first row is title
	int nTableIndex = oDoc.GetTableIndexByBookMark(STR_XF_BOOKMARK_VARIABLES);
	oDoc.FillTable(vsVals, NUM_VARS_COLS, nTableIndex, 1);	//variables tables, first row is title
	/// END AW_TX_DIFFF
	
	
	//add combolist table in description cell
	int nDescripCellIndex, nListPosition=0;
	for(int ii=0; ii<vnComboListVar.GetSize(); ii++)
	{
		nDescripCellIndex = vnComboListVar[ii]*NUM_VARS_COLS;
		str = vsComboLists[nListPosition++];
		vsVals.SetSize(0);
		if(vbCheckBox[ii])
		{
			vsVals.Add(str);	//Check box
			vsVals.Add(vsComboLists[nListPosition++]);
		}
		else
		{
			vector<string> vsTemp;
			str.GetTokens(vsTemp, '|');
			//insert the explanation from orginal storage : vsComboLists
			for(int jj=0; jj<vsTemp.GetSize(); jj++)
			{
				vsVals.Add(vsTemp[jj]);
				vsVals.Add(vsComboLists[nListPosition++]);
			}
		}
		
		
		
		//// AW_TX_DIFFF
		
		//str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nDescripCellIndex;
		//string strCellBookMark(STR_XFV_BOOKMARK_LIST_CELL+(string)nDescripCellIndex);
		//oDoc.AddTables(vsVals, NUM_VAR_COMBOLIST_COLS, STR_XFV_OPTIONLIST, str, vnComboListVar[ii], 0, STR_XFV_STYLE_GRID_TABLE);
		BOOL bOK = oDoc.SplitCell(nTableIndex, vnComboListVar[ii], NUM_VARS_COLS );
		bOK = oDoc.InsertTable(vsVals, NUM_VAR_COMBOLIST_COLS, STR_XFV_OPTIONLIST); 
		//// END AW_TX_DIFFF
	}
	
	//info
	//if(bEditableDoc)	//ingore this section for CHM
	{
		trInfo = xf.GetHelp(IDV_HELP_BRIEF_INFO, nLang);
		str=trInfo.strVal;
		if(bClearEmpty && str.IsEmpty())
			oDoc.DeleteSection(STR_XF_BOOKMARK_BRIEF_INFO);
		else
			oDoc.AddString(str, "", STR_XF_BOOKMARK_BRIEF_INFO);
	}
	
	//summary, example, reference and algorithm
	vector<int> vnHelpIDs={IDV_HELP_SUMMARY, IDV_HELP_EXAMPLE, IDV_HELP_REF, IDV_HELP_ALGORITHM};
	vector<string> vsHelpBookMarks={STR_XF_BOOKMARK_SUMMARY, STR_XF_BOOKMARK_EXAMPLE, STR_XF_BOOKMARK_REF, STR_XF_BOOKMARK_ALGORITHM};
	
	for(ii=0; ii<vnHelpIDs.GetSize(); ii++)
	{
		trInfo = xf.GetHelp(vnHelpIDs[ii], nLang);
		_create_help_text(oDoc, trInfo, "", vsHelpBookMarks[ii], bClearEmpty);
	}
	
	//see also
	trInfo = xf.GetHelp(IDV_HELP_SEE_ALSO, nLang);
	str=trInfo.strVal;
	if(bClearEmpty && str.IsEmpty())
		oDoc.DeleteSection(STR_XF_BOOKMARK_SEEALSO);
	else
		oDoc.AddString(str, "", STR_XF_BOOKMARK_SEEALSO);
	
	if(!bEditableDoc)
		strFileName+="_help";	//to prevent write chm format file back to xf
	str = get_xf_doc_filename(strStoredFolder, strFileName, strLang);
	oDoc.SaveDoc(str);
	oDoc.CloseDoc();
	return true;
}
#endif //_XFTX_DISPLAY_H
*/
bool create_xf_documents(BaseDocument& oDoc, const string& strFileName, const string& strDestFolder, int nSpecifyLangIndex = LANG_ALL, bool bCHMDoc=false)
{
	vector<int> vnLang;
	vector<string> vsLang;
	get_xf_language_info(vnLang, vsLang, nSpecifyLangIndex);
	
	XFunction xf;
	TreeNode trXF;
	//----- CPY 11/20/07 FORCE_LOAD_XF_WIHTOUT_VALDATA_LOCALIZATION
	//if(!xf.Load(&trXF, strFileName, LTXF_BY_FILENAME))
	if(!xf.LoadNoLocalize(&trXF, strFileName, LTXF_BY_FILENAME))
	//-----
	{
		printf("err loading %s\n", strFileName);
		return false;    
	}
	//---- CPY 9/2/05	CHECK_EMPTY_HELP_NODES
	string strXFname = xf.GetFunctionName(false), strDocFile;
	///Justin 2007-04-10 v8.0597b qa-9585 SKIP_DOCUMENT_IF_NO_NEED
	if(trXF.SkipHelpDoc.nVal)
	{
		printf(_L("X-Function %s is skipped, for it does not need document"), strXFname);
		return true;
	}
	///END SKIP_DOCUMENT_IF_NO_NEED
	//----CPY 9/20/05 XF_WORD_DOC_LOCATION_ADD_XF_CATEGORY
	string strStoredFolder = _check_path_XF_category(trXF, strDestFolder);
	printf("Processing %s, destination folder = %s...\n", strXFname, strStoredFolder);
	//----
	
	DWORD dwOptions = bCHMDoc ? XF2DOC_CLEAR_EMPTY : XF2DOC_EDITING_DOC;
	for(int jj = 0; jj < vnLang.GetSize(); jj++)
	{
		///DG MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN
		if(!_check_xfdoc_checked_out(strXFname, strStoredFolder, vsLang[jj]))
			continue;
		///end MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN
		

		///Kevin 09/30/05 ADD_WARNING_MESSAGE_WHEN_OVERWRITE
		//add a judgement that prevent to overwrite the newer document
		string strDocName;
	
		///Joseph 11/14/06  NOT_OVERWRITHE_WHEN_NAME_IS_DIFFERENT
		//strDocName = strStoredFolder + strXFname + "_" + vsLang[jj] + ".doc";
		if(!bCHMDoc)
			strDocName = strStoredFolder + strXFname + "_" + vsLang[jj] + ".doc";
		else
			strDocName = strStoredFolder + strXFname + "_" + "help" + "_" + vsLang[jj] + ".doc";
		///End NOT_OVERWRITHE_WHEN_NAME_IS_DIFFERENT
		int nRet = file_time_compare(strFileName, strDocName, LAST_WRITE_TIME);
		if ( 0 == nRet && MessageBox( GetWindow(), 
										"Doc file is newer than the XFunction document!\r\nDo you want to overwrite the Doc file?", 
										"Warning!" , 
										MB_YESNO | MB_ICONQUESTION | MB_DEFBUTTON2) == IDNO )
		{
			printf("Convert stopped\n");
			continue;
		}
		///End ADD_WARNING_MESSAGE_WHEN_OVERWRITE

		///DG 9/17/05 delay to wait for word's response, I am try to find a strange problem in creating large number of file
		LT_execute("sec -p 3");	//wait for 3 second
		///end
		
		/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//	create_xf_document(oDoc, xf, trXF, strStoredFolder, vnLang[jj], dwOptions);
		create_xf_document(oDoc, trXF, strStoredFolder, vnLang[jj], dwOptions, xf.IsInternal());
		/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	}
	out_str("done!");//---------CPY 9/2/05	CHECK_EMPTY_HELP_NODES
	return true;
}

/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
//	bool update_xf_by_document(BaseDocument& oDoc, XFunction& xf, TreeNode& trXF, const string& strDocFile, int nLang, DWORD dwOptions)
bool update_xf_by_document(BaseDocument& oDoc, TreeNode& trXF, const string& strDocFile, int nLang, DWORD dwOptions)
/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
{
	bool bDebugMode = XF2DOC_DEBUG_MODE & dwOptions;
	
	/// Iris 06/19/06 QA70-8767 MORE_CONDITION_TO_CHECK_OP_BASED
	/////DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
	//bool bIsOperationBased = trXF.UsageCtxt.mainmenu.ClassOp.nVal;
	/////end ADD_PARAMETERS_NODE_TO_XFT
	bool bIsOperationBased = is_op_based(trXF);
	///End MORE_CONDITION_TO_CHECK_OP_BASED
	
	if(bDebugMode)
		oDoc.SetDebugMode(true);
	
	string strLang(xf_get_language_string(nLang)), str;
	TreeNode trInfo;
	vector<string> vsVals;
	///Joseph 09/27/06  LABEL_CANNOT_CONTAIN_ENTER
   	//if(!oDoc.OpenDoc(strDocFile)){return false;}
   	string strTempFile;
   	if(!GetTempFileName(strTempFile))
   		return false;
	if(oDoc.OpenDoc(strDocFile))
	{
		oDoc.SaveDoc(strTempFile);
		oDoc.CloseDoc();
	}
	
    if(!oDoc.OpenDoc(strTempFile)){return false;}
   	///End LABEL_CANNOT_CONTAIN_ENTER
	//syntax : syntax only in English, ingore others
	
	///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	bool bShowParam = false;
	if(trXF.UsageCtxt.LabTalk.nVal!= 0)
		bShowParam = true;
	///Justin 2007-04-18 DROP_COMMENT_FROM_COMMAND_LINE_USAGE  ///so need not to support other language
	///Justin 2007-03-09 TO_SUPPORT_OTHER_LANGUIGES_FOR_COMMAND_LINE_USAGE
	//if(bShowParam && IDRS_HELP_E==nLang && oDoc.GetString(STR_XF_BOOKMARK_SYNTAX, str))
	//if(bShowParam && oDoc.GetString(STR_XF_BOOKMARK_SYNTAX, str))
	if(bShowParam && IDRS_HELP_E==nLang && oDoc.GetString(STR_XF_BOOKMARK_SYNTAX, str))
	/// End TO_SUPPORT_OTHER_LANGUIGES_FOR_COMMAND_LINE_USAGE
	/// End DROP_COMMENT_FROM_COMMAND_LINE_USAGE
	//if(IDRS_HELP_E==nLang && oDoc.GetString(STR_XF_BOOKMARK_SYNTAX, str))
	///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	{
		trInfo = trXF.syntax;
		
		/// Iris 5/10/06 ADD_TIP_FOR_AUTO_CREATED_USAGE
		/// must ignore the tip when write the syntax back to xfunction, the tip begin with '(' and end with ')'
		if( trInfo.strVal.IsEmpty() && '(' == str.GetAt(0) )
		{
			str.Delete(0);			
			vector<string> vsTemp;
			string strTip = str.GetToken(0, ')') + ")";			
			str.Delete(0, strTip.GetLength());	
			str.TrimLeft();//remove newline, space...
		}
		///End ADD_TIP_FOR_AUTO_CREATED_USAGE
		
		trInfo.strVal = str;	
	}
	///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	if(!bIsOperationBased && bShowParam)///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
		//if(!bIsOperationBased)///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
	///End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	{
	int nVar=1, nCellDisplayName, nCellHint, nCellDescription, nCellComboList;
	foreach(TreeNode trV in trXF.vars.Children)
	{
		///------ Folger 08/12/09 QA80-14112 NEED_OPTION_STRING_TO_HIDE_XF_VARIABLE_FROM_LT
		XFVariable	var(trV);
		if ( !var.IsAccessibleFromLT() )
			continue;
		///------ End NEED_OPTION_STRING_TO_HIDE_XF_VARIABLE_FROM_LT

		TreeNode trVhelp;
		if(octree_find_node(&trV, &trVhelp, STR_DATAID_ATTRIB, IDV_VAR_LOCAL_HELP_BRANCH, false, 0, nLang))
		{
			//display name
			///Joseph 09/21/06 DOCTOXF_VAR_LABEL_CORRENT
			//nCellDisplayName = nVar*NUM_VARS_COLS - 2;
			nCellDisplayName = nVar*NUM_VARS_COLS - 3;
			///End DOCTOXF_VAR_LABEL_CORRENT
			
			/// Hong 08/09/07 v8.0678 GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC
			/* Echo said we NOT allowed user to edit variable label in doc
			str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nCellDisplayName;	//variable display name cell bookmark
			if(oDoc.GetString(str, str, false))
			///Joseph 09/27/06  LABEL_CANNOT_CONTAIN_ENTER
				//trVhelp.description.strVal = str;				
			{
				str.TrimLeft();
				str.TrimRight();
				if(str.Find('\r')>-1)
				{
					printf("The Label contains illegal character!\n");
					oDoc.CloseDoc();
					return false;
				}
				///End TRIM_SPACE_AND_CHECK_NEW_LINE
				trVhelp.description.strVal = str;
			}
			*/
			/// end GET_SYSTEM_LABEL_FROM_OC_FOR_XF2DOC
			///End LABEL_CANNOT_CONTAIN_ENTER
			//Brief description
			///Joseph 09/21/06 DOCTOXF_VAR_LABEL_CORRENT
			//nCellHint = nCellDisplayName + 1;
			nCellHint = nCellDisplayName + 2;
			///End DOCTOXF_VAR_LABEL_CORRENT
			str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nCellHint;	//variable brief description cell bookmark
			if(oDoc.GetString(str, str, false))
				trVhelp.hint.strVal = str;
			
			//description
			nCellDescription = nVar*NUM_VARS_COLS;
			str = STR_XFV_BOOKMARK_TABLE_CELL+(string)nCellDescription;	//variable description cell bookmark
			///Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
			string strBookMark = str;
			//if(oDoc.GetString(str, str, false))
			if(oDoc.GetString(strBookMark, str, false))
			///End SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
				trVhelp.remark.strVal = str;
			/// Hong 08/29/07 QA80-0548 v8.0691 MORE_BETTER_STRING_FOR_REFER_MORE_DETAIL
			/*
			///Joseph 11/30/06	SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
			if(trV.type.strVal == STR_TREENODE)
			{	
				vector<char> vcCombo;
				_GET_NODE_VAR_DESPTION(strBookMark);
				if(oDoc.GetRichText(strBookMark, vcCombo, false))
				{
					///Joseph 03/28/07 ADD_COMBO_NAMES_LIST_FOR_TREE_NODE fix bug about type dis match
					// temp code for old xf, will remove later.
					//_set_help_text(trV.help.comboString, vcCombo);
					if(trV.help.comboDescription.TypeID != TNVAL_TYPE_CSTRING_VECTOR)
					{
						trV.help.comboDescription.TypeID = TNVAL_TYPE_CSTRING_VECTOR;	
					}
					
					_set_help_text(trV.help.comboEx, vcCombo);
					///End ADD_COMBO_NAMES_LIST_FOR_TREE_NODE
				}
			}
			///End SPLITE_TABLE_CELL_FOR_TREENODE_VARIABLE
			*/
			/// end MORE_BETTER_STRING_FOR_REFER_MORE_DETAIL
			
			bool bCheckBox = false;
			str=get_var_combolist(trV, bCheckBox);
			//if(!str.IsEmpty())	///DG REMOVE_CHECKBOX_OPTIONLIST
			if(!bCheckBox && !str.IsEmpty())	//avoid fail to find table msg
			{
				///DG REMOVE_CHECKBOX_OPTIONLIST
				/*
				int nSize=1;
				if(!bCheckBox)
					nSize = str.GetNumTokens('|');
				*/		
				int nSize = str.GetNumTokens('|');
				///end REMOVE_CHECKBOX_OPTIONLIST
				vsVals.SetSize(0);
				///justin 03/29/07 qa70-9548 v8.0592 XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
				vector<string> vsCombList(0);
				string strCombTemplate = str;
				///End
				for(int ii=0; ii<nSize; ii++)
				{
					nCellComboList = (ii+1)*NUM_VAR_COMBOLIST_COLS;
					str = STR_XFV_BOOKMARK_LIST_CELL;
					str+=(string)nCellDescription+(string)nCellComboList;
					if(oDoc.GetString(str, str, false))
						vsVals.Add(str);
					
					///justin 03/29/07 qa70-9548 v8.0592 XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
					str = STR_XFV_BOOKMARK_LIST_CELL;
					str+=(string)nCellDescription+(string)(nCellComboList-1);
					if(!oDoc.GetString(str, str, false))
						str.Empty();
					vsCombList.Add(str);						
					///end	XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
						
				}
				
				/// Hong 12/18/07 COMBOSTR_CHANGED_INTO_J_IN_XF_BUILDER_AND_LATER_SAVED_INTO_XF
				/*
				///justin 04/02/07 qa70-9548 v8.0594 XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC 				
				//// ------------AW 04/03/07 QA80-9548 v8.0597 XF_LOCALIZATION
				// we should just use string as the combo string is not so big, so in vc level it is simple
				//vector<byte> vbComboStr;
				
				//_create_new_compbstr(strCombTemplate, vsCombList).GetBytes(vbComboStr);
				//trVhelp.comboEx.bVals = vbComboStr;
				TreeNode	trcomboEx = trVhelp.comboEx;
				trcomboEx.RemoveAttribute(TREE_ATTR_NAME_SPECAL_DATATYPE);		// AW, there is a bug here, but if we fix it, it will be a big changing, according to ML/TD, we add this temp solution				
				string strTemp = _create_new_compbstr(strCombTemplate, vsCombList, nLang);
				
				///Joseph 05/10/07 QA70-9548 SHOULD_SUPPORT_MULTI_LANGUAGE
				if(nLang == IDRS_HELP_E)
				{
					trV.comboString.strVal = strTemp;
				}
				else if(_is_consistent_combstr(trV.comboString.strVal, strTemp, nLang))
				///End SHOULD_SUPPORT_MULTI_LANGUAGE
					trcomboEx.strVal = strTemp;
				//// END QA80-9548 v8.0597 XF_LOCALIZATION
				///End XF_COMBOSTRING_LOCALIZATION_VIA_XF2DOC
				*/ /// Hong 03/08/08 v8.0820 FIX_XF2DOC_LOST_COMBO_DESCRIPTION
				trVhelp.comboDescription.strVals = vsVals;
				/**/ /// Hong 03/08/08 v8.0820 FIX_XF2DOC_LOST_COMBO_DESCRIPTION
				/// end COMBOSTR_CHANGED_INTO_J_IN_XF_BUILDER_AND_LATER_SAVED_INTO_XF
			}
		}
		else
			printf("####%s: invalid tree structure.\n", trV.tagName);
		
		nVar++;
	}
	}// end if(!bIsOperationBased)
	
	
	///Joseph 10/09/06 ADD_MENU_INFO
	//help
   	//description, brief info and See Also
   	///Joseph 09/11/06 QA70-8349  	CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	//vector<int> vnSimpleHelpIDs={IDV_HELP_DESCRIPTION, IDV_HELP_BRIEF_INFO, IDV_HELP_SEE_ALSO};
	//vector<string> vsSimpleHelpBookMarks={STR_XF_BOOKMARK_DESCTIP, STR_XF_BOOKMARK_BRIEF_INFO, STR_XF_BOOKMARK_SEEALSO};
	//vector<int> vnSimpleHelpIDs={IDV_HELP_BRIEF_INFO, IDV_HELP_SEE_ALSO};
	//vector<string> vsSimpleHelpBookMarks={STR_XF_BOOKMARK_BRIEF_INFO, STR_XF_BOOKMARK_SEEALSO};
	/////End CATEGORY_UP_DESCRIPTION_SELECT_SHOW
	//for(int ii=0; ii<vnSimpleHelpIDs.GetSize(); ii++)
	//{
		//if(IDRS_HELP_E!=nLang && IDV_HELP_SEE_ALSO == vnSimpleHelpIDs[ii])
			//continue;	//ingnore other language See Also, only English is aviarable
		//if(oDoc.GetString(vsSimpleHelpBookMarks[ii], str))
		//{
			///// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			////	trInfo = xf.GetHelp(vnSimpleHelpIDs[ii], nLang);
			//trInfo = xf_get_help_node(trXF, vnSimpleHelpIDs[ii], nLang);
			///// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			//if(trInfo)	//
				//trInfo.strVal = str;
			//else
				//out_str("Fail to find node in x-function");
			//
			///// AW 05/11/06 MORE_ON_BRIEF_INFORMATION
			//// after talking with Barb and Easwar
			//// the new mapping is: in XF2Doc, XF.Description --> Doc.BriefInfo, in Doc2XF, Doc.BriefInfo -->Both XF.Description and XF.AutoCompleteHint
			//// by this way instead of rename some of nodes in both Doc and XF, we will not mass up the current systm
			//if ( IDV_HELP_BRIEF_INFO == vnSimpleHelpIDs[ii] )
			//{
				//trInfo = xf_get_help_node(trXF, IDV_HELP_DESCRIPTION, nLang);
				//if(trInfo)	//
					//trInfo.strVal=str;
				//else
					//out_str("Fail to find Descrption node in x-function");	
				//
			//}			
			///// END MORE_ON_BRIEF_INFORMATION					
		//}
	//}

	if(IDRS_HELP_E == nLang)
	{
		if(oDoc.GetString(STR_XF_BOOKMARK_SEEALSO, str))
		{
			trInfo = xf_get_help_node(trXF, IDV_HELP_SEE_ALSO, nLang);
			
			if(trInfo)	
				trInfo.strVal = str;
			else
				out_str("Fail to find brief node in x-function");
		}
	}
	
	///---Joseph 04/26/07 QA70-9678 ADD_SCRIPT_EXAMPLE_NODE
	if(oDoc.GetString(STR_XF_BOOKMARK_LT_SCRIPT_EXAMPLE, str))
	{
		trInfo = xf_get_help_node(trXF, IDV_HELP_LT_SCRIPT_SAMPLE, nLang);
		
		if(trInfo)	
			trInfo.strVal = str;
		else
			out_str("Fail to find brief node in x-function");
	}
	///---End ADD_SCRIPT_EXAMPLE_NODE
	
	/// Fisher 12/04/08 QA-10236 KEEP_MENU_INFORMATION_AND_BRIEF_INFORMATION_IN_DOC2XF
	/*
	if(oDoc.GetString(STR_XF_BOOKMARK_BRIEF_INFO, str))
	{
		trInfo = xf_get_help_node(trXF, IDV_HELP_DESCRIPTION, nLang);
	
		if(trInfo)
		{	
			string strMenuInfo, strBriefInfo;
			string strCombineBrief;
			
			///justin 2007-03-09 FIX_THE_BUG_THAT_DOES_NOT_GET_MENU_INFO_FROM_DOC
			//xf_seperate_description(trInfo.strVal, strMenuInfo, strBriefInfo);
			if(!oDoc.GetString(STR_XF_BOOKMARK_MENU_INFO, strMenuInfo))
				out_str("Fail to find menu info node in x_function");						
			/// End FIX_THE_BUG_THAT_DOES_NOT_GET_MENU_INFO_FROM_DOC			

			xf_combine_description_section(strMenuInfo, str,  strCombineBrief);
			trInfo.strVal = strCombineBrief;
		}
		else
			out_str("Fail to find brief info node in x_function");
	}
	*/
	/// End KEEP_MENU_INFORMATION_AND_BRIEF_INFORMATION_IN_DOC2XF
	
	
	///End ADD_MENU_INFO
	///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT added IDV_HELP_PARAMETERS, STR_XF_BOOKMARK_PARAMETERS below
	// //summary, example, reference and algorithm and parameters
	// vector<int> vnHelpIDs={IDV_HELP_SUMMARY, IDV_HELP_EXAMPLE, IDV_HELP_REF, IDV_HELP_ALGORITHM, IDV_HELP_PARAMETERS};
	// vector<string> vsHelpBookMarks={STR_XF_BOOKMARK_SUMMARY, STR_XF_BOOKMARK_EXAMPLE, STR_XF_BOOKMARK_REF, STR_XF_BOOKMARK_ALGORITHM, STR_XF_BOOKMARK_PARAMETERS};
	// end ADD_PARAMETERS_NODE_TO_XFT
	/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
	bool	bPartialContent = XF2DOC_PARTIAL_CONTENT & dwOptions;
	vector<char> vcVals;
	if ( !bPartialContent )
	{
	/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS		
		for(int ii=0; ii<s_vnHelpIDs.GetSize(); ii++)
		{
			///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT	
			//vcVals.SetSize(0);
			//trInfo = xf.GetHelp(vnHelpIDs[ii], nLang);
			//_set_help_text(trInfo, vcVals);
			
			if( IDV_HELP_PARAMETERS==s_vnHelpIDs[ii] && !bIsOperationBased  )
				continue;
			///end ADD_PARAMETERS_NODE_TO_XFT
			///Joseph 09/21/06 QA70-8349 	MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
			string strInfo;
			oDoc.GetString(s_vsHelpBookMarks[ii], strInfo);
			trInfo = xf_get_help_node(trXF, s_vnHelpIDs[ii], nLang);
			///End MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
			///Joseph 09/21/06 QA70-8349 	MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
			//if(oDoc.GetRichText(vsHelpBookMarks[ii], vcVals))
			strInfo.TrimLeft();
			strInfo.TrimRight();
			if(!strInfo.IsEmpty() && oDoc.GetRichText(s_vsHelpBookMarks[ii], vcVals))
			///End MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
			{
				///DSC 10/27/05 ADD_PARAMETERS_NODE_TO_XFT
				//if( IDV_HELP_PARAMETERS==vnHelpIDs[ii] && !bIsOperationBased  )
				//	vcVals.SetSize(0);
				///end ADD_PARAMETERS_NODE_TO_XFT
				
				/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
				//	trInfo = xf.GetHelp(vnHelpIDs[ii], nLang);
				///Joseph 09/21/06 QA70-8349 	MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
					//trInfo = xf_get_help_node(trXF, vnHelpIDs[ii], nLang);
				///End MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
				/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
				_set_help_text(trInfo, vcVals);
			}
			///Joseph 09/21/06 QA70-8349 	MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
			else
			{
				vcVals.SetSize(0);
				if (trInfo) /// Hong 12/14/07 v8.0768 SIMPLE_FIX_RUNTIME_ERROR, some structure maybe changed, but seem NOT consistent
					trInfo.bVals = vcVals;
			}
			///End MOVE_TABLE_BY_ORDER_REMOVE_EMEPTY_TABLE
			vcVals.SetSize(0);
		}
	} /// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
	
	/// ----AW 11/03/05 ADD_HELP_SCREEN_SHOT
	if ( IDRS_HELP_E == nLang )
	{
		//string strIamgeName = strDocFile.Left(strDocFile.ReverseFind('.')) + STR_IMAGE_FILE_EXT;
	
		if ( oDoc.GetImageFile( vcVals ) )
		{
			/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			//	trInfo = xf.GetHelp(IDV_HELP_SCREEN_SHOT, nLang);
			trInfo = xf_get_help_node(trXF, IDV_HELP_SCREEN_SHOT, nLang);
			/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
			_set_help_text(trInfo, vcVals);
		}
	}
	/// --- END ADD_HELP_SCREEN_SHOT
	
	
	
	/// Iris 10/09/05 ADD_MODIFICATION_LOG
	//modification log
	trInfo = trXF.modificationLog;
	if(	oDoc.GetString(STR_XF_BOOKMARK_MODIFICATION_LOG, str) && trInfo )
	{
		trInfo.strVal = str;
	}
	///end ADD_MODIFICATION_LOG
	
	//---CPY 10/25/05 ADD_RELATED_XF_NODE_FOR_XF_DOC
	if(	oDoc.GetString(STR_XF_BOOKMARK_RELATED_XF, str) && trXF.relatedXF )
		trXF.relatedXF.strVal = str;
	//----

	//error string table
	trInfo = trXF.errmsgCount;
	int nErrorCount= trInfo.nVal;
	if(nErrorCount>0)
	{
		/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//	trInfo = xf.GetHelp(IDV_ERRMSG_LIST, nLang);
		trInfo = xf_get_help_node(trXF, IDV_ERRMSG_LIST, nLang);
		/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		vsVals.SetSize(0);
		vsVals.SetSize(nErrorCount);
		for(int ii=0; ii<vsVals.GetSize(); ii++)
		{
			str = STR_XF_ERRMSG_TABLE_CELL;
			str+=(string)((ii+1)*NUM_ERRMSG_TABLE_COLS);
			if(oDoc.GetString(str, str, false))
				vsVals[ii]=str;
		}
		trInfo.strVals = vsVals;
	}
	oDoc.SaveDoc(strDocFile); ///Joseph 09/27/06  LABEL_CANNOT_CONTAIN_ENTER
	DeleteFile(strTempFile);
	oDoc.CloseDoc();
	return true;
}

/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
//bool update_xf_by_documents(BaseDocument& oDoc, const string& strXFName, const string& strUpdateFileFolder, int nSpecifyLangIndex = LANG_ALL)
bool update_xf_by_documents(BaseDocument& oDoc, const string& strXFName, const string& strUpdateFileFolder, int nSpecifyLangIndex = LANG_ALL, bool bPartialContent = true)
/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
{
	vector<int> vnLang;
	vector<string> vsLang;
	get_xf_language_info(vnLang, vsLang, nSpecifyLangIndex);
	
	string strFile, str;
	if(okutil_find_file_from_map(&strFile, SUPPORTFILE_XF, ORIGIN_PATH_UNDEF, strXFName) == ORIGIN_PATH_UNDEF)
		return out_str("Cannot Find X-Function: "+strXFName);
	
	if(_is_file_read_only(strFile))
	{
		printf("*****\nFail to update this x-function\n");
		printf("Please check out it first: %s\n", strXFName);
		printf("*****\n");
		return false;
	}

	XFunction xf;
	TreeNode trXF;
	//---------- CPY 11/20/07 FORCE_LOAD_XF_WIHTOUT_VALDATA_LOCALIZATION
	//if(!xf.Load(&trXF, strFile, LTXF_BY_FILENAME))
	if(!xf.LoadNoLocalize(&trXF, strFile, LTXF_BY_FILENAME))
	//----------
	{
		printf("err loading %s\n", strFile);
		return false;    
	}
	///Justin 2007-04-10 v8.0597b qa-9585 SKIP_DOCUMENT_IF_NO_NEED
	if(trXF.SkipHelpDoc.nVal)
	{
		printf(_L("X-Function %s is skipped, for it does not need document"), strXFName);
		return true;
	}
	///END SKIP_DOCUMENT_IF_NO_NEED
	//---- CPY 9/20/05 XF_WORD_DOC_LOCATION_ADD_XF_CATEGORY
	string  strFolder = _check_path_XF_category(trXF, strUpdateFileFolder);
	//----
	//string strXFname = xf.GetFunctionName(false);
	///Joseph 09/28/06  FIND_FILE_IN_SUBFOLDER
	//printf("Processing %s... \n", strXFName);
	printf("Processing %s, Folder = %s\n", strXFName, strFolder);
	///End FIND_FILE_IN_SUBFOLDER
	
	/// ----AW 11/03/05 ADD_HELP_SCREEN_SHOT 
	str = oDoc.SetFileName(strFolder + strXFName);
	/// ----END ADD_HELP_SCREEN_SHOT 
	
	for(int jj = 0; jj < vnLang.GetSize(); jj++)
	{
		//open document if exist
		str = get_xf_doc_filename(strFolder, strXFName, vsLang[jj]);
		//------- CPY 9/3/05 MISSING_WORD_DOC_CRASH_COM
		if(!str.IsFile())
		{
			printf("skipping missing file:%s\n", str);
			continue;
		}
		//-------

		///Kevin 09/30/05 ADD_WARNING_MESSAGE_WHEN_OVERWRITE
		int nRet = file_time_compare(str, strFile, LAST_WRITE_TIME);
			
		if( 0 == nRet && (MessageBox( GetWindow(), "XFunction document is newer than the Word document!\r\nDo you want to overwrite the XFunction document?", "Warning!", MB_YESNO | MB_ICONQUESTION | MB_DEFBUTTON2 ) == IDNO) )
		{
			printf("Convert stopped\n");
			continue;
		}

		///End ADD_WARNING_MESSAGE_WHEN_OVERWRITE

		///DG MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN
		if(!_check_xfdoc_checked_out(strXFName, strFolder, vsLang[jj]))
			continue;
		///end MAKE_UNCHECK_OUT_FILE_FAIL_TO_RUN
		/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//	update_xf_by_document(oDoc, xf, trXF, str, vnLang[jj]);
		///Joseph 09/27/06  LABEL_CANNOT_CONTAIN_ENTER	
		//update_xf_by_document(oDoc, trXF, str, vnLang[jj]);	
		/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
		//if(!update_xf_by_document(oDoc, trXF, str, vnLang[jj]))		
		DWORD	dwCtrl = 0;
		if ( bPartialContent )
			dwCtrl |= XF2DOC_PARTIAL_CONTENT;
		if(!update_xf_by_document(oDoc, trXF, str, vnLang[jj], dwCtrl))
		/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
		{
			return false;
		}
		///End LABEL_CANNOT_CONTAIN_ENTER
		/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	}
	
	// XFunctionOrganizer xfo;
	// if(xfo.Save(trXF, strFile))
	if(xf_save(trXF, strFile))	
		out_str(" done!");
	else
		out_str(" failed during saving.");

	return true;
}

/////////////////////////////////////////////////////////////////////////////
//for x-function calling: xf2doc && doc2xf
static string _format_path(const string& strPath)
{
	string str(strPath);
	if("\\"!=str.Right(1))
		str+="\\";
	str.Replace("\\\\", "\\");
	return str;
}

static string _get_format_path(const string& strPath)
{
	string str(strPath);
	//---- CPY 9/20/05 XF_WORD_DOC_LOCATION_ADD_XF_CATEGORY
	//if(str.IsEmpty() || "<>"==str || "<optional>"==str || "<unassigned>"==str)
	///Sophy 4/25/08 ROW_STATS_PUT_RESULTS_COL_TO_BEGINNING_OF_SRC_SHEET
	//int nSpecialType = cvt_str_to_predefined_type(str);
	int nSpecialType = str_to_predefined_type(str);
	///end ROW_STATS_PUT_RESULTS_COL_TO_BEGINNING_OF_SRC_SHEET
	if(str.IsEmpty() || PDS_UNASSIGNED == nSpecialType || PDS_OPTIONAL == nSpecialType)
	//----
		str = STR_DOC_DEFAULT_SAVE_PATH;
	str=_format_path(str);
	return str;
}
//---- CPY 9/20/05 XF_WORD_DOC_LOCATION_ADD_XF_CATEGORY
static string _check_path_XF_category(TreeNode& trXF, const string& strDestPath, bool bWrite = true)
{
	// XFunctionOrganizer xfo;
	// string strCat = xfo.GetCategoryName(trXF);
	string strCat = xf_get_category_name(trXF);
	string str = strDestPath + strCat + "\\";
	if(bWrite)
	{
		if(!CheckMakePath(str))
			out_str("Invalid  folder: " + str);
	}
	return str;
}
//----	

/// Hong 10/09/07 v8.0720 FIX_REDUNDANT_XFHELPID
static bool _is_doc_needed(LPCSTR lpcszXFFile)
{
	XFunction xf;
	TreeNode trXF;    
	if ( !xf.Load(&trXF, lpcszXFFile, LTXF_BY_FILENAME ))
		return false;
	
	if ( !trXF.SkipHelpDoc )
		return true;
	
	return trXF.SkipHelpDoc.nVal ? false : true;
}
/// end FIX_REDUNDANT_XFHELPID

bool create_all_xf_docs(const string& strJunk, const int& nlanguage, const string& strFolder, bool bCHMDoc=false)
{
	string strPath(_get_format_path(strFolder));
	if(!CheckMakePath(strPath))
	{
		out_str("Invalid saving folder: "+strPath);
		return false;
	}
	
	/// Iris 12/15/05 ADD_PROCESSBAR_FOR_ALL_XF  Erica suggested
	if( IDNO == MessageBox( GetWindow(),"Writing all x-functions to documents may take over an hour. Continue?", "Warning!" , MB_YESNO))
		return true; //cancel by user, no error, so return true
	///End ADD_PROCESSBAR_FOR_ALL_XF

	XFWord oWord(false);	//default, not in debug mode
	if(!oWord.IsValid())
	{
		return false;
	}
	
	vector<string> vsNames, vsFiles;
	
	/// AW 09/15/06 MAKE_HELP_ID_FOR_XF_CHM
	//int nNumFiles = okutil_find_files_from_map(&vsNames, &vsFiles, SUPPORTFILE_XF);
	int nNumFiles = okutil_find_files_from_map(&vsNames, &vsFiles, SUPPORTFILE_XF, FF_USE_C_NAMES);	
	HelpIDFile xfHelpIDFile(XF_HELP_ID_FILE, XF_HELP_START_BEGIN);
	if ( !xfHelpIDFile.IsOpen() )
	{
		return -1;
	}
	/// END MAKE_HELP_ID_FOR_XF_CHM
	
	/// Iris 12/15/05 ADD_PROCESSBAR_FOR_ALL_XF  Erica suggested
	progressBox proBar("Press Cancel button to cancel");
	proBar.SetRange(0, vsFiles.GetSize());
	///End ADD_PROCESSBAR_FOR_ALL_XF
	
	bool bRet=true;
	for(int nf = 0; nf < vsFiles.GetSize(); nf++)
	{
		/// Iris 12/15/05 ADD_PROCESSBAR_FOR_ALL_XF  Erica suggested
		if(proBar.Set(nf))
		{
			string str;
			str.Format("Writting %s document: ", GetFileName(vsFiles[nf], true));
			proBar.SetText(str, PBOXT_TITLE);
		}
		else
			return true; //abort by user clicking Cancel button, so return true here
		///End ADD_PROCESSBAR_FOR_ALL_XF
		
		/// AW 09/15/06 MAKE_HELP_ID_FOR_XF_CHM
		if ( _is_doc_needed(vsFiles[nf]) ) /// Hong 10/09/07 v8.0720 FIX_REDUNDANT_XFHELPID
			xfHelpIDFile.AddHelpID(vsNames[nf], nf);
		/// END MAKE_HELP_ID_FOR_XF_CHM

		bRet&=create_xf_documents(oWord, vsFiles[nf], strPath, nlanguage, bCHMDoc);
	}
	return bRet;
}
///Joseph 11/06/06	 SUPPORT_FOLDER_AND_MATCH_ON_CREATE_DOC
//bool create_doc(const string& strXFName, const int& nlanguage, const string& strFolder, bool bCHMDoc=false)
bool create_doc(const string& strXFName, const string& strCategory, const int& nlanguage, const string& strFolder, bool bCHMDoc=false)
///End SUPPORT_FOLDER_AND_MATCH_ON_CREATE_DOC
{
	///Joseph 01/22/07 SUPPORT_BLANK_XF_NAME
	string strTempXFName = strXFName;
	strTempXFName.Replace(" ", "");
	///End SUPPORT_BLANK_XF_NAME
	string strPath(_get_format_path(strFolder));
	if(!CheckMakePath(strPath))
	{
		out_str("Invalid saving folder: "+strPath);
		return false;
	}
	
	XFWord oWord(false);	//default, not in debug mode
	if(!oWord.IsValid())
	{
		return false;
	}
	///Joseph 11/06/06	 SUPPORT_FOLDER_AND_MATCH_ON_CREATE_DOC
	vector<string> vsNames, vsWholeNames, vsWholeFiles, vsFiles;
	int nWholeFileNum;
	nWholeFileNum = okutil_find_files_from_map(&vsWholeNames, &vsWholeFiles, SUPPORTFILE_XF, FF_USE_C_NAMES);
	
	//vsFiles = vsWholeFiles;
	//vsNames = vsWholeNames;
	strCategory.MakeLower();
	if(strCategory.IsEmpty())
	{
		vsFiles = vsWholeFiles;
		vsNames = vsWholeNames;
	}
	else
	{
		int nCateLength = strCategory.GetLength();
		string strCurrentFile;
		int nIndex;
		for(int ii= 0; ii < nWholeFileNum; ii++)
		{
			strCurrentFile = vsWholeFiles[ii];
			strCurrentFile.TrimRight(vsWholeNames[ii] + ".OXF");
			strCurrentFile.MakeLower();
			nIndex = strCurrentFile.Find(strCategory);
			if(nIndex >= 0)
			{
				vsFiles.Add(vsWholeFiles[ii]);
				vsNames.Add(vsWholeNames[ii]);
			}
		}
	}

	
	vsWholeFiles.SetSize(0);			
	vsWholeNames.SetSize(0);
	vector<string> vsCurrentFiles;
	nWholeFileNum = vsFiles.GetSize();
	
	///Joseph 01/22/07 SUPPORT_BLANK_XF_NAME
	//if(strXFName.IsEmpty())
	if(strTempXFName.IsEmpty())
	///End SUPPORT_BLANK_XF_NAME
		return false; //vsCurrentFiles = vsFiles;  //justin 2007-03-21 DON'T_CREATE_ALL_DOCUMENT_IF_EMPTY_XFNAME
	else
	{
		for(int ii = 0; ii < nWholeFileNum; ii++)
		{
			///Joseph 01/22/07 SUPPORT_BLANK_XF_NAME
			//if(vsNames[ii].Match(strXFName))
			if(vsNames[ii].Match(strTempXFName))
			///End SUPPORT_BLANK_XF_NAME
				vsCurrentFiles.Add(vsFiles[ii]);
		}
	}
	
	//for(int ii = 0; ii < nWholeFileNum; ii++)
	//{
		//if(strXFName.IsEmpty() && vsNames[ii].Match(strXFName))
			//vsCurrentFiles.Add(vsFiles[ii]);
		//else
			//vsCurrentFiles.Add
	//}
	//string strOXF;
	//if(okutil_find_file_from_map(&strOXF, SUPPORTFILE_XF, ORIGIN_PATH_UNDEF, strXFName) == ORIGIN_PATH_UNDEF)
	//{
		//return out_str("Cannot Find X-Function: "+strXFName);
	//}
	int nCurrentFileNum = vsCurrentFiles.GetSize();
	if(nCurrentFileNum == 0)
		return out_str("Cannot Find X-Function ");
	for(int ii = 0; ii < nCurrentFileNum; ii++)
	{
		string strCurrent = vsCurrentFiles[ii];
		if(!create_xf_documents(oWord, strCurrent, strFolder, nlanguage, bCHMDoc))
			return false;
	}
		return true;
	//return create_xf_documents(oWord, strOXF, strPath, nlanguage, bCHMDoc);
	///End SUPPORT_FOLDER_AND_MATCH_ON_CREATE_DOC
}

/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
//bool update_xf(const string& strXFName, const int& nlanguage, const string& strFolder)
bool update_xf(const string& strXFName, const int& nlanguage, const string& strFolder, bool bParitalContent)
/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
{
	string strPath(_get_format_path(strFolder));
	if(!strPath.IsPath())
	{
		out_str("Invalid path: "+strPath);
		return false;
	}
	
	XFWord oWord(false);	//default, not in debug mode
	if(!oWord.IsValid())
	{
		return false;
	}
	/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
	//return update_xf_by_documents(oWord, strXFName, strPath, nlanguage);
	return update_xf_by_documents(oWord, strXFName, strPath, nlanguage, bParitalContent);
	/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
}

/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
//bool update_xfs(const string& strJunk, const int& nlanguage, const string& strFolder)
bool update_xfs(const string& strJunk, const int& nlanguage, const string& strFolder, bool bParitalContent)
/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
{
	string strPath(_get_format_path(strFolder));
	if(!strPath.IsPath())
	{
		out_str("Invalid path: "+strPath);
		return false;
	}
	
	XFWord oWord(false);	//default, not in debug mode
	if(!oWord.IsValid())
	{
		return false;
	}
	///Joseph 09/28/06  FIND_FILE_IN_SUBFOLDER
	vector<string> vsFiles;
	StringArray subFolders;
	int nFolderNum = okutil_find_subfolders(&subFolders, strPath, MaxSubFolderLevel); //5 is the max level of the subfolder
	for(int tt = 0; tt< nFolderNum; tt++)
	{
		vector<string> vsTempFiles;
		subFolders[tt] = strPath + subFolders[tt];
		FindFiles(vsTempFiles, subFolders[tt], "doc");
		vsFiles.Append(vsTempFiles);
	}
	if(vsFiles.GetSize() <= 0)
 	//if(!FindFiles(vsFiles, strPath, "doc"))
 	///End FIND_FILE_IN_SUBFOLDER
	{
		out_str("Fail to find updated file in this folder: "+strFolder);
		return false;
	}
	
	//get the document xf name, (remove the language info and remove duplicate)
	string str;
	vsFiles.Sort();
	for(int ii=0; ii<vsFiles.GetSize(); ii++)
	{
		str=get_xf_name(vsFiles[ii]);
		if(-1!=vsFiles.Find(str))
			vsFiles.RemoveAt(ii--);
		else
			vsFiles[ii]=str;
	}
	
	bool bRet=true;
	for(ii=0; ii<vsFiles.GetSize(); ii++)
	{
		/// Hong 23/05/08 QA80-11565 DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
		//bRet&=update_xf_by_documents(oWord, vsFiles[ii], strPath, nlanguage);
		bRet &= update_xf_by_documents(oWord, vsFiles[ii], strPath, nlanguage, bParitalContent);
		/// end DOC2XF_ALLOW_SKIP_CONTENTS_LIKE_PARAMETERS
	}
	return bRet;
}

bool display_xf_help(const BaseDocument& oDoc, const string& strXFName, const int& nlanguage)
{
	string strOXF, strJunk;
	if(okutil_find_file_from_map(&strOXF, SUPPORTFILE_XF, ORIGIN_PATH_UNDEF, strXFName) == ORIGIN_PATH_UNDEF)
	{
		return out_str("Cannot Find X-Function: "+strXFName);
	}
	
	vector<int> vnLang;
	vector<string> vsLang;
	get_xf_language_info(vnLang, vsLang, nlanguage);
	
	XFunction xf;
	TreeNode trXF; 
	//---------- CPY 11/20/07 FORCE_LOAD_XF_WIHTOUT_VALDATA_LOCALIZATION
	//if(!xf.Load(&trXF, strOXF, LTXF_BY_FILENAME))
	if(!xf.LoadNoLocalize(&trXF, strOXF, LTXF_BY_FILENAME))
	//----------
	{
		printf("err loading %s\n", strOXF);
		return false;    
	}
	
//	XFWord oDoc(true);	//Prepare TXControl
	if(!oDoc.IsValid())
	{
		return false;
	}
	DWORD dwOptions=XF2DOC_CLEAR_EMPTY;
	for(int jj = 0; jj < 1; jj++)
	{
		/// YuI 01/31/06 DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
		//	create_xf_document(oDoc, xf, trXF, strJunk, vnLang[jj], dwOptions);
		create_xf_document(oDoc, trXF, strJunk, vnLang[jj], dwOptions, xf.IsInternal());
		/// end DOCUMENT_FUNCTIONS_SHOULD_DEAL_WITH_TREE_ONLY
	}
	return true;
}
void testxf()
{
	XFWord oDoc(true);	//Prepare TXControl
	string str("smooth");
	display_xf_help(oDoc, str, 1);
	
}

//----- CPY 10/1/07 REMOVE_DETAILED_HELP_FROM_XF
/* 
/// Hong 09/25/07 v8.0708 XFDOC_REDUCE_SIZE_BY_REMOVE_NONGUI_HELP_INFO
bool clean_xf_doc(LPCSTR lpcszFileName)
{
	if ( _is_file_read_only(lpcszFileName) )
		return false;
	
	WordDocument oDoc(false);	//default, not in debug mode

	if(!oDoc.IsValid())
	{
		return false;
	}
	
	if ( !oDoc.OpenDoc(lpcszFileName) )
		return false;
	
	for ( int ii = 0; ii < vsHelpBookMarks.GetSize(); ii++)
	{				
		oDoc.CleanString(vsHelpBookMarks[ii]);
		
	}
		
	oDoc.SetDebugMode(true);	//after running, enable document event
	
	return oDoc.CloseDoc(true);	
}

bool clean_all_xf_docs(LPCSTR lpcszFolder)
{
	string strPath(_get_format_path(lpcszFolder));
	if (!CheckMakePath(strPath))
	{
		printf(_L("Invalid saving folder: %s"),strPath);
		return false;
	}	
	
	vector<string> vsFiles, vsSubfolders;
	okutil_find_subfolders(&vsSubfolders, strPath, MaxSubFolderLevel); //5 is the max level of the subfolder
	for (int ii = 0; ii< vsSubfolders.GetSize(); ii++)
	{
		vector<string> vsTempFiles;
		vsSubfolders[ii] = strPath + vsSubfolders[ii];
		FindFiles(vsTempFiles, vsSubfolders[ii], "doc");
		for (int jj = 0; jj < vsTempFiles.GetSize(); jj++)
			vsTempFiles[jj] = vsSubfolders[ii] + "\\" + vsTempFiles[jj];
		vsFiles.Append(vsTempFiles);
	}
	
	if (vsFiles.GetSize() <= 0)
 	{
		printf(_L("Fail to find updated file in this folder:%s"), lpcszFolder);
		return false;
	}
	
	bool bRet=true;
	for (ii = 0; ii < vsFiles.GetSize(); ii++)
	{
		bRet &= clean_xf_doc(vsFiles[ii]);		
	}
	
	return bRet;
}

void _test1()
{
	clean_xf_doc("C:\\xfdoc\\Miscellaneous\\xf2doc_English.doc");
}

void _test2()
{
	clean_all_xf_docs("C:\\xfdoc");
}
/// end XFDOC_REDUCE_SIZE_BY_REMOVE_NONGUI_HELP_INFO*/

///CPY I conditionally removed help nodes, so just need to load each XF and resave it
//
enum {
	CC_XFNAME,
	CC_FULLPATH,
	CC_CATEGORY,
	CC_OLD_SIZE,
	CC_NEW_SIZE,
	CC_TOTAL,
};
static BOOL _clean_one_XF(LPCSTR lpcszFullpath)
{
	XFunction xf;
	Tree trXF;
	//---------- CPY 11/20/07 FORCE_LOAD_XF_WIHTOUT_VALDATA_LOCALIZATION
	//if ( xf.Load(&trXF, lpcszFullpath, LTXF_BY_FILENAME) )
	if ( xf.LoadNoLocalize(&trXF, lpcszFullpath, LTXF_BY_FILENAME) )
	//----------
	{
		// do any other changes to trXF
		return xf_save(trXF, lpcszFullpath);
	}
	return false;
}
void clean_all_XF_remove_docs(int nLocation = USER_FOLDER)
{
	DWORD dwUsgCntxt = IDXF_USGCTXT_LABTALK;
	vector<string> vsNames, vsFiles;
	int nFiles = okutil_find_files_from_map(&vsNames, &vsFiles, SUPPORTFILE_XF, 0, &dwUsgCntxt, 1, NULL, NULL, nLocation);
	if(nFiles <= 0)
		return;
	
	Worksheet wks;
	wks.Create();
	//name, path, Category, old size, new size
	wks.SetSize(-1, CC_TOTAL);
	Column cn = wks.Columns(CC_XFNAME);
	Column cp = wks.Columns(CC_FULLPATH);
	Column cc = wks.Columns(CC_CATEGORY);
	Column cos = wks.Columns(CC_OLD_SIZE);
	Column cns = wks.Columns(CC_NEW_SIZE);
	
	cn.SetLongName("XF Name");
	cp.SetLongName("Full Path");
	cc.SetLongName("Category");
	cos.SetLongName("Old Size");
	cns.SetLongName("New Size");
	
	int nPathType;
	string strCat;
	for(int ii = 0; ii < nFiles; ii++)
	{
		string strName = okutil_separate_composite_name(vsNames[ii], &nPathType, &strCat);
		wks.SetCell(ii, CC_XFNAME, strName);
		wks.SetCell(ii, CC_FULLPATH, vsFiles[ii]);
		wks.SetCell(ii, CC_CATEGORY, strCat);
		wks.SetCell(ii, CC_OLD_SIZE, GetFileSize(vsFiles[ii]));
		
		DWORD	dwAttributes = GetFileAttributes(vsFiles[ii]);
		if(dwAttributes & FILE_ATTRIBUTE_READONLY) 
			wks.SetCell(ii, CC_NEW_SIZE, "ReadOnly");
		else
		{
			if(_clean_one_XF(vsFiles[ii]))
				wks.SetCell(ii, CC_NEW_SIZE, GetFileSize(vsFiles[ii]));
			else
				wks.SetCell(ii, CC_NEW_SIZE, "Failed");
		}
	}
}

