/** FILE: flash-player-embed.js
* Copyright (c) 2008 C-Span Archives
*
* Provides an interface to show and hide the player.
*/

/*
  requires: flash-player-config.js
  requires: dom-util.js
  
  interface functions:
    constructor: new FlashPlayer();
    var: myFlashPlayer - the player object 
    myFlashPlayer.setPid( prog_id ) - sets program id
    myFlashPlayer.setNetTime( begin, end, net ) - sets network begin and end times as UTC Strings
    myFlashPlayer.showPopup( width, height, start, stop ) - shows player in popup
    myFlashPlayer.showInEl( dom_id, width, height, start, stop ) - shows player
    myFlashPlayer.hideInEl(dom_id) - hides player
    myFlashPlayer.writeDiv(dom_id, width, height) - document.writes a div (convenience only)
    myFlashPlayer.playToggle() - toggles playing state
    myFlashPlayer.time() - returns current time in seconds
    myFlashPlayer.seek(t) - seeks clip to time t (seconds)
    myFlashPlayer.setVolume(t) - sets volume to v (0 - 1)


    myFlashPlayer.addHook(t) - adds a hook to be invoked when player loads
    myFlashPlayer.runHooks() - invokes all hooks

  bugs:
   - Can only show one player on a page.
     No one should ever want to show more, though.
*/

var padding = 5;

/** Displays the player in a iframe inserted in element `dom_id'.

width, height, start, and stop are optional parameters

*/
function showFlashPlayerInEl( dom_id, width, height, start, stop ) {
    if(this.is_in_element) return;

    if( this.is_in_popup && !this.popup_window.closed ) {
	this.popup_window.close();
	this.is_in_popup = false;
	this.popup_window = null;
    };
    //alert( width);
    this.is_in_element = true;
    this.element_id = dom_id;
    if( !dom_id) {alert("Must specify dom id"); return; }
    if(!width) var width =  this.config.default_width;
    if(!height) var height =  this.config.default_height;
   
    //alert( width);
    var url = this.getUrl({ width: width, height: height, start: start, stop: stop} );
    var markup = buildMarkup("iframe", 
	{
	    style: "border-style: none",
	    src: url, 
	    width: width + padding , 
	    height: height + padding, 
	    id: this.config.iframe_id,
	    name: this.config.iframe_id,
            frameborder:  "no"
	});
    //alert(markup);
    //setHTML(dom_id, markup);
    setHTML(dom_id, markup);
}

/** Hides the player being shown in an iframe inserted in element `dom_id'.
*/
function hideFlashPlayerInEl( dom_id ) {
    if(!this.is_in_element) return;
    this.is_in_element = false;
    this.element_id = null;
    this.movie = null;
    setHTML(dom_id, "");
    this.reset();
}

/** Writes a div.
Convenience function.
height and width are optional
*/
function writePlayerDiv( dom_id, width, height ) {
    var width1 =  width ?  width : this.config.default_width  + padding;
    var height1 =  height ?  height : this.config.default_height  + padding;
    //var style = "width: " + width1 + "; height: " + height1 + ";";
    var s = buildCSS( {width: width1, height: height1, "border-style": "none", overflow: "hidden"} );
    var t= buildOpenTag( "div", {id: dom_id, style: s}  );

    document.write( t + "</div>" );

}
 

/** Shows the player in a popup window.
    If the player is in the embedded window, hide and start the popup at the same time, 
      ignoring the parameter that's passed.
    If player is already running in the popup window, do nothing.
*/
function showFlashPlayerPopup( width, height, start, stop ) {
    if( !this.pid) {alert("Must specify program id"); return; }
    if(!width) var width = this.config.default_width;
    if(!height) var height = this.config.default_height;
    if(!start) var start = "";
    if(!stop) var stop = "";

    // handle player location
    if( this.is_in_popup ){
	if( !this.popup_window.closed )
	    return;
    };
    this.is_in_popup = true;
    if( this.is_in_element ) {
	start = this.movie.time();
	this.hideInEl( this.element_id );
    }
    
    var url = this.getUrl( { width: width, height: height, start: start, stop: stop} );
    var winprop = 'height=' + height; 
    winprop += ',width=' + (parseInt(width) + 80);
    winprop += ',resizable=0'; //honored by safari and ie, not by firefox and opera
    winprop += ',location=0';
    winprop += ',scrollbars=1';
    winprop += ',status=0';

    var newwindow = window.open(url,"C_Span_Flash_Player_Popup", winprop );
    newwindow.parentFlashPlayer = this;

    this.popup_window = newwindow;

    if (window.focus) {newwindow.focus()}

}

