/*
 * Basic class
 */
function MiyabiBasic(){
  // version
  this.version = '0.0.6';

  // error handler
  this.errorHandler = function(e){alert(e)};
}


/*
 * Controller class
 */
function MiyabiController(InstanceName){
  this.constructor = MiyabiBasic;
  this.constructor();

  try {
    // instance name
    this.instanceName = InstanceName;

    // timer
    this.checkLocationInterval = 200;

    // module
    this.defaultModule = 'Index';
    this.modules = new Object();
    this.moduleBaseName = "MiyabiModule";

    // action
    this.defaultAction = 'Index';
    this.actionBaseName = "MiyabiAction";

    // view
    this.defaultView = 'Index';
    this.viewBaseName = "MiyabiView";

    // check whether changed
    this.checkLocation();
  } catch(e){
    this.errorHandler(e);
  }
}
MiyabiController.prototype = new MiyabiBasic;


MiyabiController.prototype.checkLocation = function(){
  try {
    // analyze hash
    var module, action;
    if(location.hash.match(/^#M&([A-z0-9-_]+)?(&([A-z0-9-_]+))?$/)){
      module = RegExp.$1;
      if(RegExp.$3){
        action = RegExp.$3;
      }
    }
    module = module || this.defaultModule;
    action = action || this.defaultAction;

    // return if module and action are not changed
    if(module == this.module && action == this.action){
      this.setTimeoutCheckLocation();
      return true;
    }

    // set module and action
    this.module = module;
    this.action = action;

    // load module
    this.loadModule();
    this.setTimeoutCheckLocation();
    return true;
  } catch(e){
    this.errorHandler(e);
  }
}


MiyabiController.prototype.setTimeoutCheckLocation = function(){
  try {
    setTimeout(this.instanceName+".checkLocation()", this.checkLocationInterval);
  } catch(e){
    this.errorHandler(e);
  }
}


MiyabiController.prototype.loadModule = function(){
  try {
    // new module class
    var new_class = "new "+this.moduleBaseName+this.module;
    this.moduleInstance = eval(new_class);

    // exec exec method
    this.moduleInstance.exec();

    // exec action
    return this.execAction();
  } catch(e){
    this.errorHandler(e);
  }
}


MiyabiController.prototype.execAction = function(){
  try {
    // exec action
    var new_class = "new "+this.actionBaseName+this.module+this.action+"(this.moduleInstance)";
    this.actionInstance = eval(new_class);

    // exec exec method
    this.actionInstance.exec(this.moduleInstance);

    // get view
    return this.getView();
  } catch(e){
    this.errorHandler(e);
  }
}


MiyabiController.prototype.getView = function(){
  try {
    // get view
    var new_class = "new "+this.viewBaseName+this.module+this.action+"(this.moduleInstance)";
    this.viewInstance = eval(new_class);

    // exec exec method
    this.viewInstance.exec(this.moduleInstance);

    return true;
  } catch(e){
    this.errorHandler(e);
  }
}


/*
 * Module class
 */
function MiyabiModule(){
  this.constructor = MiyabiBasic;
  this.constructor();
}
MiyabiModule.prototype = new MiyabiBasic;
MiyabiModule.prototype.exec = function(){};


/*
 * Action class
 */
function MiyabiAction(){
  this.constructor = MiyabiBasic;
  this.constructor();
}
MiyabiAction.prototype = new MiyabiBasic;
MiyabiAction.prototype.exec = function(){};


/*
 * View class
 */
function MiyabiView(){
  this.constructor = MiyabiBasic;
  this.constructor();
}
MiyabiView.prototype = new MiyabiBasic;
MiyabiView.prototype.exec = function(){};


/*
 * init
 */
var Miyabi;
window.onload = function(){
  Miyabi = new MiyabiController("Miyabi");
}

