﻿
/*************************************************************************
*
* ADOBE CONFIDENTIAL
* ___________________
*
*  Copyright 2011 Adobe Systems Incorporated
*  All Rights Reserved.
*
* NOTICE:  All information contained herein is, and remains
* the property of Adobe Systems Incorporated and its suppliers,
* if any.  The intellectual and technical concepts contained
* herein are proprietary to Adobe Systems Incorporated and its
* suppliers and may be covered by U.S. and Foreign Patents,
* patents in process, and are protected by trade secret or copyright law.
* Dissemination of this information or reproduction of this material
* is strictly forbidden unless prior written permission is obtained
* from Adobe Systems Incorporated.
*
* $DateTime:  $
*
* Adobe Output Module 4.0
*
* MediaGallery Originally Written by Quality Process Incorporated, Enhanced by
* Adobe Systems China. Contact Sheet written by Adobe Systems China.
* 
*
**************************************************************************/

/**
  * Paths class
  * Define application program pathes
  *
  *  @Date: 2008-1-7
*/
AOM.CS = {};

AOM.CS.Paths = function() {};

AOM.CS.Paths.mainApp = AOM.Paths.project + "/";
AOM.CS.Paths.app = AOM.CS.Paths.mainApp + "contactsheet/";
AOM.CS.Paths.resources = AOM.CS.Paths.app + "resources/";
AOM.CS.Paths.templates = AOM.CS.Paths.resources + "templates/";
AOM.CS.Paths.scripts = AOM.CS.Paths.resources + "scripts/";
AOM.CS.Paths.images = AOM.CS.Paths.resources + "images/";

//TODO , templately set user path as same as app path
AOM.CS.Paths.user = AOM.Paths.userData + "/";
AOM.CS.Paths.preview = AOM.CS.Paths.user + "preview/";
AOM.CS.Paths.log = AOM.CS.Paths.user + "contactsheet.log";
AOM.CS.Paths.userData = AOM.CS.Paths.user + "ContactSheet/";
AOM.CS.Paths.defaultPersistedUserData = AOM.CS.Paths.resources + "datas/userInputDefault.json";
AOM.CS.Paths.commonTemplateData = AOM.CS.Paths.resources + "datas/templateDefault.json";
AOM.CS.Paths.persistedUserData = AOM.CS.Paths.userData + "userInput.json";
AOM.CS.Paths.customTemplate = AOM.CS.Paths.resources + "datas/customtemplate/";

/**
  * Log class
  * Define Log class
  *
  *  @Date: 2007-1-7
*/


AOM.CS.Log =function() {};

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//if debug is verbose mode, app can write log file, otherwise can not write log file
AOM.CS.Log.debugVerbose = false;

AOM.CS.Log.logFile = undefined;

AOM.CS.Log.checkFolder= function(path) {
	var hasExists = true;
	var folder = new Folder(path);
	
	if (!folder.exists) {
		var hasCreated = folder.create();
		if (!hasCreated) {
			hasExists = false;
		}
	}

	return hasExists;
}

//TODO
AOM.CS.Log.checkFolder(AOM.CS.Paths.user);
AOM.CS.Log.checkFolder(AOM.CS.Paths.userData);

AOM.CS.Log.initializeLogFile = function() {
	if (AOM.CS.Log.debugVerbose == false) return;
	
	this.logFile = new File(AOM.CS.Paths.log);
	
	if (this.logFile == undefined) {
		AOM.alert("Log file cann't be created.");
		return;
	} 
	
	if (this.logFile.open("w")) {
		this.logFile.close();
		return;
	} else {
		AOM.alert("Log file cann't be opened. - " + this.logFile.fsName);
		this.logFile = undefined;
	}
}

//init log file
AOM.CS.Log.initializeLogFile();

AOM.CS.Log.writeLine = function(line)  {
	if (this.logFile == undefined) {
		return;
	}
	if (!this.logFile.open("e")) {
		return;
	}
	this.logFile.seek(0, 2);
	var date = new Date();
	this.logFile.writeln(date.getHours() + ":" + date.getMinutes() + ":" + date.getSeconds() + "	"+ line);
	this.logFile.close();
}

AOM.CS.Log.errorsDetected = false;
AOM.CS.Log.writeError = function (error)
{
	if (AOM.CS.Log.debugVerbose == false)  return ;
	this.writeLine("Error:"  + error);
	AOM.CS.Log.errorsDetected = true;
	return undefined;
}