/***********************/
/** Utility Functions **/
/***********************/

/** builds a url to the flash player page
*/
function flash_url( params ) 
{
	var url_args = new Object();

	if( !this.doNetTime ) 
	{
		if( !this.pid) 
		{ 
			alert("Must specify program id"); return ""; 
		}

		url_args.pid = this.pid;
	}
	else 
	{
		if( !this.playBegin && !this.playEnd && !this.net)  
		{
		alert("Must specify program net-times"); 
		return ""; 
		}

		url_args.pid = "NULL";
		url_args.playBegin = this.playBegin;
		url_args.playEnd = this.playEnd;
		url_args.net = this.net;
	}

	url_args.width = ( params.width ?  params.width : this.config.default_width );
	url_args.height = ( params.height ?  params.height : this.config.default_height );

	if ( this.noautoplay )
		url_args.noautoplay = 1;
 
	if(this.dev) url_args.dev = "true";

	if( params.start) url_args.start = params.start;
	if( params.stop) url_args.stop = params.stop;
	
	url = buildURL(this.config.flash_page, url_args);
	//alert(url);
	return url;
}


function validateTime( time ) {
    var r = new RegExp("^\\d\\d\\d\\d-[0-1]\\d-[0-3]\\d [0-2]\\d:[0-5]\\d:[0-5]\\d$");
    return r.exec(time) != null;
}

function FlashPlayer(config) {
    this.config = config ? config : flashplayer_config;
    this.is_in_element =   false;
    this.element_id =      null;
    this.is_in_popup =     false;
    this.popup_window =    null;
    this.dev =             false;
    this.iframe_id = this.config.iframe_id;
    this.setMovie = function(m) { this.movie = m };
    this.pid = "";
    this.doNetTime = false;

    this.hooks = new Array(); // : thunks
    this.hooks1 = new Array(); // : thunks

    this.setPid = function(p) {
	this.pid = p; 
	this.doNetTime = false;
    };

    this.setNetTime = function(beg, end, net ) {
        if( ! validateTime( beg ) ) {
            alert("Invalid time: " + beg);
            return;
        }
        if( ! validateTime( end ) ) {
            alert("Invalid time: " + end);
            return;
        }
        if( ! (net == "1" || net == "2" || net=="3" ) ) {
            alert("Invalid network: " + net );
            return;
        }
	this.playBegin = beg;
	this.playEnd = end;
	this.net = net;
	this.doNetTime = true;
    }

    this.showInEl = showFlashPlayerInEl;
    this.hideInEl = hideFlashPlayerInEl;
    this.showPopup = showFlashPlayerPopup;
    this.writeDiv = writePlayerDiv;
    this.getUrl = flash_url;

    this.playToggle = function() {this.movie.playToggle(); };
    this.time = function() { return this.movie.time(); }
    this.seek = function(t) { this.movie.seek(parseFloat(t)); };
    this.setVolume = function(v) { this.movie.setVolume(parseFloat(v)); };
    this.doDev = function() {this.dev = true; }

    this.addHook = function(thunk) { 
	this.hooks[this.hooks.length] = thunk;
    }
    this.addHookOnce = function(thunk) { 
	this.hooks[this.hooks.length] = thunk;
    }
    this.runHooks = function () {
	for( i = 0; i < this.hooks.length; i++ ) {
	    this.hooks[i]();
	}
	for( i = 0; i < this.hooks1.length; i++ ) {
	    this.hooks1[i]();
	}
	hooks1 = new Array();
    }
    this.reset = function() {
        this.playBegin = null;
        this.playEnd = null;
        this.net = null;
        this.doNetTime = null;
        this.pid = "";
    }
}

var myFlashPlayer = new FlashPlayer(flashplayer_config);

