/*------------------------------------------------------------------------------*
 * File Name: sys_utils.h				 										*
 * Creation: CPY 3/13/02														*
 * Purpose: Basic and common utilities for general Origin C development.		*
 * Copyright (c) OriginLab Corp.	2002, 2003, 2004, 2005, 2006, 2007			*
 * All Rights Reserved															*
 * 																				*
 * Modification Log:															*
 * EJP 07-10-2003 v7.0622 QA70-4745 SET_PAGE_IMPORT_INFO_ON_123_ASC_IMPORT		*
 *------------------------------------------------------------------------------*/

#ifndef _SYS_UTILS_H
#define _SYS_UTILS_H

// Included files
#include <stdio.h>           // IO functions and string.h
#include <OC_const.h>        // MAXFULLPATH
#include <math.h>            // Mathematical functions
#include <utilities.h>       // LT_ functions
#include <complex.h>		 // For implementing the Re, Im, and Conj functions
#include <mswin.h>           // Windows API functions
#include <page.h>			 // GraphPage class

// Enumerated definitions
typedef enum { FDLOG_ORIGIN = 1, FDLOG_EXCEL, FDLOG_TEMPLATE, FDLOG_ASCII, FDLOG_LOTUS, FDLOG_IMPORT_EXCEL,
	FDLOG_DBASE, FDLOG_DIF, ORIGIN_LABTECH, FDLOG_SOUND, FDLOG_MATHEMATICA, FDLOG_KALEIDAGRAPH,
	FDLOG_IMAGE, FDLOG_CSV, FDLOG_PCLAMP, FDLOG_SCRIPT, FDLOG_NOTES, FDLOG_EDITOR, FDLOG_SIGMA_PLOT,
	FDLOG_ODAQ, FDLOG_THERMO_GALACTIC_SPC, FDLOG_MINI_TAB,
	FDLOG_FILTER_ASCII=10000, FDLOG_FILTER_BINARY, FDLOG_FILTER_USERDEFINED } FDLogUseGroup;
	 
typedef enum { FDLOG_TYPE_SAVE_AS = 0, FDLOG_TYPE_OPEN_SINGLE, FDLOG_TYPE_OPEN_MULTISEL,
	FDLOG_TYPE_MULTI_OPEN } FDLogDialogType;

// FDLog Multi-Selection/Multi-Open options
#define FDLOG_MULTI_OPEN_MULTI_SELECTION_ONLY	-1
#define FDLOG_MULTI_OPEN_SHOW_COL_DESIG			1
#define FDLOG_MULTI_OPEN_SHOW_TEMPLATE			2
#define FDLOG_MULTI_OPEN_SHOW_FILE_SIZE			4
#define FDLOG_MULTI_OPEN_SHOW_MODIFY			8

// Function prototypes
/** >User Interface Controls
		Open an FDLog Browse (OpenPath) dialog box.
	Example:
		string strPath;
		strPath = BrowseGetPath();                                      // or
		strPath = BrowseGetPath( "C:\\Program Files\\" );               // or
		strPath = BrowseGetPath( GetAppPath() + "OriginC\\", "Browse" );
	Parameters:
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking  
		lpcszDialogName=Title of the dialog box, default NULL uses "Open" 
	Return:
		Returns the path browsed to or an empty string if Cancel button in dialog
		box is clicked.
*/
string BrowseGetPath( LPCSTR lpcszPath = NULL, LPCSTR lpcszDialogName = NULL );

/** >User Interface Controls
		Open an FDLog Open dialog box passing the file types to list in an array
		of strings.
	Example:
		string strPath;
		StringArray saFiletypes;
		saFiletypes.SetSize( 3 );
		saFiletypes[0]="[Project (*.OPJ)] *.OPJ";
		saFiletypes[1]="[Old version (*.ORG)] *.ORG";
		saFiletypes[2]="[Worksheets (*.OGW)] *.OGW";
		strPath = GetOpenBox( saFiletypes ); // or
		//strPath = GetOpenBox( saFiletypes, "C:\\Program Files\\" ); // or
		//strPath = GetOpenBox( saFiletypes, "C:\\Program Files\\", "Origin" ); // or
		//strPath = GetOpenBox( saFiletypes, "C:\\Program Files\\", "Origin", "OpenOPJ" );
		if( strPath.IsEmpty() )
			out_str( "User has cancelled the Open dialog box." );
		else
			printf( "The file chosen is %s\n.", strPath );
	Parameters:
		saFiletypes=Vector containing file types to list in the dialog box, each element
			of vector must follow syntax of LabTalk FDLog.TypeN$ object property
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Initial filename when dialog opens, default NULL uses an empty string 
		lpcszDialogName=Title of the dialog box, default NULL uses "Open" 
	Return:
		Returns the path and filename of a selecetd file or an empty string if Cancel button
		in dialog box is clicked.
*/
string GetOpenBox( StringArray &saFiletypes, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL );

/** >User Interface Controls
		An FDLog.UseGroup version of GetOpenBox that uses an enumerated FDLog.UseGroup
		code to indicate the set of file types to list. See sys_utils.h or the Origin.ini
		file for a list of the enumerated FDLOG.UseGroup codes.
	Example:
		string strPath;
		strPath = GetOpenBox( FDLOG_ORIGIN ); // or
		//strPath = GetOpenBox( FDLOG_EXCEL, "C:\\Program Files\\" ); // or
		//strPath = GetOpenBox( FDLOG_ASCII, "C:\\Program Files\\", "Origin" ); // or
		//strPath = GetOpenBox( FDLOG_SCRIPT, "C:\\Program Files\\", "Origin", "OpenOGS" );
		if( strPath.IsEmpty() )
			out_str( "User has cancelled the Open dialog box." );
		else
			printf( "The file chosen is %s\n.", strPath );
	Parameters:
		nFDLogUseGroup=A LabTalk FDLog.UseGroup code as enumerated in sys_utils.h and in
			the Origin.ini file
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Initial filename when dialog opens, default NULL uses an empty string
		lpcszDialogName=Title of the dialog box, default NULL uses "Open"
	Return:
		Returns the path and filename of a selected file or an empty string if Cancel button
		in dialog box is clicked.
*/
string GetOpenBox( FDLogUseGroup nFDLogUseGroup, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL );

/** >User Interface Controls
		An easier to use version of GetOpenBox that works for a single file type.
	Example:
		string strPath;
		strPath = GetOpenBox(); // or
		//strPath = GetOpenBox( "[Old version (*.ORG)] *.ORG" ); // or
		//strPath = GetOpenBox( "*.OPJ"); // or
		//strPath = GetOpenBox( "*.ocw Workspace", GetAppPath() + "OriginC\\" ); // or
		//strPath = GetOpenBox( "*.ocw Workspace", GetAppPath() + "OriginC\\", "Origin" ); // or
		//strPath = GetOpenBox( "*.ocw Workspace", "C:\\Program Files\\", "Origin", "Open Workspace" );
		if( strPath.IsEmpty() )
			out_str( "User has cancelled the Open dialog box." );
		else
			printf( "The file chosen is %s\n.", strPath );
	Parameters:
		lpcszFileType="*.ext description", or "[decription (*.ext)] *.ext", or just "*.ext"
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Initial filename when dialog opens, default NULL uses an empty string
		lpcszDialogName=Title of the dialog box, default NULL uses "Open"
	Return:
		Returns the path and filename of a selecetd file or an empty string if Cancel button
		in dialog box is clicked.
*/
string GetOpenBox( LPCSTR lpcszFileType = "*.* All Files", LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL );

/** >User Interface Controls
		Open an FDLog SaveAs dialog box passing the file types to list in an array
		of strings.
	Example:
		string strPath;
		StringArray saFiletypes;
		saFiletypes.SetSize( 3 );
		saFiletypes[0]="[Project (*.OPJ)] *.OPJ";
		saFiletypes[1]="[Old version (*.ORG)] *.ORG";
		saFiletypes[2]="[Worksheets (*.OGW)] *.OGW";
		strPath = GetSaveAsBox( saFiletypes ); // or
		//strPath = GetSaveAsBox( saFiletypes, "C:\\Program Files\\" ); // or
		//strPath = GetSaveAsBox( saFiletypes, "C:\\Program Files\\", "Origin" ); // or
		//strPath = GetSaveAsBox( saFiletypes, "C:\\Program Files\\", "Origin", "SaveAsOPJ" );
		if( strPath.IsEmpty() )
			out_str( "User has cancelled the SaveAs dialog box." );
		else
			printf( "The file chosen is %s\n.", strPath );
	Parameters:
		saFiletypes=Vector containing file types to list in the dialog box, each element
			of vector must follow syntax of LabTalk FDLog.TypeN$ object property
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Initial filename when dialog opens, default NULL uses an empty string 
		lpcszDialogName=Title of the dialog box, default NULL uses "SaveAs" 
	Return:
		Returns the path and filename of a selecetd file or an empty string if Cancel button
		in dialog box is clicked.
*/
string GetSaveAsBox( StringArray &saFiletypes, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL );

