var CNN_PLAYER = "CNN_PLAYER";
var findPlayer = xmp.baseplayer.BasePlayer.findPlayer;
var playerInstances = new Array();
var currentPlayer = '';

/* ********************
   Begin Adobe Client Side Flash Detection Script
   ********************
 */
 
// Flash Player Version Detection - Rev 1.6
// Detect Client Browser type
// Copyright(c) 2005-2006 Adobe Macromedia Software, LLC. All rights reserved.

var isIE  = (navigator.appVersion.indexOf("MSIE") != -1) ? true : false;
var isWin = (navigator.appVersion.toLowerCase().indexOf("win") != -1) ? true : false;
var isOpera = (navigator.userAgent.indexOf("Opera") != -1) ? true : false;

function ControlVersion()
{
	var version;
	var axo;
	var e;

	// NOTE : new ActiveXObject(strFoo) throws an exception if strFoo isn't in the registry

	try {
		// version will be set for 7.X or greater players
		axo = new ActiveXObject("ShockwaveFlash.ShockwaveFlash.7");
		version = axo.GetVariable("$version");
	} catch (e) {
	}

	if (!version)
	{
		try {
			// version will be set for 6.X players only
			axo = new ActiveXObject("ShockwaveFlash.ShockwaveFlash.6");
			
			// installed player is some revision of 6.0
			// GetVariable("$version") crashes for versions 6.0.22 through 6.0.29,
			// so we have to be careful. 
			
			// default to the first public version
			version = "WIN 6,0,21,0";

			// throws if AllowScripAccess does not exist (introduced in 6.0r47)		
			axo.AllowScriptAccess = "always";

			// safe to call for 6.0r47 or greater
			version = axo.GetVariable("$version");

		} catch (e) {
		}
	}

	if (!version)
	{
		try {
			// version will be set for 4.X or 5.X player
			axo = new ActiveXObject("ShockwaveFlash.ShockwaveFlash.3");
			version = axo.GetVariable("$version");
		} catch (e) {
		}
	}

	if (!version)
	{
		try {
			// version will be set for 3.X player
			axo = new ActiveXObject("ShockwaveFlash.ShockwaveFlash.3");
			version = "WIN 3,0,18,0";
		} catch (e) {
		}
	}

	if (!version)
	{
		try {
			// version will be set for 2.X player
			axo = new ActiveXObject("ShockwaveFlash.ShockwaveFlash");
			version = "WIN 2,0,0,11";
		} catch (e) {
			version = -1;
		}
	}
	
	return version;
}

// JavaScript helper required to detect Flash Player PlugIn version information
function GetSwfVer(){
	// NS/Opera version >= 3 check for Flash plugin in plugin array
	var flashVer = -1;
	if (navigator.plugins != null && navigator.plugins.length > 0) {
		if (navigator.plugins["Shockwave Flash 2.0"] || navigator.plugins["Shockwave Flash"]) {
			var swVer2 = navigator.plugins["Shockwave Flash 2.0"] ? " 2.0" : "";
			var flashDescription = navigator.plugins["Shockwave Flash" + swVer2].description;
			var descArray = flashDescription.split(" ");
			var tempArrayMajor = descArray[2].split(".");			
			var versionMajor = tempArrayMajor[0];
			var versionMinor = tempArrayMajor[1];
			var versionRevision = descArray[3];
			if (versionRevision == "") {
				versionRevision = descArray[4];
			}
			if (versionRevision[0] == "d") {
				versionRevision = versionRevision.substring(1);
			} else if (versionRevision[0] == "r") {
				versionRevision = versionRevision.substring(1);
				if (versionRevision.indexOf("d") > 0) {
					versionRevision = versionRevision.substring(0, versionRevision.indexOf("d"));
				}
			}
			var flashVer = versionMajor + "." + versionMinor + "." + versionRevision;
		}
	}
	// MSN/WebTV 2.6 supports Flash 4
	else if (navigator.userAgent.toLowerCase().indexOf("webtv/2.6") != -1) flashVer = 4;
	// WebTV 2.5 supports Flash 3
	else if (navigator.userAgent.toLowerCase().indexOf("webtv/2.5") != -1) flashVer = 3;
	// older WebTV supports Flash 2
	else if (navigator.userAgent.toLowerCase().indexOf("webtv") != -1) flashVer = 2;
	else if ( isIE && isWin && !isOpera ) {
		flashVer = ControlVersion();
	}	
	return flashVer;
}

