// JavaScript Document
var cc = 0;

function jsASConnection_registerConnector(moviename,connector)
{
  //alert(document.getElementById(moviename));
	if(document.asConnectorlist == undefined)
	{
		document.asConnectorlist = new Object();
		setInterval("jsAsConnection_process();",500);
	}
	if(document.asConnectorlist[moviename] == undefined)
	{
		document.asConnectorlist[moviename] = connector;
	}
}

function jsAsConnection_process()
{
  if(document.asConnectorlist == undefined)
  {
    alert("Process without connectionlist.");
  }
  var n;
  for(n in document.asConnectorlist)
  {
    document.asConnectorlist[n].process();
  }
}
/* This function handles an FSCommand.
returns true if the command was handled (also on error but on a known command)
returns false if the command is unknown*/
function jsASConnection_FSCommand(movie,befehl,param)
{
	/* On Mac OS X the command consists of "FSCommand:"+command
	so we trim it*/
	if(befehl.substr(0,10) == "FSCommand:") befehl = befehl.substr(10);
	
	//if(cc++ < 10) alert("FsCommand" + movie + befehl + document.asConnectorlist[movie]);
	if(document.asConnectorlist[movie] != undefined)
	{
     switch(befehl)
     {
      case "jsLoadVars":
        document.asConnectorlist[movie].onDataRequest(param);
        return true;
      case "jsConnector_reply":
        document.asConnectorlist[movie].onDataResult(param);
        return true;
      case "jsConnector_data_received":
        document.asConnectorlist[movie].block--;
        document.asConnectorlist[movie].process();
        return true;
      case "jsConnector_flash_loaded":
        //alert("Flash loaded");
        document.asConnectorlist[movie].flashLoaded=true;
        return true;
      }
   }
	return false;
}

function asConnector(moviename)
{
	
	this.mOutqueue = new Array();
	this.mMovieName = moviename;
	this.mCurrentMessage = undefined;
	this.mCurrentInMsg = undefined;
	this.flashLoaded = false; //is true if flash movie is loaded and we can send data
	
	/* block is an integer in JS because we have two levels of blocking:
	   1. we don't know when flash catches the variable set by SetVariable
	   2. if we sent a request with reply we have to wait for the result
	   
	   The workflow is like that:
	   sendAndLoad sets block to 2, a flash fsCommand with jsConnector_data_received will decrement block by one
	   onDataResult will again decrement by one
     
     block is only interesting for outgoing requests eg. send() and sendAndLoad()
     for reply() flash assures that we can directly send*/
	this.block = 0;  
	
	if (navigator.appName && navigator.appName.indexOf("Microsoft") != -1 && navigator.userAgent.indexOf("Windows") != -1)
	{
		//Windows Version with event="FSCommand()"
		document.write("<Script language=\"JavaScript\" type=\"text/JavaScript\" event=\"FSCommand (befehl, param)\" for= \""+moviename+"\">\n");
		document.write("if(!jsASConnection_FSCommand(\"" + moviename + "\",befehl,param)) handleFSCommand(\"" + moviename + "\",befehl,param);\n");
		document.write("</script\>\n");
	}
	else
	{
		document.write("<script language=\"JavaScript\" type=\"text/JavaScript\"\>\n");
		document.write("function "+moviename+"_DoFSCommand(befehl,param)\n");
		document.write("{ if(!jsASConnection_FSCommand(\"" + moviename + "\",befehl,param)) handleFSCommand(\"" + moviename + "\",befehl,param); }\n");
		document.write("</script\>\n");
	}
	/*document.write("if (navigator.appName && navigator.appName.indexOf(\"Microsoft\") != -1 && \n");
	document.write("navigator.userAgent.indexOf(\"Windows\") != -1 && navigator.userAgent.indexOf(\"Windows 3.1\") == -1) {\n");
	document.write("document.write('<SCRIPT LANGUAGE=VBScript\\> \\n');\n");
	document.write("document.write('on error resume next \\n');\n");
	document.write("document.write('Sub "+moviename+"_FSCommand(ByVal command, ByVal args)\\n');\n");
	document.write("document.write(' call "+moviename+"_DoFSCommand(command, args)\\n');\n");
	document.write("document.write('end sub\\n');\n");
	document.write("document.write('</SCRIPT\\> \\n');\n");
	document.write("}\n");*/
	
	
	jsASConnection_registerConnector(moviename,this);
}
/* this is called when flash has replyed a call to sendAndLoad */
asConnector.prototype.onDataResult = function(src)
{
  if(this.mCurrentOutMsg == undefined)
  {
    alert("onDataResult called without current outgoing message");
    return;
  }
  this.block--;
  this.mCurrentOutMsg.onData(src);
  if(this.mCurrentOutMsg.getSendType() != this.mCurrentOutMsg.SEND_TYPE_NONE) alert("Send type available on result.");
  this.mCurrentOutMsg = undefined;
  this.process();
}

