﻿/// DEBUG CLASS ///
//© 2008 SeatQuest LLC.
function DEBUG(args)
{
    this.args=args;
    if(!this.args){this.args={};}
    
    this.queue={};
    this.timers={};
    this.elapsed={};
    this.errors={};
    this.output={};
    this.time_stamp={};
    
    
    //BOGDAN 
    var _this = this;
    if(this.args.key_hook)
    {
        framework.observe(window, 'load', function(e){_this.create_window(e);}, false);
        framework.observe(document, 'keydown', function(e){_this.key_down_handler(e);}, false);
        framework.observe(document, 'keyup', function(e){_this.key_up_handler(e);}, false);
        framework.observe(document, 'keypress', function(e){_this.key_press_handler(e);}, false);    
    }        
};


DEBUG.prototype.args={
    active:null,
    add_categories:null,
    key_hook:null
};
//DEBUG.prototype.errors=null;
//DEBUG.prototype.output=null;
//DEBUG.prototype.timers={};
//DEBUG.prototype.elapsed={};
//DEBUG.prototype.time_stamp={};
DEBUG.prototype.changes={};
DEBUG.prototype.shiftPressed=0;
//DEBUG.prototype.queue={
//    apply_to:null
//};

DEBUG.prototype.start=function(s){this.changes[s]=s;this.timers[s]= new Date().getTime(); };
DEBUG.prototype.stop=function(s){if(this.timers[s]){this.elapsed[s]=(new Date().getTime()-this.timers[s]);} return this.elapsed[s];};
DEBUG.prototype.time=function(id,exec)
{
    if(typeof exec=='function')
    {
        this.start(id);
        exec();
        this.stop(id);
    }else{
        if(!exec){
            this.start(id);
        }else{
            this.stop(id);
        }
    }
};

DEBUG.prototype.window_id='div_framework_debug';
DEBUG.prototype.window_created=null;
DEBUG.prototype.create_window=function()
{
    var _this=this;
    var e=document.createElement('div');
    try
    {
        e.style.position='absolute';
        e.style.left='0px';
        e.style.bottom='0px';
        e.style.zIndex='1999';
        e.style.width='300px';
        e.style.display='none';
        e.style.padding='3px';
        
        e.style.fontSize='10px';
        e.style.fontFamily='MS Sans Serif';
        e.style.backgroundColor='White';
        e.style.borderRight='1px solid gray';
        e.style.borderTop='1px solid gray';

        e.id=this.window_id;
        var body = document.getElementsByTagName('body')[0];
        if(body)
        {
            body.appendChild(e);
            this.window_created=true;
            if(this.queue.apply_to){this.queue.apply_to();}
        }
    }catch(err){
        this.debug.error("DEBUG->create_window",err);
    }    
};

DEBUG.prototype.hide=function()
{
    //if(!id){id=this.args.id;}
    var id=this.window_id;
    var e =document.getElementById(id);
    if(e)
    {
        e.style.display='none';
    }
};

DEBUG.prototype.post=function()
{
    //CHRIS
    var operations=new StringBuilder(), times=new StringBuilder();
    for(var s in this.elapsed)
    {
        operations.append(";"+s);
        times.append(";"+this.elapsed[s]);
    }
    //ELI initiate an asynchronious ajax call.
    new AJAX("../profile.aspx",function(){},"operation="+operations.toString().substr(1)+"&pid="+query("pid")+"&elapsed="+times.toString().substr(1));
};

DEBUG.prototype.clear=function()
{   
    this.timers={};
    this.elapsed={};
    this.time_stamp={};
    this.changes={};
    this.output=null;
};

DEBUG.prototype.apply_to=function()
{  
    var _this=this;
    if(!this.args.active){return;}
    if(!this.window_created){this.queue.apply_to=function(){_this.apply_to();};}else{this.queue.apply_to=null;}
    
    var id=this.window_id;
    var e=document.getElementById(id);
    if(e)
    {
        e.style.display='';
        e.innerHTML=this.toString(true);
    }
};