AOM.CS.Log.writeInfo= function(info) {
	if (AOM.CS.Log.debugVerbose == false)  return ;
		
	this.writeLine("Info:" + info);
	return undefined;
}


AOM.CS.Log.dumpObject = function (object, text)
{
	if (AOM.CS.Log.debugVerbose == false)  return ;
		
	if (object == undefined)
	{
		AOM.CS.Log.writeError("dumpObject - object was undefined");
		return;
	}

	AOM.CS.Log.writeLine(">>>>>dumpObject");

	if (text != undefined)
		AOM.CS.Log.writeLine(text);

	var properties = object.reflect.properties;
	for (var i = 0; i < properties.length; i++)
	{
		if (properties[i] != undefined)
			AOM.CS.Log.writeLine("	" +object.reflect.name + "." + properties[i].name + " == " + object[properties[i].name]);
	}
	var methods = object.reflect.methods;
	for (i = 0; i < methods.length; i++)
	{
		if (methods[i] != undefined)
			AOM.CS.Log.writeLine("	" + object.reflect.name + "." + methods[i].name + "()");
	}

	AOM.CS.Log.writeLine("<<<<<dumpObject");
}


/**
  * CString class
  * Define application program pathes
  *
  *  @Date: 2007-1-7
*/
AOM.CS.CString = function() {};


AOM.CS.CString.trim = function(s) {
	
	var rev = "";
	if (s != undefined) {
		s = s.toString();
		if (s.length) {
			var re = /\s*((\S+\s*)*)/;
			s = s.replace(re, "$1");
		
			re = /((\s*\S+)*)\s*/;
			rev = s.replace(re, "$1");
		}
	}
	return rev;
	
}


/*
AOM.CS.CString.trim = function(s) 
{ 
	if (s == undefined || s.length == 0) {
		return s;
	}
	if (s instanceof String) {
		return s.replace(/(^\s*)|(\s*$)/g, ""); 
	}
} 
*/

AOM.CS.CString.ltrim = function(s) 
{ 
	return this.replace(/(^\s*)/g, ""); 
} 

AOM.CS.CString.rtrim = function(s) 
{ 
	return this.replace(/(\s*$)/g, ""); 
} 


