﻿/// <reference path="~/TopletsResources/js/jquery-vsdoc.js" />

if (typeof (TD) == 'undefined') {
    var TD = {};
    TD.Toplets = {};
}

TD.Framework = {
    PageOnLoad: function() {
        TD.Framework.IsPageLoaded = true;

        if (!TD.Framework.IsInFrame()) {
            //param shouls starts from "popup"
            var QueryParams = TD.Framework.ParseQueryString(document.location);

            if (QueryParams['popuplogin'] != null && QueryParams['popuplogin'] == "true")
                TD.Framework.PopupLogin();

            if (QueryParams['PopupResetPassword2'] != null && QueryParams['PopupResetPassword2'] == "true" && QueryParams['rCode'] != null && QueryParams['uCode'] != null)
                TD.Framework.PopupResetPassword2(QueryParams['rCode'], QueryParams['uCode']);

            if (QueryParams['popupactivation'] != null && QueryParams['popupactivation'] == "true" && QueryParams['ACode'] != null)
                TD.Framework.PopupActivation(QueryParams['ACode']);
            if (QueryParams['popupactivation'] != null && QueryParams['popupactivation'] == "true")
                TD.Framework.PopupActivation('');




        }
    },

    IsPageLoaded: false,

    Browser: {
        IE: !!(window.attachEvent && navigator.userAgent.indexOf('Opera') === -1),
        Opera: navigator.userAgent.indexOf('Opera') > -1,
        WebKit: navigator.userAgent.indexOf('AppleWebKit/') > -1,
        Gecko: navigator.userAgent.indexOf('Gecko') > -1 && navigator.userAgent.indexOf('KHTML') === -1,
        MobileSafari: !!navigator.userAgent.match(/Apple.*Mobile.*Safari/)
    },

    IncDecFontSize: function(_obj, _vector) {
        var curFontSize;
        if (typeof jQuery != "undefined")
            curFontSize = parseInt(jQuery(_obj).css("fontSize"));
        else if (typeof Prototype != "undefined")
            curFontSize = parseInt(_obj.getStyle('fontSize'));

        if (!_obj.DefaultFontSize)
            _obj.DefaultFontSize = curFontSize;

        if (_vector == 0)
            _obj.style.fontSize = _obj.DefaultFontSize + 'px';
        else {
            var newVal = curFontSize + _vector;
            _obj.style.fontSize = newVal + 'px';
        }
        return false;
    },

    IsInFrame: function() {
        return !(window.top == window);
    },

    EvalScript: function(scripts) {
        try {
            if (scripts != '') {
                var script = "";
                scripts = scripts.replace(/<script[^>]*>([\s\S]*?)<\/script>/gi, function() {
                    if (scripts !== null) script += arguments[1] + '\n';
                    return '';
                });
                if (script) (window.execScript) ? window.execScript(script) : window.setTimeout(script, 0);
            }
            return false;
        }
        catch (e) {
            alert(e)
        }
    },

    ReadCookie: function(name) {
        if (document.cookie.length == 0)
            return null;
        var search = name + "=";
        offset = document.cookie.indexOf(search);
        if (offset == -1)
            return null;
        offset += search.length;
        end = document.cookie.indexOf(";", offset);
        if (end == -1) end = document.cookie.length;
        var cookieValue = unescape(document.cookie.substring(offset, end))
        return cookieValue;
    },

    // writeCookie("myCookie", "my name", 24); // Stores the string "my name" in the cookie "myCookie" which expires after 24 hours.
    WriteCookie: function(name, value, hours, host) {
        var expire = "";
        if (hours != null) {
            expire = new Date((new Date()).getTime() + hours * 3600000);
            expire = "; expires=" + expire.toGMTString();
        }
        var path = (host) ? "; path=" + host : "; path=/";
        document.cookie = name + "=" + escape(value) + expire + path;
    },

    Popup: function(url, title, width, height) {
        var link = {
            title: '', //title, iframe will show title
            href: url,
            className: "iframe",
            rel: ""
        };
        var options = {
            overlayShow: true,
            width: width,
            height: height,
            showCloseButton: true,
            hideOnContentClick: false,
            padding: 0
        };
        jQuery(link).fancybox(options).trigger('click');
        return false;
    },

    ClosePopup: function(reload) {
        if (TD.Framework.IsInFrame()) {
            window.top.TD.Framework.ClosePopup();
            return false;
        }
        if (reload === true) {
            var QueryParams = TD.Framework.ParseQueryString(document.location);
            if (QueryParams['ReturnUrl'] != null)
                document.location.href = QueryParams['ReturnUrl'];
            else {
                var url = new String(document.location.href);
                url = url.replace(/popup[\w\d]+=[^&]+/i, "");
                url = url.replace(/&{2,}/, "&");
                document.location.href = url;
            }
        }
        else
            jQuery.fancybox.close()
    },
    ClosePopupViaProxy: function(iframeid, reload) {
        try {
            top.TD.Framework.ClosePopup(reload);
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, 'TD.Framework.ClosePopup(' + reload + ');');
        }
    },


    PopupLogin: function(width, height) {
        if (!width)
            width = TD.Config.AppDafults.PopupLoginWidth;
        if (!height)
            height = TD.Config.AppDafults.PopupLoginHeight;
        var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
        TD.Framework.Popup(host + TD.Config.AppDafults.PopupLoginPath, '', width, height);
        return false;
    },
    PopupLoginViaProxy: function(iframeid) {
        try {
            top.TD.Framework.PopupLogin();
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, 'TD.Framework.PopupLogin();');
        }
    },

    PopupRegistration: function(width, height) {
        if (!width)
            width = TD.Config.AppDafults.PopupRegistrationWidth;
        if (!height)
            height = TD.Config.AppDafults.PopupRegistrationHeight;
        var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
        TD.Framework.Popup(host + TD.Config.AppDafults.PopupRegistrationPath, '', width, height);
    },
    PopupRegistrationViaProxy: function(iframeid) {
        try {
            top.TD.Framework.PopupRegistration();
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, 'TD.Framework.PopupRegistration();');
        }
    },

    PopupActivation: function(aCode, width, height) {
        if (!width)
            width = TD.Config.AppDafults.PopupActivationWidth;
        if (!height)
            height = TD.Config.AppDafults.PopupActivationHeight;
        var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
        aCode = (!!aCode) ? '&ACode=' + aCode : "";
        TD.Framework.Popup(host + TD.Config.AppDafults.PopupActivationPath + aCode, '', width, height);
    },
    PopupActivationViaProxy: function(iframeid) {
        try {
            top.TD.Framework.PopupActivation();
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, 'TD.Framework.PopupActivation();');
        }
    },


    PopupResetPassword: function(width, height) {
        if (!width)
            width = TD.Config.AppDafults.PopupResetPasswordWidth;
        if (!height)
            height = TD.Config.AppDafults.PopupResetPasswordHeight;
        var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
        TD.Framework.Popup(host + TD.Config.AppDafults.PopupResetPasswordPath, '', width, height);
    },
    PopupResetPasswordViaProxy: function(iframeid) {
        try {
            top.TD.Framework.PopupResetPassword();
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, 'TD.Framework.PopupResetPassword();');
        }
    },

    PopupResetPassword2: function(rCode, uCode, width, height) {
        if (!width)
            width = TD.Config.AppDafults.PopupResetPasswordWidth;
        if (!height)
            height = TD.Config.AppDafults.PopupResetPasswordHeight;
        var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
        TD.Framework.Popup(host + TD.Config.AppDafults.PopupResetPassword2Path + 'rCode=' + rCode + '&uCode=' + uCode, '', width, height);
    },


    CallFbLoginViaProxy: function(iframeid) {
        try {
            top.TD.Facebook.ProcessLogin();
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, 'TD.Facebook.ProcessLogin();');
        }
    },
    CallFbLogoutViaProxy: function(iframeid) {
        try {
            top.TD.Facebook.ProcessLogout('/');
        }
        catch (err) {
            TD.Framework.xDomainSender(iframeid, "TD.Facebook.ProcessLogout('/');");
        }
    },

    Logout: function() {
        var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
        document.location = host + TD.Config.AppDafults.LogoutPath + escape(document.location.href);
        return false;
    },

    //update to jquery func
    ContentInject: function(_URL, _ID, _Params) {
        var ID;
        if (!_ID) {
            ID = 'ContentInject' + Math.random() * 5000;
            document.write('<div id="' + ID + '"></div>')
        }
        else
            ID = _ID;

        jQuery.get(_URL, _Params,
			function(data) {
			    elem = document.getElementById(ID);
			    if (elem == null)
			        return;
			    elem.innerHTML = data;
			    //jQuery("#" + ID).html(data);
			    TD.Framework.EvalScript(data);
			});
    },

    JSInsert: function(url) {
        document.write('<scr' + 'ipt type="text/javascript" src="' + url + '"></scr' + 'ipt>')
    },

    JSLoad: function(url) {
        scriptEl = document.createElement("script")
        scriptEl.setAttribute("type", "text/javascript")
        scriptEl.setAttribute("charset", "utf-8")
        scriptEl.setAttribute("src", url)
        document.getElementsByTagName('head')[0].appendChild(scriptEl)
    },

    //update to jquery func
    AddLoadEvent: function(func) { //TD.AddLoadEvent(function() { TD.JSLoad('/toplets/maps/topsmap.js') })
        if (typeof func == "string") {
            var funcstr = func
            func = function() { return eval(funcstr) }
        }
        var oldonload = window.onload
        if (typeof window.onload != 'function') {
            window.onload = func
        } else {
            window.onload = function() {
                oldonload()
                func()
            }
        }
    },

    WaitUntilExists: function(obj, func) {
        if (typeof obj == "undefined") {
            window.setTimeout(1000, function() { TD.Framework.WaitUntilExists(obj, func) })
        } else {
            func()
        }
    },

    //Deprecated
    viewmore: function(divid, expandid, collapseid) {
        thisdiv = document.getElementById(divid);
        expand = document.getElementById(expandid);
        collaps = document.getElementById(collapseid);
        if (thisdiv.style.display == "none") {
            thisdiv.style.display = "block";
            expand.style.display = "none";
            collaps.style.display = "block";
        } else {
            thisdiv.style.display = "none";
            expand.style.display = "block";
            collaps.style.display = "none";
        }
    },

    ParseQueryString: function(QueryString) {
        //var query = window.location.search.substring(1);
        var query = new String(QueryString);

        var qsParm = new Array();
        var pos = query.indexOf('?');
        if (pos > 0)
            query = query.substring(pos + 1);

        var parms = query.split('&');
        for (var i = 0; i < parms.length; i++) {
            pos = parms[i].indexOf('=');
            if (pos > 0)
                qsParm[parms[i].substring(0, pos)] = unescape(parms[i].substring(pos + 1)); ;
        }
        return qsParm;
    },


    GetReturnUrl: function(url) {
        if (url == undefined || url == null || url == '')
            return '/';
        var QueryParams = TD.Framework.ParseQueryString(url);
        if (QueryParams['ReturnUrl'] != null)
            return QueryParams['ReturnUrl'];
        return url;
    },

    //TABS
    /*
    var TabsInfo = {
    TabsId: new Array('HomeT1', 'HomeT2', 'HomeT3', 'HomeT4'),
    DefaultTabId: 'HomeT1',
    BoxesId: new Array('HomeTEl1', 'HomeTEl2', 'HomeTEl3', 'HomeTEl4'),
    TabActiveClass: 'HomeTActive',
    TabOverClass: 'HomeTActive',
    TabClass: 'HomeTActive',
    TabHash: '#tab123?'
    }
    */
    Tabs: function(TabsInfo) {
        if (TabsInfo.TabsId.length != TabsInfo.BoxesId.length) {
            alert('TabsInfo.TabsId.length != TabsInfo.BoxesId.length');
            return;
        }

        var defaultTab = document.location.hash.indexOf(TabsInfo.TabHash);
        if (defaultTab > -1)
            TabsInfo.DefaultTabId = document.location.hash.substr(TabsInfo.TabHash.length, document.location.hash.length - TabsInfo.TabHash.length);

        var OnTabClick = function() {
            this.TabsInfo.ActiveTabId = this.Id;
            for (i = 0; i < this.TabsInfo.TabsId.length; i++) {
                var tab = jQuery('#' + this.TabsInfo.TabsId[i]);
                if (tab[0].Active) {
                    tab[0].Active = false;
                    tab.addClass(this.TabsInfo.TabClass);
                    tab.removeClass(this.TabsInfo.TabActiveClass);
                    tab.removeClass(this.TabsInfo.TabOverClass);

                    jQuery('#' + TabsInfo.BoxesId[i]).hide();
                }
            }
            this.Active = true;
            jQuery(this).removeClass(this.TabsInfo.TabClass);
            jQuery(this).removeClass(this.TabsInfo.TabOverClass);
            jQuery(this).addClass(this.TabsInfo.TabActiveClass);

            jQuery('#' + TabsInfo.BoxesId[jQuery.inArray(this.Id, this.TabsInfo.TabsId)]).show();

            document.location.hash = TabsInfo.TabHash + this.Id;
            return false;
        }
        var OnTabMouseOver = function() {
            if (!this.Active) {
                jQuery(this).addClass(this.TabsInfo.TabOverClass);
                jQuery(this).removeClass(this.TabsInfo.TabClass);
            }
        }
        var OnTabMouseOut = function() {
            if (!this.Active) {
                jQuery(this).addClass(this.TabsInfo.TabClass);
                jQuery(this).removeClass(this.TabsInfo.TabOverClass);
            }
        }
        for (i = 0; i < TabsInfo.TabsId.length; i++) {
            var tab = jQuery('#' + TabsInfo.TabsId[i]);
            tab[0].Id = TabsInfo.TabsId[i];
            tab[0].TabsInfo = TabsInfo;
            tab[0].Active = false;
            tab.bind("click", OnTabClick);
            tab.bind("mouseover", OnTabMouseOver);
            tab.bind("mouseout", OnTabMouseOut);
            jQuery('#' + TabsInfo.BoxesId[i]).hide();
        }

        //var fxx = OnTabClick.bind(jQuery(TabsInfo.DefaultTabId));
        //fxx();
        jQuery('#' + TabsInfo.DefaultTabId).trigger('click');
    },

    xDomainSender: function(iframeid, message) {
        var elem = document.getElementById(iframeid);
        var txt = new String(elem.src);
        var pos = txt.indexOf("#");
        if (pos > 0)
            txt = txt.substr(0, pos);
        elem.contentWindow.location = txt + '#' + message;
        elem.width = elem.width > 50 ? 50 : 100;
    },

    xDomainReceiver: function(message) {
        var message = document.location.hash;
        if (message.length > 0) {
            message = message.substr(1);
            if (target == "top")
                top.TD.Framework.xDomainEvaluator(message);
            else
                parent.frames["hostFrame"].TD.Framework.xDomainEvaluator(message);
        }
    },

    xDomainEvaluator: function(message) {
        //alert(message);
        eval(message);
        //jQuery('#xdomaindiv').html(message);
    }
}