DEBUG.prototype.add_categories=function(obj)
{
    for(var s in obj)
    {
        var e= obj[s];
        this.add_category(s,e);
    }
};

DEBUG.prototype.add_category=function(name,obj)
{
    if(!this.args.categories){this.args.categories={};}
    this.args.categories[name]=obj;
};

DEBUG.prototype.parse_category=function(name,obj,sb,sb_html,element,limit)
{

    if(obj){
        if(name)
        {
            sb.append( name + '\t->\t' +"\r\n");
            sb_html.append('<div style="float:left"><b>' + name + '</b></div><div style="float:right"></div><br/>');
        }
        for(var s in obj){

            if(s=='no_total') continue;
            var c=this.changes[s] ? 'color:red;':'';
            var value=obj[s];
            if(element){value=value[element];}
            if(!value){value=obj[s];}
            if(limit){value=value.toString().substring(0,limit);}
            sb.append(s + "\t->\t" + value + "\r\n");
            sb_html.append('<div style="float:left;border:0px solid black;'+c+'">' + s + '</div><div style="float:right;border:0px solid gray;'+c+'">' + value + "</div><br/>");
        }
    }
};

DEBUG.prototype.calcualte_totals=function(obj,element)
{
    var total=0;
    for(var s in obj)
    {
        if(s=='no_total')continue;
        var value=obj[s];
        if(element){value=value[element];}
        if(!value){value=obj[s];}
        total+=parseInt(value);
    }
    return total;
};

DEBUG.prototype.toString=function(args)
{   

    var sb=new StringBuilder();
    var sb_html=new StringBuilder();

    this.parse_category("Timers",this.elapsed,sb,sb_html);
    this.parse_category(null,{Total:this.calcualte_totals(this.elapsed)},sb,sb_html);

    //ELI collect debug categories fro other objeects.
    if(this.args.add_categories)
    {
        var categories=null;
        if(typeof this.args.add_categories =='object'){categories=this.args.add_categories;}
        if(typeof this.args.add_categories =='function'){categories=this.args.add_categories();}
        this.add_categories(categories);
    }
    
    //ELI add categories
    for(var s in this.args.categories)
    {
        sb.append("\r\n");
        sb_html.append('<br/>'); 
        var obj=this.args.categories[s];
        this.parse_category(s,obj,sb,sb_html);
        if(!obj.no_total) {this.parse_category(null,{Total:this.calcualte_totals(obj)},sb,sb_html);}
    }

    if(this.errors)
    {
        sb.append("\r\n");
        sb_html.append('<br/>');
        this.parse_category("Errors",this.errors,sb,sb_html,'message')
    }
    
    if(this.output)
    {
        sb.append("\r\n");
        sb_html.append('<br/>');    
        this.parse_category("Messages",this.output,sb,sb_html)    
    }
     
    //ELI clear the changes list
    this.changes={}; 

    if(!args){return sb.toString();}else{return sb_html.toString();}
    
};

DEBUG.prototype.print=function(name,value)
{
    if(!this.output){this.output={};}
    this.changes[name]=name;
    this.output[name]=value;

};

DEBUG.prototype.key_down_handler=function(event)
{
    if(event.shiftKey) this.shiftPressed = 1;
};


DEBUG.prototype.key_up_handler=function(event)
{
    /* there's no event.shiftKey onkeyup response
    so this detects it */
    if (event.keyCode == 18 || event.charCode == 18) 
    {
        this.shiftPressed = 0;
    }
};

DEBUG.prototype.key_press_handler=function(event) 
{
    if (this.shiftPressed == 1) {
        if(event.keyCode == 84 || event.charCode == 84)
        {
            this.args.active=true;
            this.apply_to();
        }
        if(event.keyCode == 82 || event.charCode == 82)
        {
            this.args.active=false;
            this.hide();
        }        
    }
};


DEBUG.prototype.trap=function(name,fn)
{
    try
    {
        fn();
    }catch(err){
        this.error(name,err);
    }

};

DEBUG.prototype.error=function(name,value)
{
    if(!this.errors){this.errors={};}
    this.changes['err_'+name]=name;
    this.errors[name]=value;
};