(function($, s4ntc) {

  var s4ntcKrpanoDefaults = {
    swf_url: "",
    xml_url: "",
    name: "pano",
    swf_background_color: "#000000",
    allow_fullscreen: true,
    width: "100%",
    height: "100%",
    loadParams: []
  };

  /**
   * @class s4ntc.vem.Krpano
   */
  s4ntc.vem.Krpano = function(parent_id, options) {
    this._parent_selector = "#"+parent_id;
    this._options = $.extend(true, {}, s4ntcKrpanoDefaults, options);

    this._swfo = this._create( parent_id,
      this._options.swf_url,
      this._options.xml_url,
      this._options.name,
      this._options.width,
      this._options.height,
      this._options.background_color,
      this._options.allow_fullscreen,
      this._options.loadParams);

    this._element = document.getElementById(this._options.name+"_swfo");
  };

  s4ntc.vem.Krpano.prototype._create = function(parent_id, swf_url, xml_url, name, width, height, background_color, allow_fullscreen, loadParams) {
    var swfObject;
    if(background_color == undefined) background_color = "#000000";
    if(allow_fullscreen == undefined) allow_fullscreen = true;
    // <![CDATA[
    if (typeof(deconcept) !== 'undefined' && deconcept.SWFObjectUtil.getPlayerVersion().major >= 6)
    {
      swfObject = new SWFObject(swf_url, name+"_swfo", width, height, "9.0.28", background_color);
      swfObject.addParam("allowFullScreen", allow_fullscreen ? "true" : "false");
      swfObject.addParam("allowScriptAccess", "always");
      //swfObject.addParam("wmode", "transparent");
      swfObject.addVariable("pano", xml_url);

      for(var idx in loadParams) {
        swfObject.addVariable(loadParams[idx].name, loadParams[idx].value);
      }

      // so.useExpressInstall("krpano/swfobject/expressinstall.swf");
      swfObject.setAttribute("xiRedirectUrl", window.location);
      if ( swfObject.write(parent_id) ) { /*var mousewheelfixes = new SWFkrpanoMouseWheel(so); */} else {
        alert('An error occurred while creating a krpano instance.');
      }
    }
    else
    {
      $("#"+parent_id).html('<a href="http://www.adobe.com/go/getflashplayer/" target="_blank">Scarica il player flash aggiornato '+
        '<img src="http://www.macromedia.com/images/shared/download_buttons/get_flash_player.gif" />'+
        '</a>');
    }
    // ]]>
    return swfObject;
  };


  s4ntc.vem.Krpano.prototype.call = function() {
    return this._element.call.apply(this._element, arguments);
  };

  s4ntc.vem.Krpano.prototype.set = function() {
    return this._element.set.apply(this._element, arguments);
  };

  s4ntc.vem.Krpano.prototype.get = function() {
    return this._element.get.apply(this._element, arguments);
  };

  s4ntc.vem.Krpano.prototype.loadpano = function(pano_url) {
    this.call(['loadpano(',pano_url,',null,MERGE,BLEND(2));wait(BLEND);jseventcall(notify,onblenddone);'].join(''));
  };

  s4ntc.vem.Krpano.prototype.getMouseCartesianCoordinates = function() {
    return {
      x: this.get('mouse.x'),
      y: this.get('mouse.y')
    };
  };

  s4ntc.vem.Krpano.prototype.getMouseSphericalCoordinates = function() {
    this.call('screentosphere(mouse.x,mouse.y,mouseath,mouseatv)');
    return {
      ath: this.get('mouseath'),
      atv: this.get('mouseatv')
    };
  };


  s4ntc.vem._KrpanoSwfUrl = '/krpano/krpano.swf';

  s4ntc.vem.VemKrpanoPlayer = function(viewport, controller, options) {
    var defaults = {
      krpano: {
        swf_url: window.location.host+'/krpano/krpano.swf',
        name: viewport._name
      }
    };

    s4ntc.vem.VemPlayer.call(this, viewport, controller, $.extend(true, {}, defaults, options));

    // Register to the hub
    this._krpanoPlayerId = s4ntc.vem.VemKrpanoPlayerHub.players.length;
    s4ntc.vem.VemKrpanoPlayerHub.players[this._krpanoPlayerId] = this;

    var krpanoParentId = this._vemViewport._selector.substr(1);

    this._krpano = new s4ntc.vem.Krpano(krpanoParentId, this._options.krpano);

    this._queue = new s4ntc.tools.events.EventQueue();
    this._waitOnReady();
    this._queue.start();
  };
  s4ntc.vem.VemKrpanoPlayer.prototype = new s4ntc.vem.VemPlayer();
  
  s4ntc.vem.Vem.prototype.PLAYERS['krpano'] = s4ntc.vem.VemKrpanoPlayer;

  s4ntc.vem.VemKrpanoPlayer.prototype._waitOnReady = function() {
    this._queue.enqueue(function(when) {
      this._vemViewport._element.bind('playerready', function() {
        when.resolve();
      });
      return false;
    }, [], this);
  };

  s4ntc.vem.VemKrpanoPlayer.prototype.waitFor = function(event_name) {
    this._queue.enqueue(function(when) {
      this._vemViewport._element.bind(event_name, function() {
        when.resolve();
      });
      return false;
    }, [], this);
  };

  s4ntc.vem.VemKrpanoPlayer.prototype.load = function(pano_url, params) {
    var me = this;

    // Build params set action
    var params_set_action = [];
    for(var param_name in params) {
      params_set_action.push('set(',param_name,', \'',params[param_name], '\'); ');
    }
    params_set_action = params_set_action.join('');

    this.krpanoCall(function(krpano) {
      me._waitOnReady();
      krpano.loadpano(pano_url);
    });   
    
    this.krpanoCall(function(krpano) {
      krpano.call(params_set_action);
    });
    
  };
  
  s4ntc.vem.VemKrpanoPlayer.prototype.krpanoCall = function(callback) {
    if(typeof callback == 'function') {
      this._queue.enqueue(callback, [this._krpano], {});
    }
  };
  s4ntc.vem.VemKrpanoPlayer.prototype.delayQueue = function(millis) {
    this._queue.delay(millis);
  };

  s4ntc.vem.VemKrpanoPlayer.prototype.execute = function(pano_id, action_name, destination_id, load_map) {
    this._vemController.playerEvent(action_name, arguments);
  };

  s4ntc.vem.VemKrpanoPlayer.prototype.notify = function(pano_id, event_name) {
    switch (event_name) {
      case 'onremovingpano':
        break;
      case 'onloadcomplete'://'ready':
        this._vemController.playerEvent('playerready', []);
        this._vemController.globalEvent('playerready', []);
      case 'onblenddone':
        this._vemController.playerEvent('onblenddone', []);
        this._vemController.globalEvent('onblenddone', []);
      break;
      default:
        break;
    }
    this._vemController.playerEvent(event_name, arguments);
  };

  s4ntc.vem.VemKrpanoPlayerHub = {
    players: [],
    call: function(player_id, method_name) {
      //console.log(arguments)
      var player = s4ntc.vem.VemKrpanoPlayerHub.players[player_id];
      var apply_args = [];
      for(var i = 2; i < arguments.length; i++) {
        apply_args.push(arguments[i])
      }
      player[method_name].apply(player, apply_args);
    }
  };


})(jQuery, window.s4ntc !== undefined ? window.s4ntc : (window.s4ntc = {}));