/** >User Interface Controls
		An FDLog.UseGroup version of GetSaveAsBox that uses an enumerated FDLog.UseGroup
		code to indicate the set of file types to list. See sys_utils.h or the Origin.ini
		file for a list of the enumerated FDLOG.UseGroup codes.
	Example:
		string strPath;
		strPath = GetSaveAsBox( FDLOG_ORIGIN ); // or
		//strPath = GetSaveAsBox( FDLOG_EXCEL, "C:\\Program Files\\" ); // or
		//strPath = GetSaveAsBox( FDLOG_ASCII, "C:\\Program Files\\", "Origin" ); // or
		//strPath = GetSaveAsBox( FDLOG_SCRIPT, "C:\\Program Files\\", "Origin", "SaveAsOGS" );
		if( strPath.IsEmpty() )
			out_str( "User has cancelled the SaveAs dialog box." );
		else
			printf( "The file chosen is %s\n.", strPath );
	Parameters:
		nFDLogUseGroup=A LabTalk FDLog.UseGroup code as enumerated in sys_utils.h and in
			the Origin.ini file
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Initial filename when dialog opens, default NULL uses an empty string
		lpcszDialogName=Title of the dialog box, default NULL uses "SaveAs"
	Return:
		Returns the path and filename of a selected file or an empty string if Cancel button
		in dialog box is clicked.
*/
string GetSaveAsBox( FDLogUseGroup nFDLogUseGroup, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL );

/** >User Interface Controls
		An easier to use version of GetSaveAsBox that works for a single file type.
	Example:
		string strPath;
		strPath = GetSaveAsBox(); // or
		//strPath = GetSaveAsBox( "[Old version (*.ORG)] *.ORG" ); // or
		//strPath = GetSaveAsBox( "*.OPJ"); // or
		//strPath = GetSaveAsBox( "*.ocw Workspace", GetAppPath() + "OriginC\\" ); // or
		//strPath = GetSaveAsBox( "*.ocw Workspace", GetAppPath() + "OriginC\\", "Origin" ); // or
		//strPath = GetSaveAsBox( "*.ocw Workspace", "C:\\Program Files\\", "Origin", "SaveAs Workspace" );
		if( strPath.IsEmpty() )
			out_str( "User has cancelled the SaveAs dialog box." );
		else
			printf( "The file chosen is %s\n.", strPath );
	Parameters:
		lpcszFileType="*.ext description", or "[decription (*.ext)] *.ext", or just "*.ext"
		lpcszPath=Initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Initial filename when dialog opens, default NULL uses an empty string
		lpcszDialogName=Title of the dialog box, default NULL uses "SaveAs"
	Return:
		Returns the path and filename of a selecetd file or an empty string if Cancel button
		in dialog box is clicked.
*/
string GetSaveAsBox( LPCSTR lpcszFileType = "*.* All Files", LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL );

/** >Mathematical
		This function is essentially the same as the rnd() function
	Parameters:
		nSeed = (optional) pass any nonzero value to set the seed for random number generation, or 0
				to use the current seed.
	Returns:
		A uniformly random number between 0. and 1.
	Example:
		// The example displays 10 random numbers between 0. and 1.
		void	run_rnd()
		{
			for (int ii = 0; ii < 10; ii++)
			{
				double	rr = ran();
				out_double("value = ", rr);
			}
		}
*/
double ran(int nSeed = 0);

/** >System
		Get the text data copied onto the clipboard.
	Example:
		string strClipboardText;
		BOOL bSuccess;
		bSuccess = GetClipboardText( strClipboardText );
		if( bSuccess )
			out_str( strClipboardText );
		else
			out_str( "Error reading Clipboard or Clipboard is empty." );
	Parameters:
		strData = Output text copied from clipboard
	Return:
		Returns TRUE and a string containing text copied onto the clipboard
		on success or returns FALSE and an empty string on failure or if
		the Clipboard is empty.
*/
BOOL GetClipboardText( string& strData );