// When called with reqMajorVer, reqMinorVer, reqRevision returns true if that version or greater is available
function DetectFlashVer(reqMajorVer, reqMinorVer, reqRevision)
{
	versionStr = GetSwfVer();
	if (versionStr == -1 ) {
		return false;
	} else if (versionStr != 0) {
		if(isIE && isWin && !isOpera) {
			// Given "WIN 2,0,0,11"
			tempArray         = versionStr.split(" "); 	// ["WIN", "2,0,0,11"]
			tempString        = tempArray[1];			// "2,0,0,11"
			versionArray      = tempString.split(",");	// ['2', '0', '0', '11']
		} else {
			versionArray      = versionStr.split(".");
		}
		var versionMajor      = versionArray[0];
		var versionMinor      = versionArray[1];
		var versionRevision   = versionArray[2];

        	// is the major.revision >= requested major.revision AND the minor version >= requested minor
		if (versionMajor > parseFloat(reqMajorVer)) {
			return true;
		} else if (versionMajor == parseFloat(reqMajorVer)) {
			if (versionMinor > parseFloat(reqMinorVer))
				return true;
			else if (versionMinor == parseFloat(reqMinorVer)) {
				if (versionRevision >= parseFloat(reqRevision))
					return true;
			}
		}
		return false;
	}
}

/* ********************
   End Adobe Client Side Flash Detection Script
   ********************
 */

function callControllerMethod(p_method, p_arg) 
{
	var returnVal;
	if (CNNPlaylistManager.getInstance().controller != null) {
		// we're using the DHTML control structure
		var cntl = CNNPlaylistManager.getInstance().controller;
		returnVal = cntl.handleXMPEvent(p_method, p_arg);
	} 
	else {
		try {
			if ( CNNPlaylistManager.getInstance().activePlaylist == 'saplaylist' ) {
				returnVal = CNNPlaylistManager.getInstance().SAConfiguration.controlsHandler(p_method, p_arg);
			} else {
				var controller = (navigator.appName.indexOf("Microsoft") != -1) ? window["mediacontrols"] : document["mediacontrols"];
				returnVal = controller[p_method](p_arg);
			}
		} 
		catch(err) {
			// catch error and ignore, usually caused by xmp loading before controller plugin
		}
	}
	
	if ( typeof(returnVal) != "undefined" ) return returnVal;
}

function initAdServerCookies(docDomain)
{
	if (xmp.util.Cookie.canUse()) // can the user read/write cookie values?
	{
		var cnnAdCookieIsSet = xmp.util.Cookie.read('adDEon');
		if (!cnnAdCookieIsSet)
		{
			var imgSrc = 'http://gdyn.' + docDomain + '/1.1/1.gif';
			window.top.document.images['cookieCrumb'].src = imgSrc;
		}
	}		
}

function CNNPlayer(options, parameters) {
	initAdServerCookies('cnn.com');
	var categoryFilterArray = [/*'AjaxRequestManager', 'VideoContentMetaFileLoader'*/]; // allows filtering out of categories with too many messages.
	var parameters = [ ];
	CNNPlayer.ctor.call( this, CNN_PLAYER, options, parameters );	
}

xmp.DERIVE_CLASS( xmp.baseplayer.BasePlayer, CNNPlayer );