TD.Framework.DelegateType = function(_type) {
    this.type = _type;
};
TD.Framework.DelegateType.prototype.listeners = {};
TD.Framework.DelegateType.prototype.Add = function(f) {
    if (typeof (this.listeners[this.type]) == 'undefined')
        this.listeners[this.type] = [];
    this.listeners[this.type].push(f);
};
TD.Framework.DelegateType.prototype.Invoke = function() {
    if (typeof (this.listeners[this.type]) == 'undefined')
        return;
    var c = this.listeners[this.type].length;
    var v = this.listeners[this.type];
    for (di = 0; di < c; di++)
        v[di]();
};


///////////////////////////////////////////////////////
//   TD.Facebook
///////////////////////////////////////////////////////


TD.Facebook = {
    FbAPIKey: "",
    IsRequireParseDomTree: false,
    IsInitialized: false,
    IsSecureConnection: false,

    PageOnLoad: function() {
        if (this.IsRequireParseDomTree) {
            this.ParseDomTree();
        }
    },

    OnInit: new TD.Framework.DelegateType('TD_Facebook_OnInit'),

    Init: function(id) {
        if (!!window.FB) {
            /*
            FB.Bootstrap.init(this.FbAPIKey, "/xd_receiver.htm", { reloadIfSessionStateChanged: false });
            FB.Bootstrap.ensureInit(function()
            {
            FB.FBDebug.isEnabled=false;
            FB.FBDebug.logLevel=0;
                
            TD.Facebook.IsInitialized = true;
            TD.Facebook.OnInit.Invoke();
                
            });		
            return;
            */

            var receiver = (this.IsSecureConnection === true) ? "/xd_receiver_ssl.htm" : "/xd_receiver.htm";
            FB.init(this.FbAPIKey, receiver, { /*"reloadIfSessionStateChanged": false*/
        });
        FB.ensureInit(function() {
            ///FB.FBDebug.isEnabled=false;
            ///FB.FBDebug.logLevel=0;
            TD.Facebook.IsInitialized = true;
            TD.Facebook.OnInit.Invoke();
            //TD.Facebook.IsRequireParseDomTree = false;
        });
    }
},

EnsureLoad: function(_f) {
    if (TD.Facebook.IsInitialized === true)
        _f();
    else
        this.OnInit.Add(_f);
},

ProcessLogin: function() {
    TD.Facebook.EnsureLoad(function() {
        var curentDocument = document;
        /*
        if (TD.Framework.IsInFrame()){
        FB = window.top.FB;
        //window.top.TD.Facebook.ProcessLogin();
        //return false;
        }
        */
        FB.ensureInit(function() {

            /*
            FB.Connect.requireSession();
            if(!FB.Facebook.get_sessionWaitable().result)
            FB.Facebook.get_sessionWaitable().add_changed(function()
            var sessionWaitable=FB.Facebook.get_sessionWaitable();
            if(sessionWaitable.get_isReady()&&sessionWaitable.result)
            FB.Facebook.get_sessionWaitable().waitUntilReady( function( session ) {
            */

            FB.Connect.requireSession(function() {

                $.get(TD.Config.AppDafults.PopupFbIsOurUserPath + FB.Connect.get_loggedInUser(), function(data) {
                    var host = (TD.Config.AppDafults.UseSSL === true) ? "https://" + window.location.hostname : "";
                    if (data == "true") {
                        document.location.href = host + TD.Config.AppDafults.PopupFbHandlerPath + escape(TD.Framework.GetReturnUrl(document.location));
                    }
                    else {
                        var width = TD.Config.AppDafults.PopupFbWidth;
                        var height = TD.Config.AppDafults.PopupFbHeight;
                        var url = host + TD.Config.AppDafults.PopupFbHandlerPath + escape(TD.Config.AppDafults.PopupClosePath);
                        TD.Framework.Popup(url, '', width, height);
                    }
                });
            }, null, true);
            return false;
        });
    });

    return false;
},

ProcessLogout: function(ReturnUrl) {
    TD.Facebook.EnsureLoad(function() {
        if (TD.Framework.IsInFrame()) {
            window.top.TD.Facebook.ProcessLogout(ReturnUrl);
            return false;
        }
        TD.Framework.ClosePopup();
        if (typeof (ReturnUrl) == 'function')
            FB.Connect.logout(ReturnUrl);
        else {
            if (ReturnUrl == undefined)
                ReturnUrl = escape(TD.Framework.GetReturnUrl(document.location));
            FB.Connect.logoutAndRedirect(TD.Config.AppDafults.AppLogout + ReturnUrl);
            //FB.Connect.logoutAndRedirect('/facebook/handler?Logout=true&ReturnUrl=' + ReturnUrl);
        }
    });
},

ParseDomTree: function(Timeout) {
    if (!(Timeout == undefined)) {
        setTimeout(this.ParseDomTree, 3000);
        return;
    }
    if (TD.Framework.IsPageLoaded === true && this.IsInitialized === true) {
        if (!(typeof (FB) == 'undefined')) {
            FB.ensureInit(function() {
                FB.XFBML.Host.parseDomTree();
            });
            return;
        }
    }
    else
        this.IsRequireParseDomTree = true;
},

PostFeed: function(FeedData, callback) {
    TD.Facebook.EnsureLoad(function() {
        var attachment = {
            'name': FeedData.AssetTitle,
            'href': FeedData.AssetUrl,
            'caption': FeedData.FeedCaption + FeedData.AssetType,
            //'description':'description description description description',
            'properties': [/*
										{text:'text prop 1',href:'http://google.com'},
										{text:'text prop 2',href:'http://google.com'},
										{text:'text prop 3',href:'http://google.com'},
										{text:'text prop 4',href:'http://google.com'}
										*/
									],
            'media': []
        };

        for (var i = 0; i < FeedData.AssetImages.length; i++)
            attachment.media[i] = {
                href: FeedData.AssetUrl,
                type: 'image',
                src: FeedData.AssetImages[i].src
            };

        var action_link = [
											{
											    'text': 'Read ' + FeedData.AssetType,
											    'href': FeedData.AssetUrl
											}
										];

        var msg = FeedData.CommentTitle + "\n\r" + FeedData.Comment;

        callback = (callback != null && typeof callback == 'function') ? callback : function(post_id, exception, data) { };

        FB.ensureInit(function() {
            FB.Connect.streamPublish(msg, attachment, action_link, null, FeedData.FeedUserMessagePrompt, callback);
        });
    });



    return false;

    /*
    var TemplateBundleId = FeedData.TemplateBundleId;
    var user_message_prompt = "What do you think of this " + FeedData.AssetType.toLowerCase() + "?";
    var user_message = { value: FeedData.Comment };

		        for (var i = 0; i < FeedData.AssetImages.length; i++)
    FeedData.AssetImages[i].href = FeedData.AssetUrl;

		        var template_data = {
    "WebSiteUrl": FeedData.WebSiteUrl,
    "WebSiteName": FeedData.WebSiteName,
    "AssetType": FeedData.AssetType,
    "AssetUrl": FeedData.AssetUrl,
    "AssetTitle": FeedData.AssetTitle,
    "images": FeedData.AssetImages
    }
    var body_general = '';

		        callback = (callback != null && typeof callback == 'function') ? callback : function() { };

		        FB.ensureInit(function() {
    FB.Connect.showFeedDialog(TemplateBundleId, template_data, [], body_general, null, FB.RequireConnect.require, callback, user_message_prompt, user_message);
    });
    */
},

GlobalFeedData: null,

FeedDataObj: function(PropertiesObject) {
    //TemplateBundleId, WebSiteName, AssetType
    //AssetTitle, AssetImages, AssetVideo
    //FeedCaption, FeedUserMessagePrompt
    for (x in PropertiesObject)
        this[x] = PropertiesObject[x];

    this.AssetUrl = document.location.href;
    this.WebSiteUrl = document.location.href;
    // will setted later
    this.CommentTitle = "";
    this.Comment = "";
},

calbacFunc: function(data) {
    var fff = 5;
},

AppFriends: function(callback) {
    TD.Facebook.EnsureLoad(function() {
        callback = (callback != null && typeof callback == 'function') ? callback : TD.Facebook.calbacFunc;
        FB.ensureInit(function() {
            FB.Facebook.apiClient.friends_getAppUsers(callback);
            //FB.Facebook.apiClient.friends_getLists(TD.Facebook.calbacFunc);
        });
        return;

        FB.ensureInit(function() {
            FB.Connect.inviteConnectUsers();
        });
        return;

        //var api = FB.ApiClient(TD.Facebook.FbAPIKey);
        var dddd = "dfsdf";
        FB.ensureInit(function() {
            FB.Connect.InviteConnectUsers();
            return;

            FB.Bootstrap.requireFeatures(["ApiClient"], function() {
                alert('ApiClient')
                //FB.Connect.inviteConnectUsers();
                /*
                var f = function(cont) {
                alert(cont);
                }
                //FB.ApiClient.friends_get(f);
                FB.ApiClient.Friends.get(function() { alert('a'); });
                //Friends.getAppUsers(f);
                */
            });
        });
    });
},

InviteFriends: function(excludeAppFriends) {
    TD.Facebook.EnsureLoad(function() {
        FB.ensureInit(function() {
            var showFunc = function(exclude_ids) {
                var dialog = new FB.UI.FBMLPopupDialog('Invite your friends to join', '');
                var fbml = '<fb:fbml>' +
											'<fb:request-form style="width:630px; height:540px;" action="' + document.location.href + '?" method="POST" invite="true" type="Invite Friends" ' +
												'content="You have been invited to visit website <fb:req-choice url=\'http://' + document.location.host + '/\' label=\'Ok\' />" >' +
													'<fb:multi-friend-selector showborder="false" rows="4" cols="4" exclude_ids="' + exclude_ids + '" actiontext="Invite your friends" bypass="cancel" showborder="false" />' +
											'</fb:request-form>' +
									'</fb:fbml>';
                dialog.setFBMLContent(fbml);
                dialog.setContentWidth(630);
                dialog.setContentHeight(560);
                dialog.show();
            }
            if (excludeAppFriends)
                FB.Facebook.apiClient.friends_getAppUsers(function(data) {
                    showFunc(data.join(","));
                });
            else
                showFunc('');
        });
    });
    return false;
},

ifUserConnected: function(YesFunction, NoFunction) {
    TD.Facebook.EnsureLoad(function() {
        FB.ensureInit(function() {
            FB.Bootstrap.requireFeatures(["Connect"], function() {
                FB.Connect.ifUserConnected(
								(YesFunction ? YesFunction : null),
								(NoFunction ? NoFunction : null)
							);
            });
        });
    });
    //FB.Bootstrap.requireFeatures(["ApiClient"], function() {
    //var sesrec = FB.Facebook.apiClient.get_session();
    //});
},

Temp: function() {
    //connect.getUnconnectedFriendsCount
}
}