/** >File Management
		This function constructs a temporary file name in the Windows Temp path
	Example:
		string strTempFile;
		if(GetTempFileName(strTempFile,"ABC"))
		{
			printf("You can use this file name as temp file:%s\n", strTempFile);
		}
	Parameters:
		strFile = a string to receive the temp file full path file name
		lpcszPrefix = The function uses the first three characters of this string as the prefix of the file name. 
		If left as NULL, "OTF" will be used. 

	Return:
		TRUE if success, FALSE if not able to fine a temp path.
*/
BOOL GetTempFileName(string &strFile, LPCSTR lpcszPrefix = NULL);

/** >File Management
		Get the file modification date of a file from an input string containing
		a path and filename.
	Example:
		string strFileDate, strDataFile = "C:\\Origin80\\Origin.ini";
		strFileDate = GetFileModificationDate(strDataFile);
	Parameters:
		strPathAndFilename=Input string containing a path and filename with filetype extension
	Return:
		Returns a Windows like file modification date formatted for display. 
*/
string GetFileModificationDate(LPCSTR lpcstrPathAndFilename, WORD wFormat=LDF_SHORT);

/** >File Management
	List all files of a specified file type found in a folder
Example:
	string strExePath = GetAppPath();
	StringArray saResult;
	FindFiles(saResult, strExePath, "otw");
Parameters:
	saResult = the referrence of string array will receive the finding results
	lpcszPath = the file path to search for files
	lpcszExt = the file extension to search for
	bCheckExist = true will check the given saReult to see if the file is already in that array
Return:
	Returns TRUE for success, otherwise failure.
*/	
BOOL FindFiles(StringArray& saResult, LPCSTR lpcszPath, LPCSTR lpcszExt, bool bCheckExist = false);

/** >File Management
	Copy file and also set destination file's attribute
Example:
	string strThemeFile = get_theme_file_name(nSelRow, flx);
	string strPath = GetAppPath();
	strPath += "Deleted";
	if(CheckMakePath(strPath))
	{
		string strTemp = GetFileName(strThemeFile);
		FileCopy(strThemeFile, strPath + "\\" + strTemp);
		DeleteFile(strThemeFile);
		load_themes_to_grid();
	}
		
Parameters:
	lpcszSrc = [in] Pointer to a null-terminated string that specifies the name of an existing file. 
	lpcszDest =	[in] Pointer to a null-terminated string that specifies the name of the new file. 
	dwAttribute = the file attribute to set on the new file lpcszDest
	bSetCurrentTime = set the destination file to the current time or not
Return:
	Returns TRUE for success, otherwise failure.
Remark:
	This function will call CopyFile with default bFailIfExists = FALSE
*/
BOOL FileCopy(LPCSTR lpcszSrc, LPCSTR lpcszDest, DWORD dwAttribute = FILE_ATTRIBUTE_NORMAL, bool bSetCurrentTime = false);

/** >Import Export
	Export a page to an image using settings from a tree node.
Parameters:
	pg = reference to the page to export
	lpcszFileName = pointer to the target file name
	trExport = a tree node containing the export settings
*/
bool export_page(Page &pg, LPCSTR lpcszFileName, const TreeNode &trExport);

/** >Import Export
	Export a page to an image using the page's export settings
Parameters:
	pg = reference to the page to export
	lpcszFileName = pointer to the target file name
	lpcszFormat = pointer to the target format
Return:
	Returns 0 for success, non-zero for error.
Example:
	void run_export_page()
	{
		GraphPage		gp;
		gp.Create();
		if( !gp)
		{
			return;
		}
		
		string strExt("bmp");
		string strImagePath;
		strImagePath = GetAppPath(1) + "Test." + strExt;
		bool bRet = export_page(gp,strImagePath,strExt);	
	}
*/	
bool export_page(Page &pg, LPCSTR lpcszFileName, LPCSTR lpcszFormat = "EPS");