CNNPlayer.create = function() {
	xmp.util.LogConfigurator.configure();

	var buildMap = {};
	buildMap['edition'] = 'arabic';
	buildMap['omnitureEdition'] = 'cnnarabic';

	xmp.baseplayer.BasePlayer.configure([cnnXmpPrimaryJsonObj], buildMap);

	playerInstances[0] = new CNNPlayer({}, [ ]);
	playerInstances[0].bootStrap();
}
CNNPlayer.prototype.callEnded = function() {
	CNNPlaylistManager.endOfVideoContent();
}
CNNPlayer.getInstance = function(id, context) {
	if (playerInstances[0] == null) {
	}
	return playerInstances[0];
}
CNNPlayer.setActivePlayer = function(str) { currentPlayer = str; }
CNNPlayer.getActivePlayer = function() {
	return playerInstances[0];
}
CNNPlayer.playlistContentItemCB = function() { }
CNNPlayer.secondsIntoMinutes = function(val) {
	minutes = Math.floor(val / 60);
	if (minutes > 0) seconds = val - (minutes * 60);
	else seconds = val;
	return (minutes + ':' + CNNPlayer.tenify(seconds));
}
CNNPlayer.tenify = function(val) {
	if (val - 0 < 10)
		return ("0"+val);
	return val;
}

CNNPlayer.prototype.serializerFactory = null;
CNNPlayer.prototype.playlist = null;
CNNPlayer.prototype.isSmall = false;
CNNPlayer.prototype.isScrubbing = false;
CNNPlayer.prototype.pluginError = null;
CNNPlayer.prototype.pluginErrorWindow = null;

CNNPlayer.prototype.handleLogMessage = function(level, category, message)
{
};

CNNPlayer.prototype.handleBootstrapped = function(success) {
	CNNPlaylistManager.isBootStrapped(success);
}


CNNPlayer.prototype.replacePlaylist = function(currentJsonListArray, jsonListArray) {
	this.getMediaPlayer().stop();
	for (var i = 0; i < currentJsonListArray; i++) {
		this.removeFromPlayList(currentJsonListArray[i]);
	}
	// get current playlist
	// iterate through and remove
	// iterate through and add new playlist
	// write append callbacks
}


CNNPlayer.prototype.handleEvent = function(controllerEvent) {
	if (controllerEvent == 'playPressed') { this.play(); }
	if (controllerEvent == 'pausePressed') { this.pause(); }
	if (controllerEvent == 'scrubStarted') { this.scrubStarted(); }
	if (controllerEvent == 'scrubComplete') { this.scrubComplete(); }
	if (controllerEvent == 'volumeChanged') { this.volumeChanged(); }
	if (controllerEvent == 'sharePressed') { CNNPlaylistManager.getInstance().emailVideo(); }
}
CNNPlayer.prototype.volumeChanged = function() {
	this.getMediaPlayer().setVolume( callControllerMethod('getVolume') );
}
CNNPlayer.prototype.pause = function() {
	callControllerMethod('setScrubberEnabled',false);
	this.getMediaPlayer().pause();
	callControllerMethod('togglePlay',false);
}
CNNPlayer.prototype.play = function() {
	this.getMediaPlayer().play();
	callControllerMethod('setScrubberEnabled',true);
	callControllerMethod('togglePlay',true);
}
CNNPlayer.prototype.scrubStarted = function() {
	this.isScrubbing = true;
	callControllerMethod('togglePlay',false);
}
CNNPlayer.prototype.scrubComplete = function() {
	this.isScrubbing = false;
	toVal = callControllerMethod('getTime');
	this.getMediaPlayer().seek(toVal);
	callControllerMethod('togglePlay',true);
}
CNNPlayer.prototype.setPlaylist = function(idList,finalCallback) {
	this.serializerFactory = xmp.baseplayer.MetaFileLoaderFactory.getInstance().create('videoContentMeta');
	this.playlist = this.serializerFactory.setIds(idList, (new xmp.util.Callback('contentItemCB', CNNPlayer.playlistContentItemCB, null)));	
	this.serializerFactory.setAllLoadedCallback(new xmp.util.Callback('allContentItemsCB', finalCallback, null));
	this.serializerFactory.load();
}
CNNPlayer.prototype.getPlaylist = function() {
	return this.playlist;
}
CNNPlayer.prototype.handleMediaPlayerReady = function() {
	var mediaPlayer = this.getMediaPlayer();
	callControllerMethod('setVolume',45);
	mediaPlayer.setVolume( 45 );
	mediaPlayer.setMute( false );
	mediaPlayer.setViewportConfig( xmp.FLASH_MIME_TYPE, xmp.DHTML_VIEWPORT );	
	mediaPlayer.setViewportConfig( xmp.WINDOWS_MEDIA_MIME_TYPE, xmp.DHTML_VIEWPORT );	
	mediaPlayer.setViewportConfig( xmp.IMAGE_MIME_TYPE, xmp.DHTML_VIEWPORT );	
	mediaPlayer.setViewportConfig( xmp.DHTML_MIME_TYPE, xmp.DHTML_VIEWPORT );	
};