///////////////////////////////////////////////////////
//   TD.md5
///////////////////////////////////////////////////////


TD.md5 = {
    /*
    * A JavaScript implementation of the RSA Data Security, Inc. MD5 Message
    * Digest Algorithm, as defined in RFC 1321.
    * Version 2.1 Copyright (C) Paul Johnston 1999 - 2002.
    * Other contributors: Greg Holt, Andrew Kepert, Ydnar, Lostinet
    * Distributed under the BSD License
    * See http://pajhome.org.uk/crypt/md5 for more info.
    */

    /*
    * Configurable variables. You may need to tweak these to be compatible with
    * the server-side, but the defaults work in most cases.
    */
    hexcase: 0,  /* hex output format. 0 - lowercase; 1 - uppercase        */
    b64pad: "", /* base-64 pad character. "=" for strict RFC compliance   */
    chrsz: 8,  /* bits per input character. 8 - ASCII; 16 - Unicode      */

    /*
    * These are the functions you'll usually want to call
    * They take string arguments and return either hex or base-64 encoded strings
    */
    hex_md5: function(s) { return this.binl2hex(this.core_md5(this.str2binl(s), s.length * this.chrsz)); },
    b64_md5: function(s) { return this.binl2b64(this.core_md5(this.str2binl(s), s.length * this.chrsz)); },
    str_md5: function(s) { return this.binl2str(this.core_md5(this.str2binl(s), s.length * this.chrsz)); },
    hex_hmac_md5: function(key, data) { return this.binl2hex(this.core_hmac_md5(key, data)); },
    b64_hmac_md5: function(key, data) { return this.binl2b64(this.core_hmac_md5(key, data)); },
    str_hmac_md5: function(key, data) { return this.binl2str(this.core_hmac_md5(key, data)); },

    /*
    * Perform a simple self-test to see if the VM is working
    */
    md5_vm_test: function() {
        return this.hex_md5("abc") == "900150983cd24fb0d6963f7d28e17f72";
    },

    /*
    * Calculate the MD5 of an array of little-endian words, and a bit length
    */
    core_md5: function(x, len) {
        /* append padding */
        x[len >> 5] |= 0x80 << ((len) % 32);
        x[(((len + 64) >>> 9) << 4) + 14] = len;

        var a = 1732584193;
        var b = -271733879;
        var c = -1732584194;
        var d = 271733878;

        for (var i = 0; i < x.length; i += 16) {
            var olda = a;
            var oldb = b;
            var oldc = c;
            var oldd = d;

            a = this.md5_ff(a, b, c, d, x[i + 0], 7, -680876936);
            d = this.md5_ff(d, a, b, c, x[i + 1], 12, -389564586);
            c = this.md5_ff(c, d, a, b, x[i + 2], 17, 606105819);
            b = this.md5_ff(b, c, d, a, x[i + 3], 22, -1044525330);
            a = this.md5_ff(a, b, c, d, x[i + 4], 7, -176418897);
            d = this.md5_ff(d, a, b, c, x[i + 5], 12, 1200080426);
            c = this.md5_ff(c, d, a, b, x[i + 6], 17, -1473231341);
            b = this.md5_ff(b, c, d, a, x[i + 7], 22, -45705983);
            a = this.md5_ff(a, b, c, d, x[i + 8], 7, 1770035416);
            d = this.md5_ff(d, a, b, c, x[i + 9], 12, -1958414417);
            c = this.md5_ff(c, d, a, b, x[i + 10], 17, -42063);
            b = this.md5_ff(b, c, d, a, x[i + 11], 22, -1990404162);
            a = this.md5_ff(a, b, c, d, x[i + 12], 7, 1804603682);
            d = this.md5_ff(d, a, b, c, x[i + 13], 12, -40341101);
            c = this.md5_ff(c, d, a, b, x[i + 14], 17, -1502002290);
            b = this.md5_ff(b, c, d, a, x[i + 15], 22, 1236535329);

            a = this.md5_gg(a, b, c, d, x[i + 1], 5, -165796510);
            d = this.md5_gg(d, a, b, c, x[i + 6], 9, -1069501632);
            c = this.md5_gg(c, d, a, b, x[i + 11], 14, 643717713);
            b = this.md5_gg(b, c, d, a, x[i + 0], 20, -373897302);
            a = this.md5_gg(a, b, c, d, x[i + 5], 5, -701558691);
            d = this.md5_gg(d, a, b, c, x[i + 10], 9, 38016083);
            c = this.md5_gg(c, d, a, b, x[i + 15], 14, -660478335);
            b = this.md5_gg(b, c, d, a, x[i + 4], 20, -405537848);
            a = this.md5_gg(a, b, c, d, x[i + 9], 5, 568446438);
            d = this.md5_gg(d, a, b, c, x[i + 14], 9, -1019803690);
            c = this.md5_gg(c, d, a, b, x[i + 3], 14, -187363961);
            b = this.md5_gg(b, c, d, a, x[i + 8], 20, 1163531501);
            a = this.md5_gg(a, b, c, d, x[i + 13], 5, -1444681467);
            d = this.md5_gg(d, a, b, c, x[i + 2], 9, -51403784);
            c = this.md5_gg(c, d, a, b, x[i + 7], 14, 1735328473);
            b = this.md5_gg(b, c, d, a, x[i + 12], 20, -1926607734);

            a = this.md5_hh(a, b, c, d, x[i + 5], 4, -378558);
            d = this.md5_hh(d, a, b, c, x[i + 8], 11, -2022574463);
            c = this.md5_hh(c, d, a, b, x[i + 11], 16, 1839030562);
            b = this.md5_hh(b, c, d, a, x[i + 14], 23, -35309556);
            a = this.md5_hh(a, b, c, d, x[i + 1], 4, -1530992060);
            d = this.md5_hh(d, a, b, c, x[i + 4], 11, 1272893353);
            c = this.md5_hh(c, d, a, b, x[i + 7], 16, -155497632);
            b = this.md5_hh(b, c, d, a, x[i + 10], 23, -1094730640);
            a = this.md5_hh(a, b, c, d, x[i + 13], 4, 681279174);
            d = this.md5_hh(d, a, b, c, x[i + 0], 11, -358537222);
            c = this.md5_hh(c, d, a, b, x[i + 3], 16, -722521979);
            b = this.md5_hh(b, c, d, a, x[i + 6], 23, 76029189);
            a = this.md5_hh(a, b, c, d, x[i + 9], 4, -640364487);
            d = this.md5_hh(d, a, b, c, x[i + 12], 11, -421815835);
            c = this.md5_hh(c, d, a, b, x[i + 15], 16, 530742520);
            b = this.md5_hh(b, c, d, a, x[i + 2], 23, -995338651);

            a = this.md5_ii(a, b, c, d, x[i + 0], 6, -198630844);
            d = this.md5_ii(d, a, b, c, x[i + 7], 10, 1126891415);
            c = this.md5_ii(c, d, a, b, x[i + 14], 15, -1416354905);
            b = this.md5_ii(b, c, d, a, x[i + 5], 21, -57434055);
            a = this.md5_ii(a, b, c, d, x[i + 12], 6, 1700485571);
            d = this.md5_ii(d, a, b, c, x[i + 3], 10, -1894986606);
            c = this.md5_ii(c, d, a, b, x[i + 10], 15, -1051523);
            b = this.md5_ii(b, c, d, a, x[i + 1], 21, -2054922799);
            a = this.md5_ii(a, b, c, d, x[i + 8], 6, 1873313359);
            d = this.md5_ii(d, a, b, c, x[i + 15], 10, -30611744);
            c = this.md5_ii(c, d, a, b, x[i + 6], 15, -1560198380);
            b = this.md5_ii(b, c, d, a, x[i + 13], 21, 1309151649);
            a = this.md5_ii(a, b, c, d, x[i + 4], 6, -145523070);
            d = this.md5_ii(d, a, b, c, x[i + 11], 10, -1120210379);
            c = this.md5_ii(c, d, a, b, x[i + 2], 15, 718787259);
            b = this.md5_ii(b, c, d, a, x[i + 9], 21, -343485551);

            a = this.safe_add(a, olda);
            b = this.safe_add(b, oldb);
            c = this.safe_add(c, oldc);
            d = this.safe_add(d, oldd);
        }
        return Array(a, b, c, d);

    },

    /*
    * These functions implement the four basic operations the algorithm uses.
    */
    md5_cmn: function(q, a, b, x, s, t) {
        return this.safe_add(this.bit_rol(this.safe_add(this.safe_add(a, q), this.safe_add(x, t)), s), b);
    },
    md5_ff: function(a, b, c, d, x, s, t) {
        return this.md5_cmn((b & c) | ((~b) & d), a, b, x, s, t);
    },
    md5_gg: function(a, b, c, d, x, s, t) {
        return this.md5_cmn((b & d) | (c & (~d)), a, b, x, s, t);
    },
    md5_hh: function(a, b, c, d, x, s, t) {
        return this.md5_cmn(b ^ c ^ d, a, b, x, s, t);
    },
    md5_ii: function(a, b, c, d, x, s, t) {
        return this.md5_cmn(c ^ (b | (~d)), a, b, x, s, t);
    },

    /*
    * Calculate the HMAC-MD5, of a key and some data
    */
    core_hmac_md5: function(key, data) {
        var bkey = this.str2binl(key);
        if (bkey.length > 16) bkey = this.core_md5(bkey, key.length * this.chrsz);

        var ipad = Array(16), opad = Array(16);
        for (var i = 0; i < 16; i++) {
            ipad[i] = bkey[i] ^ 0x36363636;
            opad[i] = bkey[i] ^ 0x5C5C5C5C;
        }

        var hash = this.core_md5(ipad.concat(this.str2binl(data)), 512 + data.length * this.chrsz);
        return this.core_md5(opad.concat(hash), 512 + 128);
    },

    /*
    * Add integers, wrapping at 2^32. This uses 16-bit operations internally
    * to work around bugs in some JS interpreters.
    */
    safe_add: function(x, y) {
        var lsw = (x & 0xFFFF) + (y & 0xFFFF);
        var msw = (x >> 16) + (y >> 16) + (lsw >> 16);
        return (msw << 16) | (lsw & 0xFFFF);
    },

    /*
    * Bitwise rotate a 32-bit number to the left.
    */
    bit_rol: function(num, cnt) {
        return (num << cnt) | (num >>> (32 - cnt));
    },

    /*
    * Convert a string to an array of little-endian words
    * If chrsz is ASCII, characters >255 have their hi-byte silently ignored.
    */
    str2binl: function(str) {
        var bin = Array();
        var mask = (1 << this.chrsz) - 1;
        for (var i = 0; i < str.length * this.chrsz; i += this.chrsz)
            bin[i >> 5] |= (str.charCodeAt(i / this.chrsz) & mask) << (i % 32);
        return bin;
    },

    /*
    * Convert an array of little-endian words to a string
    */
    binl2str: function(bin) {
        var str = "";
        var mask = (1 << this.chrsz) - 1;
        for (var i = 0; i < bin.length * 32; i += this.chrsz)
            str += String.fromCharCode((bin[i >> 5] >>> (i % 32)) & mask);
        return str;
    },

    /*
    * Convert an array of little-endian words to a hex string.
    */
    binl2hex: function(binarray) {
        var hex_tab = this.hexcase ? "0123456789ABCDEF" : "0123456789abcdef";
        var str = "";
        for (var i = 0; i < binarray.length * 4; i++) {
            str += hex_tab.charAt((binarray[i >> 2] >> ((i % 4) * 8 + 4)) & 0xF) +
			   hex_tab.charAt((binarray[i >> 2] >> ((i % 4) * 8)) & 0xF);
        }
        return str;
    },

    /*
    * Convert an array of little-endian words to a base-64 string
    */
    binl2b64: function(binarray) {
        var tab = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
        var str = "";
        for (var i = 0; i < binarray.length * 4; i += 3) {
            var triplet = (((binarray[i >> 2] >> 8 * (i % 4)) & 0xFF) << 16)
					| (((binarray[i + 1 >> 2] >> 8 * ((i + 1) % 4)) & 0xFF) << 8)
					| ((binarray[i + 2 >> 2] >> 8 * ((i + 2) % 4)) & 0xFF);
            for (var j = 0; j < 4; j++) {
                if (i * 8 + j * 6 > binarray.length * 32) str += this.b64pad;
                else str += tab.charAt((triplet >> 6 * (3 - j)) & 0x3F);
            }
        }
        return str;
    }
}