/** >Import Export
	Export a page to an image using current ini settings or prompt user with export options
Parameters:
	lpcszFileName = pointer to the target file name
	lpcszFormat = pointer to the target format
	pg = reference to the page to export
	bShowOptions = TRUE to show the export options dialog, FALSE to use current settings
Return:
	Returns 0 for success, non-zero for error.
Example:
	PageBase pbActive;
	pbActive = Project.Pages();
	string strPgName = pbActive.GetName();
	Page pg(strPgName);
	export_page_to_image( pg, "c:\\test.bmp", "bmp", false);
*/	
bool export_page_to_image(Page &pg, LPCSTR lpcszFileName, LPCSTR lpcszFormat, BOOL bShowOptions=FALSE);

/** >Import Export
	Export a page to an image using the specified settings
Parameters:
	lpcszFileName = pointer to target file name
	lpcszFormat = pointer to target image format
	pg = reference to source page
	nWidth = target image width in pixels.  If nHeight parameter is zero then nWidth specifies dots per inch.
	nHeight = target image height in pixels.  If zero then nWidth specifies dots per inch.
	nBitsOrHeight = target image bits per pixel
	nCompression = target image compression level.  This parameter is ignored by some image formats.
Return:
	Returns TRUE for success, FALSE for failure.
Example:
	void run_export_page_to_image()
	{
		GraphPage gp;
		gp.Create();
		if( !gp )
		{
			return;
		}
		
		string 	strImagePath("C:\\Test.bmp");
		int nRet = export_page_to_image(strImagePath, "bmp", gp, 1029, 789, 8, 0);
	}
*/	
bool export_page_to_image(LPCSTR lpcszFileName, LPCSTR lpcszFormat, Page &pg, int nWidth, int nHeight, int nBitsPerPixel, int nCompression=0);

//------------------- GJL v7.0357 QA70-4078 3/17/03 ORIGINC_MULTI_OPEN_SUPPORT
//////////////////////////////////////////////////////////////////////////////////
/** >User Interface Controls
		Open an FDLog Open dialog box passing the file types to list in an array
		of strings. Optionally uses a simple Open dialog with multiple selection
		enabled or a Multi-Open dialog box.
	Example:
		int iNumSelFiles;
		string strPath;
		StringArray saFiletypes, saFilePaths;
		saFiletypes.SetSize( 3 );
		saFiletypes[0]="[Project (*.OPJ)] *.OPJ";
		saFiletypes[1]="[Old version (*.ORG)] *.ORG";
		saFiletypes[2]="[Worksheets (*.OGW)] *.OGW";
		iNumSelFiles = GetMultiOpenBox( saFilePaths, saFiletypes ); // or
		iNumSelFiles = GetMultiOpenBox( saFilePaths, saFiletypes, "C:\\Program Files\\" ); // or
		iNumSelFiles = GetMultiOpenBox( saFilePaths, saFiletypes, "C:\\Program Files\\", "Origin" ); // or
		iNumSelFiles = GetMultiOpenBox( saFilePaths, saFiletypes, "C:\\Program Files\\", "Origin", "OpenOPJ" ); // or
		iNumSelFiles = GetMultiOpenBox( saFilePaths, saFiletypes, "C:\\Program Files\\", "Origin", "OpenOPJ", true );
	Parameters:
		saFilePaths=Output vector of strings containing path and filename of all selected files
		saFiletypes=Input vector containing file types to list in the dialog box, each element
			of vector must follow syntax of LabTalk FDLog.TypeN$ object property
		lpcszPath=Input initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Input initial filename when dialog opens, default NULL uses an empty string 
		lpcszDialogName=Input title of the dialog box, default NULL uses "Open"
		bMultiSelection=Input flag specifiying to use multi-selection Open (default true) or Multi-Open (false) dialog box
	Return:
		Returns the path and filename of all selected files or an empty string if Cancel button
		in dialog box is clicked. Also returns the number of files selected.
*/
int GetMultiOpenBox( StringArray& saFilePaths, StringArray &saFiletypes, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL, bool bMultiSelection = true );