CNNPlayer.prototype.handleCreateViewport = function( type, name, parameters, settings ) {
	if ( type === xmp.FLASH_VIEWPORT ) {
		return this.createFlashViewport( type, name, parameters, settings );
	}
	else if ( type === xmp.DHTML_VIEWPORT ) {
		return this.createDHTMLViewport( type, name, parameters, settings );
	}
	return null;
};

CNNPlayer.prototype.handleFatalException = function( err ) {
	CNNPlaylistManager.getInstance().errorObject = err;
};

CNNPlayer.prototype.createFlashViewport = function( type, name, parameters, settings ) {
	var viewport = new SWFObject( xmp.makeSWFPath("TestFlashViewport", false), name, "574", "324", 8, "#FFFFFF" );
	for ( var i = 0; i < parameters.length; i++ ) {
		viewport.addParam( parameters[i].name, parameters[i].value );	
	}
	for ( i = 0; i < settings.length; i++ ) {
		viewport.addVariable( settings[i].name, settings[i].value );
	}
// removed per Chad and 113007 XMP release
//	viewport.addVariable( xmp.FLASH_NATIVE_PLAYER_COMPONENT, xmp.getSWFRoot() + "FlashMediaPlayer.swf" );
	if (CNNPlaylistManager.getInstance().activePlaylist != 'saplaylist')
		viewport.write( document.getElementById("cnnVPFlashLargeContainer").id );	
	else
		viewport.write( document.getElementById(CNNPlaylistManager.getInstance().SAConfiguration.videoDivId).id );	

	// ------------------------------------------------------------------------------------------
	// Store reference to flash container to use later to set container flash content.
	flash_container = xmp.findDomElement(name);
	// ------------------------------------------------------------------------------------------

	flash_container.style.cssText = "position: absolute";
	return flash_container;
};

CNNPlayer.prototype.createDHTMLViewport = function( type, name, parameters, settings )  {
	var viewport = document.createElement( "div" );
	viewport.setAttribute( xmp.ID_ATTRIBUTE, name );
	viewport.setAttribute( xmp.NAME_ATTRIBUTE, name );
	if (CNNPlaylistManager.getInstance().activePlaylist != 'saplaylist')
		var sample_container = document.getElementById( "cnnVPFlashLargeContainer" );
	else
		var sample_container = document.getElementById( CNNPlaylistManager.getInstance().SAConfiguration.videoDivId );
	if (CNNPlaylistManager.getInstance().activePlaylist == 'bvpplaylist') {
		if (this.isSmall) {
			viewport.style.width = '287px';
			viewport.style.height = '161px';
		} else {
			viewport.style.width  = "574px";
			viewport.style.height = "324px";	
		}
	} else if (CNNPlaylistManager.getInstance().activePlaylist == 'saplaylist') {
		viewport.style.width = CNNPlaylistManager.getInstance().SAConfiguration.slateSize[0]+"px";
		viewport.style.height = CNNPlaylistManager.getInstance().SAConfiguration.slateSize[1]+"px";
	}

	viewport.style.backgroundColor = "#000000";	
										
	xmp.insertDomChildBefore(sample_container, viewport);

	return viewport;
};