///////////////////////////////////////////////////////
//   TD.Forms
///////////////////////////////////////////////////////


TD.Forms = {

    IsPressedEnter: function(e) {
        var event = window.event || e;
        var key = event.keyCode ? event.keyCode : event.which ? event.which : event.charCode;
        return (key == 13);
    },

    IsEmail: function(_email) {
        ///^(\w+[\-\.])*\w+@(\w+\.)+[A-Za-z]+$/
        email_re1 = /(@.*@)|(\.\.)|(@\.)|(\.@)|(^\.)|(\.$)/;
        email_re2 = /^([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\]?)$/;
        if (_email == "" || email_re1.exec(_email) || !email_re2.exec(_email))
            return false;
        return true;
    },

    //C#
    //Date: DateTime.ToShortDateString();
    //Date and Time: DateTime.ToShortDateString() + " " + DateTime.ToShortTimeString();
    AddCalendar: function(input, showsTime) {
        if (input.HasCalendar === undefined) {
            input.HasCalendar = true;

            if (input.id == '')
                input.id = 'Calendar' + Math.floor(Math.random() * 1001);
            jQuery(input).attr("readonly", "readonly");
            //jQuery(input).addClass("td_input_calendar");

            showsTime = (showsTime == true) ? true : false;
            var ifFormat = (showsTime == true) ? "%m/%d/%Y %I:%M %p" : "%m/%d/%Y"; //"en-US"

            Calendar.setup({
                inputField: input.id,
                ifFormat: ifFormat,
                showsTime: showsTime,
                timeFormat: "24", //"en-US"
                eventName: 'click'
            });
        }
    },

    Select: {

        OptionAdd: function(_objSelect, _text, _value) {
            if (TD.Framework.Browser.IE) {
                var _objOption = document.createElement("OPTION");
                _objOption.text = _text;
                _objOption.value = _value;
                _objSelect.add(_objOption);
            }
            else {// if (TD.Framework.Browser.Gecko || TD.Framework.Browser.Opera) {
                var _nextOption = _objSelect.options.length;
                _objOption = new Option(_text, _value);
                _objSelect.options[_nextOption] = _objOption
            }
        },
        OptionInsert: function(_objSelect, _text, _value, _position) {
            _itemsTextsBackup = new Array()
            _itemsValuesBackup = new Array()
            for (i = _position; i < _objSelect.length; i++) {
                _itemsTextsBackup.push(_objSelect[i].text)
                _itemsValuesBackup.push(_objSelect[i].value)
            }
            TD.Forms.Select.OptionDelete(_objSelect, _position)
            TD.Forms.Select.OptionAdd(_objSelect, _text, _value)
            for (i = 0; i < _itemsValuesBackup.length; i++)
                TD.Forms.Select.OptionAdd(_objSelect, _itemsTextsBackup[i], _itemsValuesBackup[i])
        },
        OptionDelete: function(_objSelect, _start, _length) {
            if (_start == null || _start < 0)
                _start = 0;
            if (_length == null || _length < 0 || _length == 0)
                _elements = _objSelect.length;
            else
                _elements = (_length > (_objSelect.length - _start)) ? _objSelect.length - _start : _start + _length;
            for (i = _start; i < _elements; i++)
                _objSelect.options[_start] = null;
        },
        OptionSelect: function(_objSelect, _index) {
            _index = (_index == null || _index >= _objSelect.length) ? 0 : _index;
            if (TD.Framework.Browser.IE || TD.Framework.Browser.Opera)
                _objSelect.selectedIndex = _index
            if (TD.Framework.Browser.Gecko)
                _objSelect.options[_index].selected = true
        },
        OptionSelectValue: function(_objSelect, _value) {
            _elements = _objSelect.length
            for (i = 0; i < _elements; i++) {
                if (_objSelect.options[i].value == _value) {
                    _objSelect.options[i].selected = true;
                    return;
                }
            }
        }
    },
    Serialize: function(selector, isOutputJSON) {
        var $src = jQuery(selector).clone(true);
        var $form = jQuery("<form></form>").append($src);
        return (!isOutputJSON) ? $form.serialize() : $form.serializeArray();
    }
}


TD.OnLoad = function() {
    TD.Framework.PageOnLoad();
    TD.Facebook.PageOnLoad();
}

var TDFrameworkOldInit = window.onload;
if (typeof window.onload != 'function') {
    window.onload = TD.OnLoad;
}
else {
    window.onload = function() {
        TDFrameworkOldInit();
        TD.OnLoad();
    }
}