/**#
		An FDLog.UseGroup version of GetMultiOpenBox that uses an enumerated FDLog.UseGroup
		code to indicate the set of file types to list. See sys_utils.h or the Origin.ini
		file for a list of the enumerated FDLOG.UseGroup codes. Optionally uses a simple
		Open dialog with multiple selection enabled or a Multi-Open dialog box.
	Example:
		int iNumFiles;
		StringArray saFilePaths;
		iNumFiles = GetMultiOpenBox( saFilePaths, FDLOG_ORIGIN ); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, FDLOG_EXCEL, "C:\\Program Files\\" ); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, FDLOG_ASCII, "C:\\Program Files\\", "Origin" ); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, FDLOG_SCRIPT, "C:\\Program Files\\", "Origin", "OpenOGS" );
		iNumFiles = GetMultiOpenBox( saFilePaths, FDLOG_SCRIPT, "C:\\Program Files\\", "Origin", "OpenOGS", false );
	Parameters:
		saFilePaths=Output vector of strings containing path and filename of all selected files
		nFDLogUseGroup=Input LabTalk FDLog.UseGroup code as enumerated in sys_utils.h and in
			the Origin.ini file
		lpcszPath=Input initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Input initial filename when dialog opens, default NULL uses an empty string 
		lpcszDialogName=Input title of the dialog box, default NULL uses "Open"
		bMultiSelection=Input flag specifiying to use multi-selection Open (default true) or Multi-Open (false) dialog box
	Return:
		Returns the path and filename of all selected files or an empty string if Cancel button
		in dialog box is clicked. Also returns the number of files selected.
*/
int GetMultiOpenBox( StringArray& saFilePaths, FDLogUseGroup nFDLogUseGroup, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL, bool bMultiSelection = true);

//////////////////////////////////////////////////////////////////////////////////
/** >User Interface Controls
		An easier to use version of GetMultiOpenBox that works for a single file type.
		Optionally uses a simple Open dialog with multiple selection enabled or a
		Multi-Open dialog box.
	Example:
		int iNumFiles;
		StringArray saFilePaths;
		iNumFiles = GetMultiOpenBox(saFilePaths); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, "[Old version (*.ORG)] *.ORG" ); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, "*.OPJ"); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, "*.ocw Workspace", GetAppPath() + "OriginC\\" ); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, "*.ocw Workspace", GetAppPath() + "OriginC\\", "Origin" ); // or
		iNumFiles = GetMultiOpenBox( saFilePaths, "*.ocw Workspace", "C:\\Program Files\\", "Origin", "Open Workspace", false );
	Parameters:
		saFilePaths=Output vector of strings containing path and filename of all selected files
		lpcszFileType=Input file type string like "*.ext description", "[decription (*.ext)] *.ext", or just "*.ext"
		lpcszPath=Input initial path when dialog opens, default NULL uses FDLog tracking
		lpcszFileName=Input initial filename when dialog opens, default NULL uses an empty string 
		lpcszDialogName=Input title of the dialog box, default NULL uses "Open"
		bMultiSelection=Input flag specifiying to use multi-selection Open (default true) or Multi-Open (false) dialog box
	Return:
		Returns the path and filename of all selected files or an empty string if Cancel button
		in dialog box is clicked. Also returns the number of files selected.
*/
int GetMultiOpenBox( StringArray& saFilePaths, LPCSTR lpcszFileType = NULL, LPCSTR lpcszPath = NULL, LPCSTR lpcszFilename = NULL,
	 LPCSTR lpcszDialogName = NULL, bool bMultiSelection = true );
//------------------- QA70-4078

/**#
		Compute a LabTalk (1 based) index from a C (0 based) index and add an offset.
	Parameters:
		iCindex=Input 0 based C index
		nOffset=Input offset, default is 0
	Return:
		Returns a LabTalk 1 based index with added offset.
*/
int c_index_to_labtalk_index(int iCindex, int nOffset = 0);

/**#
		Compute a C (0 based) index from a LabTalk (1 based) index and add an offset.
	Parameters:
		iLTindex=Input 1 based LabTalk index
		nOffset=Input offset, default is 0
	Return:
		Returns a C 0 based index with added offset.
*/
int labtalk_index_to_c_index(int iLTindex, int nOffset = 0);



/**#
*/
BOOL	worksheets_are_same(Worksheet &wks1, Worksheet &wks2);


/**#
*/
int FDLogInit();

/**#
*/
bool validate_identifier_name(string &strName);

/** >Note Window
*/
bool	get_create_Note(string &strNoteWnd);

/** >Character/String Manipulation
	It appends to the string str the ' ' characters until its size reaches nSize. 

*/
void	append_blanks_to_size(string &str, int nSize);