AOM.CS.CString.badPathCharacters = function(os) {
	if (os == undefined) {
		os = File.fs;
	} 
	var re = new RegExp();
	switch(os) {
	case "Windows" :
		re = /[\/*?"<>|]/;
		re.toString = function() {
			return "/*?\"<>|";
		}
		break;
	case "Macintosh" :
		re  = /:/;
		re.toString = function() {
			return ":";
		}
		break;
	default:
		AOM.alert(AOM.localize("$$$/ContactSheet/badPathCharactersUnknownOs=AOM.CS.CString.badPathCharacters - unknown os."));
		break;
	}
	return re;
};

AOM.CS.CString.badFileCharacters = function(os) {
	if (os == undefined) {
		os = File.fs;
	}

	var re = new RegExp();
	switch(os) {
	case "Windows":
		re  =/[\/\\:*?"<>|]/;
		re.toString = function () { return "/\\:*?\"<>|"; }
		break;
	case "Macintosh":
		re = /:/;	
		re.toString = function () { return ":"; }
		break;
	default:
		AOM.alert(AOM.localize("$$$/ContactSheet/badFileCharactersUnknownOs=AOM.CS.CString.badFileCharacters - unknown os."));
		break;
	}
	return re;
};

AOM.CS.CString.strToBoolean = function (str) {
	if (str) {
         if (str.toString().toLowerCase() == "true") 
             return true;
         else if (str.toString().toLowerCase() == "1") 
             return true;
         else
            return false;
	} else {
		return false;
	}
}

AOM.CS.CString.strToNumber = function(str) {
	if (AOM.CS.Locale.isNumber(str)) {
		return AOM.CS.Locale.parseFloat(str);
	} else {
		return 0;
	}
}


AOM.CS.CString.strToColor = function(colorString) {
	if (colorString == undefined) {
		return undefined;
	}
	
	var newColor = eval(colorString);
	for (var i = 0; i < newColor.length; i++) {
		newColor[i] = Math.round(newColor[i] * 255);
	}
	return (newColor[0] << 16 | newColor[1] << 8 | newColor[2]);
}

/**
  * UIUtil
  * Define application program pathes
  *
  *  @Date: 2007-1-7
*/
AOM.CS.UIUtils = function() {};

AOM.CS.UIUtils.unitConvertion = function(from, to , value,  realPixelPerInch) {
	if (from == undefined || to == undefined || value == undefined) {
		throw new Error("AOM.CS.UIUtils.unitConvertion() throw an error: the arguments 'from, to, value' must not be empty. from="
									+ from + ",to=" + to + ",value=" + value);
	}

	var numValue = AOM.CS.Locale.parseFloat(value);
	if (from == to) return numValue;
	
	//change unit.
	var myVal = UnitValue(numValue, from);
	myVal.convert(to);
	return myVal.value;
}

AOM.CS.UIUtils.getUnitDisplayValue = function(pxValue, unit) {
	var rev = 0;
	if(AOM.CSConstant.UNIT_PIXELS != unit) {
		rev = AOM.CS.UIUtils.unitConvertion(AOM.CSConstant.UNIT_PIXELS, unit, pxValue);
		rev = AOM.CS.Locale.parseFloat(rev, 2, "round");
	}
	else {
		rev = AOM.CS.Locale.parseFloat(pxValue, 0, "round");
	}
	return rev;
}

AOM.CS.UIUtils.getUnitDisplayText = function(value, unit) {
	return AOM.CS.Locale.toLocaleString(
		AOM.CS.UIUtils.getUnitDisplayValue(value, unit));
}


/**
 * AOM.CS.hasProgramInteract is a global variable.
 * It's a workaround for the onChange event mechanism of drop-down-list control, 
 * to distinguish the onChange event is called by program or by user changes. 
 * 
 * As the Javascript Tool guild mentioned " the onChange function called whenever the
 * selection property changes. This can happen when a script sets the property
 * directly or removes a selected item from the list, or when the user changes the
 * selection." 
 * 
 */
AOM.CS.hasProgramInteract = false;

AOM.CS.UIUtils.blockDropDownListEvent = function() {
	var oldValue = AOM.CS.hasProgramInteract;
	AOM.CS.hasProgramInteract = true;
	return oldValue;
}

AOM.CS.UIUtils.unblockDropDownListEvent = function(oldValue) {
	AOM.CS.hasProgramInteract = oldValue;
}

/**
 * setDropDownList
 * Thinking about two types of dropdownlist: one is single, another is parent-children.
 * if current dropdownlist is single, check if items has no empty, don't remove current items,  (Just for performance consider)
 * if current dropdownlist is parent-children, always remove children items, and add new items in the controller. 
 *
 * @param dropDownList       Current DropDownList control element.
 * @param newItems           Set new items into dropdownlist
 * @param value              Equal to selected item text value
 * @param isAlwaysSelected   If true, one item must be selected. 
 */
AOM.CS.UIUtils.setDropDownList = function(dropDownListObj, newItems, value, isAlwaysSelected, isStringArray) {
	if (dropDownListObj == undefined) {
		return undefined;
	}

	// Add lock
	var oldHasProgramInteract = AOM.CS.UIUtils.blockDropDownListEvent();
	
	dropDownListObj.removeAll();
	AOM.CS.UIUtils.addDropDownListItems(dropDownListObj, newItems, isStringArray);
	
	var selectedText = AOM.CS.UIUtils.setDropDownListSelection(dropDownListObj, value, isAlwaysSelected);
	
	// Release Lock
	AOM.CS.UIUtils.unblockDropDownListEvent(oldHasProgramInteract);
	
	return selectedText;
}

AOM.CS.UIUtils.addDropDownListItems = function(dropDownListObj, newItems, isStringArray) {
	if (newItems != undefined) {		
		for(var idx = 0; idx < newItems.length; idx++) {
			var itm = newItems[idx];
			
			var newItem;
			if (isStringArray == undefined || isStringArray == false) {
				if (itm.value == "-") {
					newItem = dropDownListObj.add("separator", "-");
				} else {
					newItem = dropDownListObj.add("item", itm.text);
				}
				newItem.value = itm.value;
			} else {
				//is string array is true
				var pair = itm.split("|||");
				if (pair.length != 2) {
					newItem = dropDownListObj.add("item", itm);
					newItem.value = itm;
				}
				else {
					newItem = dropDownListObj.add("item", pair[0]);
					newItem.value = pair[1];
				}
			}
		}
	}
}

AOM.CS.UIUtils.removeDropDownListItem = function(dropDownListObj, item) {
	// Add lock
	var oldHasProgramInteract = AOM.CS.UIUtils.blockDropDownListEvent();
	
	dropDownListObj.remove(item);
	
	// Release Lock
	AOM.CS.UIUtils.unblockDropDownListEvent(oldHasProgramInteract);
}

AOM.CS.UIUtils.removeAllDropDownListItems = function(dropDownListObj) {
	// Add lock
	var oldHasProgramInteract = AOM.CS.UIUtils.blockDropDownListEvent();
	
	dropDownListObj.removeAll();
	
	// Release Lock
	AOM.CS.UIUtils.unblockDropDownListEvent(oldHasProgramInteract);
}

AOM.CS.UIUtils.addDropDownListItem = function(dropDownListObj, itemText, itemValue, setToSelected) {
	// Add lock
	var oldHasProgramInteract = AOM.CS.UIUtils.blockDropDownListEvent();
	
	var newItem = dropDownListObj.add("item", itemText);
	newItem.value = itemValue;
	
	if (setToSelected) {
		dropDownListObj.selection = newItem;
	}
	
	// Release Lock
	AOM.CS.UIUtils.unblockDropDownListEvent(oldHasProgramInteract);
}

AOM.CS.UIUtils.setDropDownListSelection = function(dropDownListObj, value, isAlwaysSelected) {
	// Add lock
	var oldHasProgramInteract = AOM.CS.UIUtils.blockDropDownListEvent();
	
	var items = dropDownListObj.items; 
	var selectedValue = undefined;
	if (items == undefined || items.length ==0) {
		dropDownListObj.enabled = false;
		dropDownListObj.selection = undefined;
	} else {
		dropDownListObj.enabled = true;
		if(value != undefined) {
			for (var idx = 0; idx < items.length; idx++) {
				if (items[idx].value == value) {
					dropDownListObj.selection = items[idx];
					break;
				}
			}
		}
		
		if (dropDownListObj.selection == undefined && isAlwaysSelected) {
			dropDownListObj.selection = items[0];
		}
		selectedValue = dropDownListObj.selection.value;
	}
	dropDownListObj.gsEnabled = dropDownListObj.enabled;
	
	// Release Lock
	AOM.CS.UIUtils.unblockDropDownListEvent(oldHasProgramInteract);
	
	return selectedValue;
}

AOM.CS.UIUtils.getColorFromColorPicker = function(color) {
	if (color < 0) {
		return undefined;
	}

	var blue  = (color & 0xFF)/255.0; color = color >>> 8;
	var green = (color & 0xFF)/255.0; color = color >>> 8;
	var red   = (color & 0xFF)/255.0;
	
	return [red, green, blue];
}

AOM.CS.UIUtils.setColorToColorPicker = function(rgb) {
	rgb[0] = Math.round(rgb[0] * 255);
	rgb[1] = Math.round(rgb[1] * 255);
	rgb[2] = Math.round(rgb[2] * 255);
	
	return AOM.CS.UIUtils.rgbToHex(rgb[0], rgb[1], rgb[2]);
}

AOM.CS.UIUtils.rgbToHex = function(r, g, b) { 
	var r_string= r.toString(16); 
	var g_string = g.toString(16); 
	var b_string= b.toString(16); 
	r_string = (r_string.length < 2) ? ("0" + r_string) : r_string; 
	g_string = (g_string.length < 2) ? ("0" + g_string) : g_string; 
	b_string = (b_string.length < 2) ? ("0" + b_string) : b_string; 
	var rgbHex = parseInt((r_string + g_string + b_string), 16);
	return rgbHex;
} 

AOM.CS.UIUtils.getUnitZString = function(unit) {
	var unitText;	
	if (unit == AOM.CSConstant.UNIT_INCHES) {
		unitText = "$$$/ContactSheet/javascript/dropdownlist/inches=inches";
	} else if (unit == AOM.CSConstant.UNIT_CENTIMETERS) {
		unitText = "$$$/ContactSheet/javascript/dropdownlist/centimeters=cm";
	} else if (unit == AOM.CSConstant.UNIT_PIXELS) {
		unitText = "$$$/ContactSheet/javascript/dropdownlist/pixels=pixels"; 
	}
	return unitText;
}