/* this is called when flash requests something */
asConnector.prototype.onDataRequest = function(src)
{
	//if(cc++ <8) alert("onData "+src+" " +this.mCurrentMessage);
	if(this.mCurrentMessage != undefined)
	{
	   alert("Got request but currentMsg is defined");
	}
	
	var msg = new asMessage();
	//This will handle everything except the JS_CHECK messages
	msg.onData(src);
	//if(cc <8) alert(this.mCurrentOutMsg);
	if(msg.getSendType() == msg.SEND_TYPE_ONEWAY)
	{
	   this.reply(msg.getSendData());
  }
  else if(msg.getSendType() == msg.SEND_TYPE_REQUEST)
  {
    alert("Wrong Message type for request result");
  }
	
				
		
		/*//This could be either a JavaScript result, a call from JavaScript or a NOOP
		mCurrentMessage.onData(src,mLoadVars);
		//If the message is done, we can delete it
		if(mCurrentMessage.type == jsMessage.IDLE) mCurrentMessage = undefined;*/
		
}

asConnector.prototype.process = function()
{
  //alert(document.embeds[this.mMovieName]);
  /*if(document.getElementById(this.mMovieName) != null && !this.flashLoaded)
  {
    alert("Connected " + this.mMovieName);
    document.embeds[this.mMovieName] = document[this.mMovieName];
    this.flashLoaded = true;
  }*/

  if(!this.flashLoaded)
  {
    //alert("Flash not loaded");
    return;
  }
  //Checking the outqueue and send it if we are unblocked
  if(this.block == 0)
  {
    //if(this.mCurrentOutMsg != undefined) alert("process without block, but with current out msg");
    if(this.mOutqueue.length)
    {
      this.mCurrentOutMsg = this.mOutqueue.shift();
      if(this.mCurrentOutMsg.getSendType() == this.mCurrentOutMsg.SEND_TYPE_REQUEST)
      {
        this.sendAndLoad(this.mCurrentOutMsg.getSendData());
      }
      else if(this.mCurrentOutMsg.getSendType() == this.mCurrentOutMsg.SEND_TYPE_ONEWAY)
      {
        this.send(this.mCurrentOutMsg.getSendData());
        mCurrentOutMsg = undefined;
      }
      else
      {
        alert("wrong send type in process()" + this.mCurrentOutMsg.getSendType() + this.mCurrentOutMsg.SEND_TYPE_REQUEST);
      }
    }
  }
}
	
asConnector.prototype.callAsFunction = function(functionName,paramarr,callback,userdata)
{
	var msg = new asMessage();
	msg.setCallData(functionName,paramarr,callback,userdata);
	this.mOutqueue.push(msg);
	this.process();
}

asConnector.prototype.send = function(data)
{
	//if(cc++ < 20) alert("Sending "+data);
	
  if(this.block==0)
	{
		//alert("send "+data);
		//alert(document[this.mMovieName]);
		document[this.mMovieName].SetVariable('jsLoadVars_incoming_request',data);
		this.block = 1;
		//getURL("javascript:flashCall(\"bla\");");
	}
	else
	{
		alert("send blocked");
	}

}

/* Sends a message to Flash and blocks until a result is received */
asConnector.prototype.sendAndLoad = function(data)
{
	if(this.block==0)
	{
		//alert("send "+data);
		//alert(document[this.mMovieName]);
		document[this.mMovieName].SetVariable('jsLoadVars_incoming_request',data);
		//getURL("javascript:flashCall(\"bla\");");
		this.block = 2;
	}
	else
	{
	   alert("Send blocked");
		//this.trace1("fscommand blocked");
	}
}

asConnector.prototype.reply = function(data)
{
	alert("reply "+data);
	document[this.mMovieName].SetVariable('jsLoadVars_incoming',data);
}