/// EJP 07-10-2003 v7.0622 QA70-4745 SET_PAGE_IMPORT_INFO_ON_123_ASC_IMPORT
/** >Import Export
	Set the page.info.import properties.
	Parameters:
		pgTarget = reference to the page that will receive the import info
		lpcszFile = pointer to the name of the file imported
		iDataType = the type of data
	Return:
		TRUE for success, FALSE for failure
*/
BOOL set_page_import_info(Page &pgTarget, LPCSTR lpcszFile, int iDataType);
/// end SET_PAGE_IMPORT_INFO_ON_123_ASC_IMPORT

/** >File Management
	Add file extension to given string 
	Parameters:
		strFilename = filename to check and add extension 
		lpcszExt = file extension, without the dot.
	Return:
		true if extension is added, false if filename already has given extension
		
	Example:
		string str = GetAppPath() + "origin.ini";
		bool bRet = add_file_extension(str, "ini");
		ASSERT(!bRet);
		bRet = add_file_extension(str, "txt");
		ASSERT(bRet);
		string strFilename = GetFileName(str);
		ASSERT(strFilename == "origin.ini.txt");
*/
bool add_file_extension(string& strFilename, LPCSTR lpcszExt);

/** >File Management
		Check to find the filename that does not already exist 
	Parameters:
		strFilename = filename to check and update if needed 
		bCheckCreatePath = if path dose not existed, to create or just return false
	Return:
		true strFilename is a good new file name that is not in conflict with existing files
		
	Example:
		string str = GetAppPath() + "origin.ini";
		bool bRet = get_next_file_name(str);
		ASSERT(bRet);
		string strOld = GetAppPath() + "origin.ini";
		ASSERT(strOld != str);// since origin.ini must already existed
*/
bool get_next_file_name(string& strFilename, bool bCheckCreatePath = true);

/** >File Management
		Check to see if specified string is a valid file name, no path is allowed
	Parameters:
		lpcszFilename = filename to check 
	Return:
		true if lpcszFilename is not empty and does not contain illegal characters, return false if lpcszFilename contains path or has other invalid characters for filename
	Example:
		string str = "origin*.ini";
		ASSERT(!is_str_valid_for_filename(str));
		str = "origin.ini";
		ASSERT(is_str_valid_for_filename(str));
		str = GetAppPath() + "origin.ini";
		ASSERT(str.IsFile());
		ASSERT(!is_str_valid_for_filename(str));
		
		ASSERT(!is_str_valid_for_filename("abc?ef"));
		ASSERT(is_str_valid_for_filename("abcef"));
*/
bool is_str_valid_for_filename(LPCSTR lpcszFilename);

/** >Font
		Get system font name
	Example:
		void show_sys_fonts()
		{
			vector<string> vsNames = {
				"SYSTEM_FONT", "DEVICE_DEFAULT_FONT", "DEFAULT_GUI_FONT", "ANSI_VAR_FONT", "OEM_FIXED_FONT",
				"ANSI_FIXED_FONT", "SYSTEM_FIXED_FONT"};
			vector<int> vnIDs = {
				SYSTEM_FONT, DEVICE_DEFAULT_FONT, DEFAULT_GUI_FONT, ANSI_VAR_FONT, OEM_FIXED_FONT, 
				ANSI_FIXED_FONT, SYSTEM_FIXED_FONT};
				
			printf("%20s\t%s\n", "Font", "Font Face");
			out_str("-------------------------------------");
			for(int ii = 0; ii < vsNames.GetSize(); ii++)
				printf("%20s\t%s\n", vsNames[ii], get_system_font_name(vnIDs[ii]));
		}
		
	Parameters:
		nType = OEM_FIXED_FONT, SYSTEM_FONT etc const, can also pass in GSFI_TYPE_DEFAULT, GSFI_TYPE_FIXED_WIDTH, GSFI_TYPE_SCALABLE for Origin fonts
	Return:
		name of the specified font type, or an empty string if specified type is not valid
*/
string get_system_font_name(int nType = ANSI_VAR_FONT, int* lpnCharSet = NULL);

/** >System
		Test Windows version to see if it is Windows 2000 or later
	Parameters:
		bAndLater = false if you need to test to see if OS is exactly Windows 2000
	Return:
		TRUE or FALSE
*/
bool is_win2k(bool bAndLater = true);

#endif //_SYS_UTIL_H