CNNPlayer.prototype.handleRegisterNodeListeners = function() {
	this._playerListener = new CNNPlayerListener('AllNodes', this);

	var listeners = [ {object: this._playerListener, nodes: ["*"]},
		              {object: new AdNodeListener('Ad', this), nodes: ["PreRoll", "PostRoll", "SponsoredAd", "HouseAd", "AdInsertNotForSale"]},
		              {object: new xmp.baseplayer.listeners.DefaultPromoNodeListener('Promo', this), nodes: ["Promo"]},
									{object: new VideoNodeListener('Video', this), nodes: ["Content"]},
		              {object: new NextUpSlateNodeListener('NextUpSlate', this), nodes: ["NextUpSlate"]},
		              {object: new StartSlateNodeListener('StartSlate', this), nodes: ["StartSlate"]},
		              {object: new EndSlateNodeListener('EndSlate', this), nodes: ["EndSlate"]},
		              {object: new ErrorSlateNodeListener('ErrorSlate', this), nodes: ["ErrorSlate"]}, 
		              {object: new xmp.baseplayer.listeners.DefaultSlateNodeListener('Slate', this), nodes: ["CustomSlate"]}
		              ];
		              
	for ( var i = 0; i < listeners.length; i++ )
	{
		this.registerNodeListener( listeners[i].object, listeners[i].nodes );	
	}						   
};


CNNPlayer.prototype.loadSynchUnit = function(node) {
	var resType = node.getPlayableData().getRuntimeMetadata('synch_unit_type', 'synch_unit');
	var res = node.getMetaResource(resType);
	var synchUnitLogger = new xmp.util.internals.CategoryLogger( 'loadSynchUnit' );

	digger = node;
	if (!res) { return; }
	if (res.isError())
	{
		return;
	}
	// data will be the full URL of the banner ad call to the ad server
	var data = res.getDataObject();
	var dataType = res.getDataType();
	var logData = (dataType === 'html') ? 'html' : data;
	if (res.getMetadata('played_' + resType, false))
	{
		return;
	}
	res.setMetadata('played_' + resType, true);

  this._createBannerAd("banner_ad_iframe", data, dataType);
  this._playerListener.setStatus(node, xmp.SYNCH_UNIT);
};

// original version from cnn_adspaces.js (cnnad_createAd) - need to have a method that does not set the tile ID, we have already built it into the url.
CNNPlayer.prototype._createBannerAd = function( adId, data, dataType )
{
		if (CNNPlaylistManager.getInstance().playlistType == 'mos') {
		CNNPlaylistManager.getInstance().MOSCBannerAdWrite(data,adId);
	} else { 
		var bannerDiv = document.getElementById("cnnVPAd");
		var innerHtml = '';
		if (dataType === 'url')
		{
			innerHtml = '<iframe hspace="0" vspace="0" marginHeight="0" marginWidth="0" src="' + data + '&page.allowcompete=yes&domId=' + adId + '" border="0" frameBorder="0" height="0" width="0" scrolling="no"  id="'+adId+'" style="position: absolute; visibility: hidden;" ></iframe>';
		}
		else
		{
			// If this is not working, make sure that 'params.styles=fs' is removed from primary.xml under 
			// 'Additional segvars' for your player context.
			innerHtml = data;
		}
		bannerDiv.innerHTML = innerHtml;
	}
};

CNNPlayer.prototype._findNextContentNode = function( ) {	
	var lookAhead = this.getLookAheadNodeArray();	
	for ( var i = 0; i < lookAhead.length; i++ ) {
		var node = lookAhead[i];
		if ( node.isContentType() ) {
			return node;
		}
	}	
	return null;
};
CNNPlayer.prototype._findPreviousContentNode = function( ) {	
	var lookBehind = this.getLookBehindNodeArray();
	for ( var i = 0; i < lookBehind.length; i++ )
	{
		var node = lookBehind[i];
		if ( node.isContentType() ) {
			return node;
		}
	}
	return null;
};
