【ToolKit】轻量级JS库

优点:

丢弃了一些不常用的方法(jQuery.fn):slideUp、fadeIn、animate等;

新增获取子节点的方法(ToolKit.fn):firstChild,lastChild等;

新增ToolKit.Threads线程操作函数(有效解决自定义弹窗同时运行的问题);

加入JSON对象(JSON.parse和JSON.stringify);

重写ToolKit.toString方法为JSON.stringify,ToolKit.get和ToolKit.post的dataType为json格式,使用更方便;

代码更小,但功能一样强大,选择器、异步取数和基本方法一个都不少,最重要的是逻辑清晰,初学者都可以进行二次开发。

(function(window) {
    var
        version = "1.1.1",
        arr = [],
        push = arr.push,
        slice = arr.slice,
        concat = arr.concat,
        indexOf = arr.indexOf ||
        function(o, from) {
            var
                len = this.length,
                i = from ? from < 0 ? Math.max(0, len + from) : from : 0;
            for (; i < len; i++) {
                if (this[i] === o) {
                    return i;
                }
            }
            return -1;
        },

        support = {},
        class2type = {},
        toString = class2type.toString,
        hasOwn = class2type.hasOwnProperty,
        cssfix = ["Moz", "Webkit", "O", "ms"],
        cssform = {
            letterSpacing: "0",
            fontWeight: "400"
        },
        csslock = {
            position: "absolute",
            visibility: "hidden",
            display: "block"
        },

        rtrim = /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,
        rsingleTag = /^<([\w-]+)\s*\/?>(?:<\/\1>|)$/,
        rxhtmlTag = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:-]+)[^>]*)\/>/gi,

        rmsPrefix = /^-ms-/,
        rdashAlpha = /-([\da-z])/gi,
        fcamelCase = function(all, letter) {
            return letter.toUpperCase();
        },
        isArrayLike = function(o) {
            if (o == null) {
                return false;
            }
            var len = o.length,
                type = ToolKit.type(o);
            if (type === "function" || type === "string" || o.window === o || len == null) {
                return false;
            }
            return type === "array" || len === 0 || o.nodeType === 1 || (typeof len === "number") && (len - 1 in o);
        },

        ToolKit = function(selector, context) {
            return new ToolKit.fn.init(selector, context);
        };
    ToolKit.extend = function() {
        var
            key, value, length, isArray, configs, options, i = 1,
            limit = false,
            len = arguments.length,
            target = arguments[0];

        if (typeof target === "boolean") {
            limit = target;
            target = arguments[i++] || {};
        }
        if (typeof target !== "object" && typeof target !== "function" && typeof target !== "array") {
            target = {};
        }
        for (; i < len; i++) {
            if (!!(options = arguments[i])) {
                for (key in options) {
                    value = options[key];
                    configs = target[key];
                    if (value === configs || value === undefined) continue;
                    if (limit && value && (ToolKit.isPlainObject(value) || (isArray = ToolKit.isArray(value)))) {
                        target[key] = ToolKit.extend(limit, target[key] || (isArray ? [] : {}), value);
                    } else {
                        target[key] = value;
                    }
                }
            }
        }
        return target;
    }
    ToolKit.improve = function() {
        var
            key, value, length, isArray, configs, options, i = 1,
            limit = false,
            len = arguments.length,
            target = arguments[0];

        if (typeof target === "boolean") {
            limit = target;
            target = arguments[i++] || {};
        }
        if (typeof target !== "object" && typeof target !== "function" && typeof target !== "array") {
            target = {};
        }
        for (; i < len; i++) {
            if (!!(options = arguments[i])) {
                for (key in options) {
                    value = options[key];
                    configs = target[key];
                    if (value === configs || value === undefined) continue;
                    if (limit && value && (ToolKit.isPlainObject(value) || (isArray = ToolKit.isArray(value)))) {
                        target[key] = ToolKit.improve(limit, target[key] || (isArray ? [] : {}), value);
                        isArray = false;
                    } else {
                        target[key] = configs || value;
                    }
                }
            }
        }
        return target;
    }
    ToolKit.extend(ToolKit, {
        kit: "kit",
        zIndex: 1000,
        type: function(o) {
            return o === null ? "null" : typeof o === "object" ? class2type[toString.call(o)] || "object" : typeof o;
        },
        isString: function(o) {
            return ToolKit.type(o) === "string";
        },
        isFunction: function(o) {
            return ToolKit.type(o) === "function";
        },
        isArray: Array.isArray ||
            function(obj) {
                return ToolKit.type(obj) === "array";
            },
        isNumber: function(o) {
            return !ToolKit.isArray(0) && Math.abs(o - parseFloat(o)) >= 0;
        },
        isWindow: function(o) {
            return !!o && (o === o.window);
        },
        inArray: function(o, list, from) {
            if (ToolKit.isArray(list)) {
                return indexOf.call(list, o, from);
            }
            return -1;
        },
        isEmptyObject: function(o) {
            for (var i in o) {
                return false;
            }
            return true;
        },
        isPlainObject: function(o) {
            if (!o || ToolKit.type(o) !== "object" || !!o.nodeType || ToolKit.isWindow(o)) {
                return false;
            }
            try {
                if (o.constructor && !hasOwn.call(o, "constructor") && !hasOwn.call(o.constructor.prototype, "constructor")) {
                    return false;
                }
            } catch (e) {
                return false;
            }
            var key;
            for (key in o) {}
            return key === undefined || hasOwn.call(o, key);
        },
        support: support
    });
    ToolKit.extend(ToolKit, {
        error: function(msg) {
            throw new Error(msg);
        },
        syntaxError: function(msg) {
            throw new SyntaxError(msg);
        }
    });
    ToolKit.extend(ToolKit, {
        each: function(o, iterator, context) {
            var i = 0;
            if (isArrayLike(o)) {
                for (var len = o.length; i < len; i++) {
                    if (iterator.call(context || o[i], i, o[i], o) === false) {
                        break;
                    }
                }
            } else {
                for (i in o) {
                    if (iterator.call(context || o[i], i, o[i], o) === false) {
                        break;
                    }
                }
            }
            return o;
        },
        map: function(o, iterator, context) {
            var val, i = 0,
                list = [];
            if (isArrayLike(o)) {
                for (var len = o.length; i < len; i++) {
                    if ((val = iterator.call(context, o[i], i, o)) != null) list.push(val);
                }
            } else {
                for (i in o) {
                    if ((val = iterator.call(context, o[i], i, o)) != null) list.push(val);
                }
            }
            return concat.apply([], list);
        },
        merge: function(to, from) {
            var i = 0,
                l = +to.length || 0,
                len = (from && +from.length) || -1;
            while (i < len) {
                to[l++] = from[i++];
            }
            if (len !== len) {
                while (from[i] !== undefined) {
                    to[l++] = from[i++];
                }
            }
            to.length = l;
            return to;
        },
        makeArray: function(arr, results) {
            var r = results || [];
            if (arr != null) {
                if (isArrayLike(Object(arr))) {
                    ToolKit.merge(r, typeof arr === "string" ? [arr] : arr);
                } else {
                    push.call(r, arr);
                }
            }
            return r;
        }
    });

    ToolKit.extend(ToolKit, {
        trim: function(string) {
            return string == null ? "" : String(string).replace(rtrim, "");
        },
        camelCase: function(string) {
            return String(string).replace(rmsPrefix, "ms-").replace(rdashAlpha, fcamelCase);
        },
        globalEval: function(code) {
            code = ToolKit.trim(code);
            if (code) {
                if (code.indexOf("use strict") > -1) {
                    script = document.createElement("script");
                    script.text = code;
                    document.head.appendChild(script).parentNode.removeChild(script);
                } else {
                    (window.execScript ||
                        function(data) {
                            window["eval"].call(window, data);
                        })(code);
                }
            }
        },
        htmlPrefilter: function(html) {
            return html.replace(rxhtmlTag, "<$1></$2>");
        }
    });


    var
        rtbody = /<tbody/i,
        rhtml = /<|&#?\w+;/,
        rtagName = /<([\w:]+)/,
        rleadingWhitespace = /^\s+/,
        rscriptType = (/^$|\/(?:java|ecma)script/i),
        whitespace = "[\\x20\\t\\r\\n\\f]",
        booleans = "checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",
        wrapMap = {
            option: [1, "<select multiple='multiple'>", "</select>"],
            legend: [1, "<fieldset>", "</fieldset>"],
            area: [1, "<map>", "</map>"],
            param: [1, "<object>", "</object>"],
            thead: [1, "<table>", "</table>"],
            tr: [2, "<table><tbody>", "</tbody></table>"],
            col: [2, "<table><tbody></tbody><colgroup>", "</colgroup></table>"],
            td: [3, "<table><tbody><tr>", "</tr></tbody></table>"],
            _default: support.htmlSerialize ? [0, "", ""] : [1, "X<div>", "</div>"]
        },
        rwhitespace = new RegExp(whitespace + "+", "g"),
        rcomma = new RegExp("^" + whitespace + "*," + whitespace + "*");
    wrapMap.optgroup = wrapMap.option;
    wrapMap.tbody = wrapMap.tfoot = wrapMap.colgroup = wrapMap.caption = wrapMap.thead;
    wrapMap.th = wrapMap.td;

    function buildFragment(elems, context, selection) {
        var elem, tmp, tag, wrap, index, counter, fragment = context.createDocumentFragment(),
            i = 0,
            list = [],
            len = elems.length;

        for (; i < len; i++) {
            elem = elems[i];
            if (elem || elem === 0) {
                if (ToolKit.type(elem) === "object") {
                    ToolKit.merge(list, elem.nodeType ? [elem] : elem);
                } else if (!rhtml.test(elem)) {
                    list.push(context.createTextNode(elem));
                } else {
                    tmp = tmp || fragment.appendChild(context.createElement("div"));
                    tag = (rtagName.exec(elem) || ["", ""])[1].toLowerCase();
                    wrap = wrapMap[tag] || wrapMap._default;
                    tmp.innerHTML = wrap[1] + ToolKit.htmlPrefilter(elem) + wrap[2];
                    index = wrap[0];
                    while (index--) {
                        tmp = tmp.lastChild;
                    }
                    if (!support.leadingWhitespace && !!(counter = rleadingWhitespace.exec(this))) {
                        list.push(context.createTextNode(counter[0]));
                    }
                    if (!support.tbody) {
                        var xml = (tag === "table" && !rtbody.test(this)) ? tmp.firstChild : match[1] === "<table>" && !rtbody.test(this) ? tmp : 0;
                        tbody = xml && xml.childNodes.firstChild;
                        do {
                            if (ToolKit.nodeName(tbody, "tbody") && !tbody.childNodes.length) {
                                xml.removeChild(tbody);
                            }
                        }
                        while (tbody && !!(tbody = tbody.nextSibling));
                    }
                    ToolKit.merge(list, tmp.childNodes);
                    tmp.textContent = "";
                    while (tmp.firstChild) {
                        tmp.removeChild(tmp.firstChild);
                    }
                    tmp = fragment.lastChild;
                }
            }
        }
        if (tmp) {
            fragment.removeChild(tmp);
        }
        i = 0;
        while (!!(elem = list[i++])) {
            if (selection && ToolKit.inArray(elem, selection) !== -1) {
                continue;
            }

            fragment.appendChild(elem);
        }
        return fragment;
    };

    ToolKit.extend(ToolKit, {
        parse: function(text, reviver) {
            return window.JOSN.parse(text, reviver);
        },
        toString: function(value, replacer, space) {
            return window.JOSN.stringify(value, replacer, space);
        },
        parseHTML: function(data, context) {
            if (!data || typeof data !== "string") {
                return null;
            }
            context = context || document;
            var html = rsingleTag.exec(data);
            if (html) {
                return [context.createElement(html[1])];
            }
            html = buildFragment([data], context);
            return ToolKit.merge([], html.childNodes);
        }
    });

    ToolKit.each(["Boolean", "Number", "String", "Function", "Array", "Date", "RegExp", "Error", "Object", "Document", "Symbol"], function() {
        class2type["[object " + this + "]"] = this.toLowerCase();
    });

    (function($) {
        var
            cx = /[\u0000\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,
            escapable = /[\\\"\x00-\x1f\x7f-\x9f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,
            indent, iterator, target = '',
            meta = {
                '\b': '\\b',
                '\t': '\\t',
                '\n': '\\n',
                '\f': '\\f',
                '\r': '\\r',
                '"': '\\"',
                '\\': '\\\\'
            };

        function quote(string) {
            escapable.lastIndex = 0;
            return escapable.test(string) ? '"' + string.replace(escapable, function(a) {
                var c = meta[a];
                return typeof c === 'string' ? c : '\\u' + ('0000' + a.charCodeAt(0).toString(16)).slice(-4);
            }) + '"' : '"' + string + '"';
        }

        function str(key, holder) {
            var
                i, // The loop counter.
                k, // The member key.
                v, // The member value.
                length, mind = target,
                partial, value = holder[key];
            if (value && $.isFunction(value.toJSON)) {
                value = value.toJSON(key);
            }
            if ($.isFunction(iterator)) {
                value = iterator.call(holder, key, value);
            }
            switch (typeof value) {
                case 'string':
                    return quote(value);
                case 'number':
                    return isFinite(value) ? String(value) : 'null';

                case 'boolean':
                case 'null':
                    return String(value);
                case 'object':
                    if (!value) {
                        return 'null';
                    }
                    target += indent;
                    partial = [];
                    if ($.isArray(value)) {
                        length = value.length;
                        for (i = 0; i < length; i += 1) {
                            partial[i] = str(i, value) || 'null';
                        }
                        v = partial.length === 0 ? '[]' : target ? '[\n' + target + partial.join(',\n' + target) + '\n' + mind + ']' : '[' + partial.join(',') + ']';
                        target = mind;
                        return v;
                    }
                    if (iterator && typeof iterator === 'object') {
                        length = iterator.length;
                        for (i = 0; i < length; i += 1) {
                            if (typeof iterator[i] === 'string') {
                                k = iterator[i];
                                v = str(k, value);
                                if (v) {
                                    partial.push(quote(k) + (target ? ': ' : ':') + v);
                                }
                            }
                        }
                    } else {
                        for (k in value) {
                            if (hasOwn.call(value, k)) {
                                v = str(k, value);
                                if (v) {
                                    partial.push(quote(k) + (target ? ': ' : ':') + v);
                                }
                            }
                        }
                    }
                    v = partial.length === 0 ? '{}' : target ? '{\n' + target + partial.join(',\n' + target) + '\n' + mind + '}' : '{' + partial.join(',') + '}';
                    target = mind;
                    return v;
            }
        }

        if (!$.isFunction(Date.prototype.toJSON)) {
            function f(n) {
                return n < 10 ? '0' + n : n;
            }
            Date.prototype.toJSON = function(key) {
                return isFinite(this.valueOf()) ? this.getUTCFullYear() + '-' + f(this.getUTCMonth() + 1) + '-' + f(this.getUTCDate()) + 'T' + f(this.getUTCHours()) + ':' + f(this.getUTCMinutes()) + ':' + f(this.getUTCSeconds()) + 'Z' : null;
            };

            String.prototype.toJSON = Number.prototype.toJSON = Boolean.prototype.toJSON = function(key) {
                return this.valueOf();
            };
        }
        $.improve(window.JSON = window.JSON || {}, {
            parse: function(text, reviver) {
                var j, walk = function(holder, key) {
                    var k, v, value = holder[key];
                    if (value && typeof value === 'object') {
                        for (k in value) {
                            if (Object.prototype.hasOwnProperty.call(value, k)) {
                                v = walk(value, k);
                                if (v !== undefined) {
                                    value[k] = v;
                                } else {
                                    delete value[k];
                                }
                            }
                        }
                    }
                    return reviver.call(holder, key, value);
                }
                text = String(text);
                cx.lastIndex = 0;
                if (cx.test(text)) {
                    text = text.replace(cx, function(a) {
                        return '\\u' + ('0000' + a.charCodeAt(0).toString(16)).slice(-4);
                    });
                }
                if (/^[\],:{}\s]*$/.test(
                        text.replace(/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g, '@').replace(/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, ']').replace(/(?:^|:|,)(?:\s*\[)+/g, ''))) {
                    j = eval('(' + text + ')');
                    return $.isFunction(reviver) ? walk({
                        '': j
                    }, '') : j;
                }
                $.error('JSON.parse');
            },
            stringify: function(value, replacer, space) {
                var i;
                indent = '';
                iterator = '';
                if ($.isNumber(space)) {
                    for (i = 0; i < space; i += 1) {
                        indent += ' ';
                    }
                } else if ($.isString(space)) {
                    indent = space;
                }
                iterator = replacer;
                if (
                    replacer && !$.isFunction(replacer) && (typeof replacer !== 'object' || typeof replacer.length !== 'number')) {
                    $.error('JSON.stringify');
                }
                return str('', {
                    '': value
                });
            }
        });
    })(ToolKit);

    var sortInput, hasDuplicate;
    var documentElement = document.documentElement;
    var rnative = /^[^{]+\{\s*\[native \w/;
    var check = function(tag, callbak) {
        if (arguments.length === 1) {
            callbak = tag;
            tag = "div";
        }
        var elem = document.createElement(tag);
        try {
            return !!callbak(elem);
        } catch (e) {
            return false;
        } finally {
            if (elem.parentNode) {
                elem.parentNode.removeChild(elem);
            }
            elem = null;
        }
    };
    if (rnative.test(document.getElementsByClassName)) {
        support.getElementsByClassName = check(function(div) {
            div.innerHTML = "<div class='a'></div><div class='a i'></div>";
            div.firstChild.className = "i";
            return div.getElementsByClassName("i").length === 2;
        });
    }
    if (rnative.test(document.querySelectorAll)) {
        support.querySelectorAll = true;
        var rquerySelectorAll = [];
        check(function(div) {
            div.innerHTML = "<select msallowclip=''><option selected=''></option></select>";
            if (div.querySelectorAll("[msallowclip^='']").length) {
                rquerySelectorAll.push("[*^$]=" + whitespace + "*(?:''|\"\")");
            }
            if (!div.querySelectorAll("[selected]").length) {
                rquerySelectorAll.push("\\[" + whitespace + "*(?:value|" + booleans + ")");
            }
            if (!div.querySelectorAll(":checked").length) {
                rquerySelectorAll.push(":checked");
            }
        });
        check(function(div) {
            var input = document.createElement("input");
            input.setAttribute("type", "hidden");
            input.id = "B";
            div.appendChild(document.createElement("div").appendChild(document.createElement("a")));
            div.appendChild(input).setAttribute("name", "D");
            if (div.querySelectorAll("[name=d]").length || !div.querySelectorAll("[name=D]").length) {
                rquerySelectorAll.push("name" + whitespace + "*[*^$|!~]?=");
            }
            if (div.querySelectorAll("input[id='b']").length || !div.querySelectorAll("input[id='B']").length) {
                rquerySelectorAll.push("id" + whitespace + "*[*^$|!~]?=");
            }
            if (!div.querySelectorAll(":enabled").length) {
                rquerySelectorAll.push(":enabled", ":disabled");
            }
            div.querySelectorAll("*,:x");
            rquerySelectorAll.push(",.*:");
        });
        check(function(div) {
            documentElement.appendChild(div).innerHTML = "<a id='toolkit'></a>" + "<select id='toolkit-\r\\' msallowcapture=''>" + "<option selected=''></option></select>";
            if (div.querySelectorAll("[msallowcapture^='']").length) {
                rquerySelectorAll.push("[*^$]=" + whitespace + "*(?:''|\"\")");
            }
            if (!div.querySelectorAll("[selected]").length) {
                rquerySelectorAll.push("\\[" + whitespace + "*(?:value|" + booleans + ")");
            }
            if (!div.querySelectorAll("[id~=toolkit-]").length) {
                rquerySelectorAll.push("~=");
            }
            if (!div.querySelectorAll(":checked").length) {
                rquerySelectorAll.push(":checked");
            }
            if (!div.querySelectorAll("a#toolkit+*").length) {
                rquerySelectorAll.push(".#.+[+~]");
            }
        });
        support.rquerySelectorAll = !rquerySelectorAll.length || new RegExp(rquerySelectorAll.join("|"));
    }
    if (rnative.test((support.matches = documentElement.matches || documentElement.webkitMatchesSelector || documentElement.mozMatchesSelector || documentElement.oMatchesSelector || documentElement.msMatchesSelector))) {
        support.matchesSelector = true;
        check(function(div) {
            var matchesSelector = [];
            support.disConnectedMatch = support.matches.call(div, "div");
            matches.call(div, "[s!='']:x");
            matchesSelector.push("!=", extensions);
            support.rmatchesSelector = new RegExp(matchesSelector.join("|"));
        });
    }
    support.getElementById = check(function() {
        document.documentElement.appendChild(div).id = "test";
        if (document.getElementById) {
            return !document.getElementsByName || !document.getElementsByName("test").length;
        }
    });
    support.getElementsByTagName = check(function(div) {
        div.appendChild(document.createComment(""));
        return !div.getElementsByTagName("*").length;
    });
    check("form", function(form) {
        support.enctype = !!form.enctype;
    });
    check("input", function(input) {
        input.type = "checkbox";
        support.checkOn = input.value !== "";
        input.value = "t";
        input.type = "radio";
        support.radioValue = input.value === "t";
    });
    check("select", function(select) {
        var option = select.appendChild(document.createElement("option"));
        select.disabled = true;
        support.optionSelected = option.selected;
        support.optionDisabled = !option.disabled;
    });
    check(function(div) {
        var a, t, style, input;
        div.setAttribute("className", "t"), div.innerHTML = "  <link/><table></table><a href='/a'>a</a><input type='checkbox'/><!--<span></span>-->";
        a = (t = div.getElementsByTagName("a")) ? t[0] : null;
        input = (t = div.getElementsByTagName("input")) ? t[0] : {};
        style = a && a.style;
        if (!style) {
            return;
        }
        support.leadingWhitespace = div.firstChild.nodeType === 3;
        support.leadingAnnotation = div.lastChild.nodeType === 8;
        support.tbody = !div.getElementsByTagName("tbody").length;
        support.htmlSerialize = !!div.getElementsByTagName("link").length;
        support.html5Clone = document.createElement("nav").cloneNode(true).outerHTML !== "<:nav></:nav>";
        support.attr = div.className !== "t";
        style.cssText = "float:left;opacity:.5;top:1px";
        support.opacity = style.opacity === "0.5";
        support.cssFloat = !!style.cssFloat;
        support.style = /top/.test(a.getAttribute("style"));
        support.hrefNormalized = a.getAttribute("href") === "/a";
    });
    check(function(div) {
        var
            i, len, value, target, style = div.style,
            list = ["boxSizing", "boxShadow", "animation", "transition", "transform", "transformOrigin", "transitionDelay", "filter"];
        checking = function(t) {
            if (t in style) return true;
            target = t.charAt(0).toUpperCase() + t.slice(1);
            for (var i = 0, len = cssfix.length; i < len; i++) {
                if ((cssfix[i] + target) in style) {
                    return true;
                }
            }
            return false;
        };
        for (i = 0, len = list.length; i < len; i++) {
            value = list[i];
            support[value] = checking(value)
        }
        for (i in {
                submit: true,
                change: true,
                focusin: true
            }) {
            value = "on" + i;
            support[i] = (value in window);
        }
    });
    check(function(div) {
        div.style.backgroundClip = "content-box";
        div.cloneNode(true).style.backgroundClip = "";
        support.clearCloneStyle = div.style.backgroundClip === "content-box";

        div.innerHTML = "<input type='radio' checked='checked' name='t'/>";
        support.checkClone = !!div.cloneNode(true).cloneNode(true).lastChild.checked;

        support.eventClone = false;
        var motheds = function() {
            support.eventClone = true;
        };
        if (div.addEventListener) {
            div.addEventListener("click", motheds, false);
        } else if (div.attachEvent) {
            div.attachEvent("onclick", motheds);
        }
        div.cloneNode(true).click();
    });

    var siblingCheck = function(a, b) {
        var cur = b && a,
            diff = cur && a.nodeType === 1 && b.nodeType === 1 && (~b.sourceIndex || MAX_NEGATIVE) - (~a.sourceIndex || MAX_NEGATIVE);
        if (diff) {
            return diff;
        }
        if (cur) {
            while ((cur = cur.nextSibling)) {
                if (cur === b) {
                    return -1;
                }
            }
        }
        return a ? 1 : -1;
    };

    var hasCompare = rnative.test(documentElement.compareDocumentPosition);
    var contains = hasCompare || rnative.test(documentElement.contains) ?
        function(a, b) {
            var adown = a.nodeType === 9 ? a.documentElement : a,
                bup = b && b.parentNode;
            return a === bup || !!(bup && bup.nodeType === 1 && (
                adown.contains ? adown.contains(bup) : a.compareDocumentPosition && a.compareDocumentPosition(bup) & 16));
        } : function(a, b) {
            if (b) {
                while ((b = b.parentNode)) {
                    if (b === a) {
                        return true;
                    }
                }
            }
            return false;
        };

    var sortOrder = hasCompare ?
        function(a, b) {

            if (a === b) {
                hasDuplicate = true;
                return 0;
            }
            var compare = !a.compareDocumentPosition - !b.compareDocumentPosition;
            if (compare) {
                return compare;
            }
            compare = (a.ownerDocument || a) === (b.ownerDocument || b) ? a.compareDocumentPosition(b) : 1;
            if (compare & 1 || (!support.sortDetached && b.compareDocumentPosition(a) === compare)) {
                if (a === document || a.ownerDocument === window.document && contains(window.document, a)) {
                    return -1;
                }
                if (b === document || b.ownerDocument === window.document && contains(window.document, b)) {
                    return 1;
                }
                return sortInput ? (indexOf(sortInput, a) - indexOf(sortInput, b)) : 0;
            }

            return compare & 4 ? -1 : 1;
        } : function(a, b) {
            if (a === b) {
                hasDuplicate = true;
                return 0;
            }

            var cur, i = 0,
                aup = a.parentNode,
                bup = b.parentNode,
                ap = [a],
                bp = [b];
            if (!aup || !bup) {
                return a === document ? -1 : b === document ? 1 : aup ? -1 : bup ? 1 : sortInput ? (indexOf(sortInput, a) - indexOf(sortInput, b)) : 0;
            } else if (aup === bup) {
                return siblingCheck(a, b);
            }
            cur = a;
            while ((cur = cur.parentNode)) {
                ap.unshift(cur);
            }
            cur = b;
            while ((cur = cur.parentNode)) {
                bp.unshift(cur);
            }
            while (ap[i] === bp[i]) {
                i++;
            }
            return i ? siblingCheck(ap[i], bp[i]) : ap[i] === window.document ? -1 : bp[i] === window.document ? 1 : 0;
        };

    var
        init, analysis, rmargin = (/^margin/),
        rnumber = /^[+-]?(\d+\.|)(\d+)$/,
        ropacity = /opacity\s*=\s*([^)]*)/,
        rposition = /^(top|right|bottom|left)$/,
        number = "[+-]?(?:\\d*\\.|)\\d+(?:[eE][+-]?\\d+|)",
        rsplitnumber = new RegExp("^(" + number + ")(.*)$", "i"),
        rrealnumber = new RegExp("^([+-])=(" + number + ")", "i"),
        rpercentnumber = new RegExp("^(" + number + ")(%)$", "i"),
        rstylenumber = new RegExp("^(" + number + ")[a-z%]+$", "i"),
        rnopxnumber = new RegExp("^(" + number + ")(?!px)[a-z%]+$", "i"),
        rfxnumber = new RegExp("^(?:([+-])=|)(" + number + ")([a-z%]*)$", "i"),
        booleans = "checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",
        rbooleans = new RegExp("^(?:" + booleans + ")$", "i"),
        fixNumber = {
            "columnCount": true,
            "fillOpacity": true,
            "flexGrow": true,
            "flexShrink": true,
            "fontWeight": true,
            "lineHeight": true,
            "opacity": true,
            "order": true,
            "orphans": true,
            "windows": true,
            "zIndex": true,
            "zoom": true
        },
        fix = function(o, key) {
            if (key in o) return key;
            var i = 0,
                fixkey;
            key = key.charAt(0).toUpperCase() + key.slice(1);
            while ((fixkey = cssfix[i++]) && !((fixkey = fixkey + key) in o)) {}
            return ToolKit.fx.props[key] = (fixkey || key);
        };
    if (window.getComputedStyle) {
        init = function(elem, key) {
            var width, minWidth, maxWidth, view = analysis(elem),
                style = elem && elem.style,
                value = view && (view.getPropertyValue(key) || view[key]) || style && style[key] || "";
            if (style && rnopxnumber.test(value) && !rmargin.test(key)) {
                width = style.width;
                minWidth = style.minWidth;
                maxWidth = style.maxWidth;
                style.minWidth = style.maxWidth = style.width = value;

                value = view.width;

                style.width = width;
                style.minWidth = minWidth;
                style.maxWidth = maxWidth;
            }
            return value && (value + "");
        }
        analysis = function(elem) {
            return elem && elem.ownerDocument && elem.ownerDocument.defaultView.getComputedStyle(elem, null);
        }
    } else {
        init = function(elem, key) {
            var left, rs, rsLeft, view = analysis(elem),
                style = elem && elem.style,
                value = view && view[name] || style && style[name] || "";
            if (style && rnopxnumber.test(value) && !rposition.test(name)) {
                left = style.left;
                rs = elem.runtimeStyle;
                rsLeft = rs && rs.left;
                if (rsLeft) {
                    rs.left = elem.currentStyle.left;
                }
                style.left = name === "fontSize" ? "1em" : value;

                value = style.pixelLeft + "px";

                style.left = left;
                if (rsLeft) {
                    rs.left = rsLeft;
                }
            }
            return (value != null) && ((value + "") || "auto");
        }
        analysis = function(elem) {
            return elem && elem.currentStyle;
        }
    }
    ToolKit.fx = {
        base: init,
        init: function(elem, key, value) {
            if (!elem || !key || !elem.nodeType || elem.nodeType === 3 || elem.nodeType === 8 || elem.nodeType === 9) {
                return;
            }
            key = ToolKit.camelCase(key);
            var
                hooks, style = elem.style,
                fixkey = ToolKit.fx.props[key] || fix(style, key);
            hooks = ToolKit.fx.hooks[fixkey] || ToolKit.fx.hooks[key];
            if (arguments.length === 2) {
                if (hooks && ("get" in hooks)) {
                    value = hooks.get(elem);
                }
                if (value == null) {
                    value = ToolKit.fx.base(elem, key);
                }
                if (value === "normal") {
                    value = cssform[key] || value;
                }
                return value;
            }
            if (value == null) {
                if (rbooleans.test(key)) {
                    if (support.input && support.attr || !rdefault.test(key)) {
                        elem[key] = false;
                    } else {
                        elem[ToolKit.camelCase("default-" + name)] = elem[key] = false;
                    }
                } else {
                    ToolKit.fx.init(elem, key, "");
                }
                elem.removeAttribute(key);
            }
            var type = ToolKit.type(value);
            if ((type === "string") && (result = rrealnumber.exec(value))) {
                type = "number";
                value = (result[1] + 1) * result[2] + parseFloat(ToolKit.fx.init(elem, key));
            }
            if (value == null || value !== value) {
                return value;
            }
            if (!fixNumber[key] && ((type === "number") && !rpercentnumber.test(value) || rnumber.test(value))) {
                value += "px";
            }
            if (!support.clearCloneStyle && value === "" && key.indexOf("background") === 0) {
                style[key] = "inherit";
            }
            if (!hooks || !("set" in hooks) || (value = hooks.set(elem, value)) != null) {
                try {
                    style[key] = value;
                } catch (e) {}
            }
        },
        hooks: {
            opacity: support.opacity ? {
                get: function(elem) {
                    var value = init(elem, "opacity");
                    return value === "" ? "1" : value;
                }
            } : {
                get: function(elem) {
                    return ropacity.test((elem.currentStyle ? elem.currentStyle.filter : elem.style.filter) || "") ? (0.01 * parseFloat(RegExp.$1)) + "" : "1";
                },
                set: function(elem, value) {
                    var style = elem.style,
                        currentStyle = elem.currentStyle,
                        opacity = ToolKit.isNumber(value) ? "alpha(opacity=" + (value < 1 ? value * 100 : value) + ")" : "",
                        filter = currentStyle && currentStyle.filter || style.filter || "";
                    style.zoom = 1;
                    if ((value === "") && ToolKit.trim(filter.replace(ralpha, "")) === "" && style.removeAttribute) {
                        style.removeAttribute("filter");
                        if (value === "" || currentStyle && !currentStyle.filter) {
                            return;
                        }
                    }
                    style.filter = ralpha.test(filter) ? filter.replace(ralpha, opacity) : filter + " " + opacity;
                }
            }
        },
        props: {
            "float": support.cssFloat ? "cssFloat" : "styleFloat"
        }
    };

    var
        rclickable = /^(?:a|area)$/i,
        rdefault = /^(?:checked|selected)$/i,
        rfocusable = /^(?:input|select|textarea|button|object)$/i,
        hooks = {
            _default: {
                get: function(elem, key) {
                    if (elem && elem.getAttribute) {
                        return elem.getAttribute(key);
                    }
                    return null;
                },
                set: function(elem, value, key) {
                    if (elem && elem.setAttribute) {
                        elem.setAttribute(key, value);
                    }
                    return value;
                }
            }
        };
    ToolKit.ft = {
        init: function(elem, key, value) {
            if (!elem || !key || !elem.nodeType || elem.nodeType === 2 || elem.nodeType === 3 || elem.nodeType === 8) {
                return null;
            }
            if (!support.attr) {
                key = ToolKit.ft.props[key] || key;
            }
            var val, hooks = ToolKit.ft.hooks[key];
            if (arguments.length == 2) {
                if (!hooks || !("get" in hooks) || (val = hooks.get()) == null) {
                    val = ToolKit.ft.hooks._default.get(elem, key);
                }
                if (!val && support.attr && (key in ToolKit.ft.props)) {
                    val = ToolKit.ft.hooks._default.get(elem, ToolKit.ft.props[key]);
                }
                return val;
            }
            if (hooks && "set" in hooks && (val = hooks.set(elem, value + "", key)) !== undefined) {
                return val;
            } else {
                ToolKit.ft.hooks._default.set(elem, value + "", key);
                return value;
            }
        },
        hooks: hooks,
        props: {
            "for": "htmlFor",
            "class": "className"
        }
    };
    ToolKit.extend(hooks, {
        tabIndex: {
            get: function(elem) {
                var val = hooks._default.get(elem, "tabindex");
                return val ? parseInt(val, 10) : rfocusable.test(elem.nodeName) || rclickable.test(elem.nodeName) && elem.href ? 0 : -1;
            }
        },
        type: {
            set: function(elem, value, key) {
                if (!support.radioValue && value === "radio" && ToolKit.nodeName(elem, "input")) {
                    var val = elem.value;
                    elem.setAttribute("type", value);
                    if (val) {
                        elem.value = val;
                    }
                    return value;
                }
            }
        },
        option: {
            get: function(elem) {
                var val = ToolKit.attr(elem, "value");
                return val != null ? val : ToolKit.trim(ToolKit.text(elem));
            }
        },
        select: {
            get: function(elem) {
                var
                    value, option, options = elem.options,
                    index = elem.selectedIndex,
                    only = elem.type === "select-one" || index < 0,
                    values = only ? null : [],
                    max = only ? index + 1 : options.length,
                    i = index < 0 ? max : only ? index : 0;
                for (; i < max; i++) {
                    option = options[i];
                    if ((option.selected || i === index) && (support.optionDisabled ? !option.disabled : option.getAttribute("disabled") === null) && (!option.parentNode.disabled || !ToolKit.nodeName(option.parentNode, "optgroup"))) {
                        value = hooks.option.get(option);
                        if (only) {
                            return value;
                        }
                        values.push(value);
                    }
                }
                return values;
            },
            set: function(elem, value) {
                var
                    optionSet, option, options = elem.options,
                    values = concat.apply([], value),
                    i = options.length;
                while (i--) {
                    option = options[i];
                    if (ToolKit.inArray(hooks.option.get(option), values) >= 0) {
                        try {
                            option.selected = optionSet = true;
                        } catch (_) {
                            option.scrollHeight;
                        }
                    } else {
                        option.selected = false;
                    }
                }
                if (!optionSet) {
                    elem.selectedIndex = -1;
                }
                return options;
            }
        }
    });
    ToolKit.each(["radio", "checkbox"], function() {
        hooks[this] = {
            set: function(elem, value) {
                if (ToolKit.isArray(value)) {
                    return (elem.checked = ToolKit.inArray(ToolKit(elem).val(), value) >= 0);
                }
            }
        };
        if (!support.checkOn) {
            hooks[this].get = function() {
                return elem.getAttribute("value") === null ? "on" : elem.value;
            };
        }
    });
    ToolKit.each(booleans.split("|"), function(_, key) {
        hooks[key] = {
            get: function(elem) {
                return elem[key] === true || elem.getAttribute(key);
            },
            set: function(elem, value) {
                if (support.input && support.attr || !rdefault.test(key)) {
                    hooks._default.set(elem, value, key);
                } else {
                    elem[ToolKit.camelCase("default-" + key)] = elem[key] = true;
                }
                return value;
            }
        }
    });
    ToolKit.each(["tabIndex", "readOnly", "maxLength", "cellSpacing", "cellPadding", "rowSpan", "colSpan", "useMap", "frameBorder", "contentEditable"], function() {
        ToolKit.ft.props[this.toLowerCase()] = this;
    });
    if (!support.attr || !support.input) {
        hooks["value"] = {
            get: function(elem) {
                if (elem.nodeName.toLowerCase() === "input") {
                    return elem.defaultValue;
                }
            },
            set: function(elem, value) {
                if (elem.nodeName.toLowerCase() === "input") {
                    return elem.defaultValue = value;
                } else {
                    return hooks._default.set(elem, value, "value");
                }
            }
        };
    }
    if (!support.hrefNormalized) {
        ToolKit.each(["type", "height", "width"], function(_, key) {
            hooks[key] = {
                get: function(elem) {
                    var val = elem.getAttribute && elem.getAttribute(key, key === "type" ? 1 : 2);
                    if (!val && !!(val = elem.getAttributeNode(key))) {
                        val = val.specified ? val.value : null;
                    }
                    return val;
                }
            };
        });
        ToolKit.each(["href", "src"], function(_, key) {
            hooks[key] = {
                get: function(elem) {
                    return elem.getAttribute(key, 4);
                }
            };
        });
    }
    if (!support.enctype) {
        ToolKit.ft.props.enctype = "encoding";
    }
    if (!support.attr) {
        ToolKit.extend(hooks, {
            button: {
                get: function(elem, key) {
                    var ret = elem.getAttributeNode(key);
                    if (ret && ret.specified) {
                        return ret.value;
                    }
                }
            },
            contenteditable: {
                set: function(elem, value, key) {
                    hooks._default.set(elem, value === "" ? false : value, key);
                }
            }
        });
        ToolKit.each(["width", "height"], function(_, key) {
            hooks[key] = {
                set: function(elem, value) {
                    if (value === "") {
                        elem.setAttribute(key, "auto");
                        return value;
                    }
                }
            };
        });
    }
    if (!support.style) {
        hooks.style = {
            get: function(elem) {
                return elem.style.cssText;
            },
            set: function(elem, value) {
                return (elem.style.cssText = value);
            }
        };
    }
    if (!support.optionSelected) {
        hooks.selected = {
            get: function(elem) {
                var parent = elem.parentNode;
                if (parent) {
                    parent.selectedIndex;
                    if (parent.parentNode) {
                        parent.parentNode.selectedIndex;
                    }
                }
                return null;
            }
        };
    }

    ToolKit.extend(ToolKit, {
        dir: function(elem, dir, all) {
            elem = (elem || {})[dir];
            if (!all) {
                while (elem && (elem.nodeType < 6) && (elem.nodeType !== 1)) {
                    elem = elem[dir];
                }
                return elem;
            }
            var list = [];
            while (elem && (elem.nodeType < 6)) {
                if (elem.nodeType === 1) {
                    list.push(elem);
                }
                elem = elem[dir];
            }
            return list;
        },
        sibling: function(elem, dir, all) {
            elem = elem || {};
            if (dir === "firstChild" || dir === "lastChild") {
                var o = {};
                elem = elem[dir];
                dir = dir === "firstChild" ? "nextSibling" : "previousSibling";
                o[dir] = elem;
                elem = o;
            }
            return ToolKit.dir(elem, dir, all);
        }
    });

    var
        tokenCache = {},
        classCache = {},
        compileCache = {},
        rsibling = /[+~]/,
        rheader = /^h\d$/i,
        rinputs = /^(?:input|select|textarea|button)$/i,
        rcomma = new RegExp("^" + whitespace + "*," + whitespace + "*"),
        characterEncoding = "(?:\\\\.|[\\w-]|[^\\x00-\\xa0])+",
        identifier = "(?:\\\\.|[\\w#-]|[^\\x00-\\xa0])+",
        rtrimV2 = new RegExp("^" + whitespace + "+|((?:^|[^\\\\])(?:\\\\.)*)" + whitespace + "+$", "g"),
        attributes = "\\[" + whitespace + "*(" + characterEncoding + ")(?:" + whitespace + "*([*^$|!~]?=)" + whitespace + "*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|(" + identifier + "))|)" + whitespace + "*\\]",
        extra = ":(" + characterEncoding + ")(?:\\((('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|" + "((?:\\\\.|[^\\\\()[\\]]|" + attributes + ")*)|" + ".*" + ")\\)|)",
        rextra = new RegExp(extra),
        ridentifier = new RegExp("^" + identifier + "$"),
        rcombinators = new RegExp("^" + whitespace + "*([>+~]|" + whitespace + ")" + whitespace + "*"),
        runescape = new RegExp("\\\\([\\da-f]{1,6}" + whitespace + "?|(" + whitespace + ")|.)", "ig"),
        funescape = function(_, escaped, escapedWhitespace) {
            var high = "0x" + escaped - 0x10000;
            return high !== high || escapedWhitespace ? escaped : high < 0 ? String.fromCharCode(high + 0x10000) : String.fromCharCode(high >> 10 | 0xD800, high & 0x3FF | 0xDC00);
        };
    support.sortStable = ["kit"].sort(sortOrder).join("") === "kit";
    support.detectDuplicates = !!hasDuplicate;

    function MakeFunction(callbak) {
        return function() {
            return callbak;
        }
    }

    ToolKit.fs = {
        match: {
            "ID": new RegExp("^#(" + characterEncoding + ")"),
            "CLASS": new RegExp("^\\.(" + characterEncoding + ")"),
            "TAG": new RegExp("^((?:\\\\.|[\\w*-]|[^\\x00-\\xa0])+)"),
            "ATTR": new RegExp("^" + attributes),
            "BOOLEAN": rbooleans,
            "BLANK": rcombinators,
            "CHILD": new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\(" + whitespace + "*(even|odd|(([+-]|)(\\d*)n|)" + whitespace + "*(?:([+-]|)" + whitespace + "*(\\d+)|))" + whitespace + "*\\)|)", "i"),
            "CONTEXT": new RegExp("^:(even|odd|eq|gt|lt|nth|first|last)(?:\\(" + whitespace + "*((?:-\\d)?\\d*)" + whitespace + "*\\)|)(?=[^-]|$)", "i"),
            "EXTRA": new RegExp("^" + extra)
        },
        blank: {
            " ": function() {
                return function(elem) {
                    return ToolKit.filterTag(elem, "*");
                }
            },
            ">": function() {
                return function(elem) {
                    return ToolKit.sibling(elem, "firstChild", true);
                }
            },
            "~": function() {
                return function(elem) {
                    return ToolKit.dir(elem, "nextSibling", true);
                }
            },
            "+": function() {
                return function(elem) {
                    elem = ToolKit.dir(elem, "nextSibling");
                    return elem && elem.parentNode ? [elem] : [];
                }
            }
        },
        find: {
            "ID": support.getElementById ?
                function(id, context) {
                    if (context.getElementById) {
                        var elem = context.getElementById(id);
                        return elem && elem.parentNode ? [elem] : [];
                    }
                } : function(id, context) {
                    var i = 0,
                        elem, filter = ToolKit.fs.filter["ID"](id),
                        list = ToolKit.fs.find["TAG"]("*", context);
                    while ((elem = list[i++])) {
                        if (filter(elem)) {
                            return [elem];
                        }
                    }
                },
            "TAG": support.getElementsByTagName ?
                function(tag, context) {
                    if (context.getElementsByTagName) {
                        return context.getElementsByTagName(tag);
                    }
                } : function(tag, context) {
                    var elem, i = 0,
                        tmp = [],
                        results = context.getElementsByTagName(tag);
                    if (tag === "*") {
                        while ((elem = results[i++])) {
                            if (elem.nodeType === 1) {
                                tmp.push(elem);
                            }
                        }
                        return tmp;
                    }
                    return results;
                },
            "CLASS": support.getElementsByClassName ?
                function(className, context) {
                    if (context.getElementsByClassName) {
                        return context.getElementsByClassName(className);
                    }
                } : function(className, context) {
                    var i = 0,
                        elem, results = [],
                        filter = ToolKit.fs.filter["CLASS"](className),
                        list = ToolKit.fs.find["TAG"]("*", context);
                    while ((elem = list[i++])) {
                        if (filter(elem)) {
                            results.push(elem);
                        }
                    }
                    return results;
                }
        },
        filter: {
            "ID": function(id) {
                var attrId = id.replace(runescape, funescape);
                return function(elem) {
                    return elem.getAttribute("id") === attrId;
                };
            },
            "TAG": function(tag) {
                var nodeName = tag.replace(runescape, funescape).toLowerCase();
                return tag === "*" ?
                    function() {
                        return true;
                    } : function(elem) {
                        return elem.nodeName && elem.nodeName.toLowerCase() === nodeName;
                    };
            },
            "CLASS": function(className) {
                var pattern = classCache[className];
                return pattern || (pattern = new RegExp("(^|" + whitespace + ")" + className + "(" + whitespace + "|$)")) && (classCache[className] = function(elem) {
                    return pattern.test(typeof elem.className === "string" && elem.className || elem.getAttribute && elem.getAttribute("class") || "");
                });
            },

            "ATTR": function(name, operator, check) {
                return function(elem) {
                    var result = ToolKit.attr(elem, name);

                    if (result == null) {
                        return operator === "!=";
                    }
                    if (!operator) {
                        return true;
                    }

                    result += "";

                    return operator === "=" ? result === check : operator === "!=" ? result !== check : operator === "^=" ? check && result.indexOf(check) === 0 : operator === "*=" ? check && result.indexOf(check) > -1 : operator === "$=" ? check && result.slice(-check.length) === check : operator === "~=" ? (" " + result + " ").indexOf(check) > -1 : operator === "|=" ? result === check || result.slice(0, check.length + 1) === check + "-" : false;
                };
            },
            "BLANK": function(type) {
                return ToolKit.fr.blank[type]();
            },
            "CHILD": function(type, what, arg, first, last) {
                if (!(type in ToolKit.fs.child)) {
                    ToolKit.syntaxError("Sorry! Not yet defined types:" + match.type);
                }
                return ToolKit.fs.child[type](what, first, last);
            },
            "CONTEXT": function(type, i) {
                if (!(type in ToolKit.fs.context)) {
                    ToolKit.syntaxError("Sorry! Not yet defined types:" + match.type);
                }
                return ToolKit.fs.context[type](this, i);
            },
            "EXTRA": function(type, args) {
                if (!(type in ToolKit.fs.extra)) {
                    ToolKit.syntaxError("Sorry! Not yet defined types:" + match.type);
                }
                return ToolKit.fs.extra[type](args);
            }
        },
        filters: {
            "ATTR": function(match) {
                match[1] = match[1].replace(runescape, funescape);
                match[3] = (match[3] || match[4] || match[5] || "").replace(runescape, funescape);

                if (match[2] === "~=") {
                    match[3] = " " + match[3] + " ";
                }
                return match.slice(0, 4);
            },
            "CHILD": function(match) {
                match[1] = match[1].toLowerCase();

                if (match[1].slice(0, 3) === "nth") {
                    if (!match[3]) {
                        ToolKit.syntaxError(match[0]);
                    }
                    match[4] = +(match[4] ? match[5] + (match[6] || 1) : 2 * (match[3] === "even" || match[3] === "odd"));
                    match[5] = +((match[7] + match[8]) || match[3] === "odd");
                    if (match[5] < 0) {
                        match[5] = match[5] % match[4];
                    }
                } else if (match[3]) {
                    ToolKit.syntaxError(match[0]);
                }
                return match;
            },
            "CONTEXT": function(match) {
                match[1] = match[1].toLowerCase();
                if (match[1] === "nth" || match[1] === "eq" || match[1] === "gt" || match[1] === "lt") {
                    if (!match[2]) {
                        ToolKit.syntaxError(match[0]);
                    }
                    match[2] = +match[2];
                } else if (match[2]) {
                    ToolKit.syntaxError(match[0]);
                }
                return match;
            },
            "EXTRA": function(match) {
                var excess, string = !match[6] && match[2];
                if (ToolKit.fs.match["CHILD"].test(match[0]) || ToolKit.fs.match["CONTEXT"].test(match[0])) {
                    return null;
                }
                if (match[3]) {
                    match[2] = match[4] || match[5] || "";
                } else if (string && rextra.test(string) && (excess = ToolKit.fs.tokenize(string, true)) && (excess = string.indexOf(")", string.length - excess) - string.length)) {
                    match[0] = match[0].slice(0, excess);
                    match[2] = string.slice(0, excess);
                }
                return match.slice(0, 3);
            }
        },
        child: {
            first: function(what) {
                return function(elem) {
                    var
                        tag = elem.nodeName.toLowerCase(),
                        node = elem.parentNode.firstChild;
                    for (; node; node = node.nextSibling) {
                        if (what === "of-type" ? node.nodeName.toLowerCase() === tag : node.nodeType === 1) {
                            return elem == node;
                        }
                    }
                    return false;
                }
            },
            last: function(what) {
                return function(elem) {
                    var
                        tag = elem.nodeName.toLowerCase(),
                        node = elem.parentNode.firstChild;
                    for (; node; node = node.previousSibling) {
                        if (what === "of-type" ? node.nodeName.toLowerCase() === tag : node.nodeType === 1) {
                            return elem == node;
                        }
                    }
                    return null;
                }
            },
            only: function(what) {
                return function(elem) {
                    var list = [];
                    var
                        tag = elem.nodeName.toLowerCase(),
                        node = elem.parentNode.firstChild;
                    for (; node; node = node.nextSibling) {
                        if (what === "of-type" ? node.nodeName.toLowerCase() === tag : node.nodeType === 1) {
                            return list.push(node);
                        }
                        if (list.length > 1) {
                            break;
                        }
                    }
                    return list.length === 1;
                }
            },
            nth: function(what, first, last) {
                return function(elem) {
                    var
                        list = [],
                        tag = elem.nodeName.toLowerCase(),
                        node = elem.parentNode.firstChild;
                    for (; node; node = node.nextSibling) {
                        if (what === "of-type" ? node.nodeName.toLowerCase() === tag : node.nodeType === 1) {
                            return list.push(node);
                        }
                    }
                    var i = 0,
                        index, len = list.length;
                    if (first > 0) {
                        for (;
                            (index = (i * first + last - 1)) < len; i++) {
                            if (index in list && list[index] == elem) {
                                return true;
                            }
                        }
                    } else {
                        index = last - 1;
                        return (index in list) && list[index] == elem;
                    }
                    return false;
                };
            },
            "nth-last": function(what, first, last) {
                return function() {
                    var
                        list = [],
                        tag = elem.nodeName.toLowerCase(),
                        node = elem.parentNode.firstChild;
                    for (; node; node = node.nextSibling) {
                        if (what === "of-type" ? node.nodeName.toLowerCase() === tag : node.nodeType === 1) {
                            return list.push(node);
                        }
                    }
                    var i, index;
                    if (first > 0) {
                        for (i = Math.ceil((list.length - last) / first);
                            (index = (i * first + last - 1)) >= 0; i--) {
                            if (index in list && list[index] == elem) {
                                return true;
                            }
                        }
                    } else {
                        index = list.length - last;
                        return index in list && list[index] == elem;
                    }
                    return false;
                }
            }
        },
        context: {
            first: function(list) {
                return list.length > 0 ? [list[0]] : [];
            },
            last: function(list) {
                return list.length > 0 ? [list[list.length - 1]] : [];
            },
            even: function(list) {
                var
                    i = 0,
                    result = [],
                    len = list.length;
                for (; i < len; i += 2) {
                    if (i in list) {
                        result.push(list[i]);
                    }
                }
                return list;
            },
            odd: function(list) {
                var
                    i = 1,
                    result = [],
                    len = list.length;
                for (; i < len; i += 2) {
                    if (i in list) {
                        result.push(list[i]);
                    }
                }
                return list;
            },
            nth: function(list, i) {
                i = i + (i < 0 ? list.length : 0);
                return list.length > i ? [list[i]] : [];
            },
            eq: function(list, i) {
                i = i + (i < 0 ? list.length : 0);
                return list.length > i ? [list[i]] : [];
            },
            gt: function(list, i) {
                var result = [];
                for (; i < list.length; i++) {
                    result.push(list[i]);
                }
                return result;
            },
            lt: function() {
                var result = [];
                i = Math.min(i, list.length);
                for (; i >= 0; i--) {
                    result.push(list[i]);
                }
                return result;
            }
        },
        extra: {
            not: function(selector) {
                var callbak = ToolKit.fs.compile(selector.replace(rtrimV2, "$1"));
                return function(elem) {
                    return !callbak(elem);
                }
            },
            has: function(selector) {
                return function(elem) {
                    return ToolKit(selector, elem).length > 0;
                }
            },
            contains: function(text) {
                return function(elem) {
                    return (elem.textContent || elem.innerText || ToolKit.text(elem)).indexOf(text) > -1
                }
            },
            lang: function(lang) {
                if (!ridentifier.test(lang || "")) {
                    ToolKit.syntaxError("unsupported lang: " + lang);
                }
                lang = lang.replace(runescape, funescape).toLowerCase();
                return function(elem) {
                    var langs;
                    do {
                        if (!!(langs = elem.lang)) {
                            langs = langs.toLowerCase();
                            return langs === lang || langs.indexOf(lang + "-") === 0;
                        }
                    }
                    while ((elem = elem.parentNode) && elem.nodeType === 1);
                }
            },
            target: MakeFunction(function(elem) {
                var hash = window.location && window.location.hash;
                return hash && hash.slice(1) === elem.id;
            }),
            root: MakeFunction(function(elem) {
                return elem === document.documentElement;
            }),
            focus: MakeFunction(function(elem) {
                return elem === document.activeElement && (!document.hasFocus || document.hasFocus()) && !!(elem.type || elem.href || ~elem.tabIndex);
            }),
            enabled: MakeFunction(function(elem) {
                return elem.disabled === false;
            }),
            disabled: MakeFunction(function(elem) {
                return elem.disabled === true;
            }),
            checked: MakeFunction(function(elem) {
                var nodeName = elem.nodeName.toLowerCase();
                return (nodeName === "input" && !!elem.checked) || (nodeName === "option" && !!elem.selected);
            }),
            selected: MakeFunction(function(elem) {
                if (elem.parentNode) {
                    elem.parentNode.selectedIndex;
                }
                return elem.selected === true;
            }),
            empty: MakeFunction(function(elem) {
                for (elem = elem.firstChild; elem; elem = elem.nextSibling) {
                    if (elem.nodeType < 6) {
                        return false;
                    }
                }
                return true;
            }),
            parent: MakeFunction(function(elem) {
                for (elem = elem.firstChild; elem; elem = elem.nextSibling) {
                    if (elem.nodeType < 6) {
                        return true;
                    }
                }
                return false;
            }),
            header: MakeFunction(function(elem) {
                return rheader.test(elem.nodeName);
            }),
            input: MakeFunction(function(elem) {
                return rinputs.test(elem.nodeName);
            }),
            button: MakeFunction(function(elem) {
                var name = elem.nodeName.toLowerCase();
                return name === "button" || name === "input" && elem.type === "button";
            }),
            text: MakeFunction(function(elem) {
                var attr;
                return elem.nodeName.toLowerCase() === "input" && elem.type === "text" && ((attr = elem.getAttribute("type")) == null || attr.toLowerCase() === "text");
            })
        }
    };
    ToolKit.each(["radio", "checkbox", "file", "password", "image"], function(_, type) {
        ToolKit.fs.extra[type] = MakeFunction(function(elem) {
            var name = elem.nodeName.toLowerCase();
            return name === "input" && elem.type === type;
        });
    });
    ToolKit.each(["submit", "reset"], function(_, type) {
        ToolKit.fs.extra[type] = MakeFunction(function(elem) {
            var name = elem.nodeName.toLowerCase();
            return (name === "input" || name === "button") && elem.type === type;
        });
    });

    function PrecisionFilter(token, result, i) {
        var r, match, filter, len = token.length;
        for (; i < len; i++) {
            match = token[i];
            filter = ToolKit.fs.filter[match.type].apply(result, match.matches);
            if (ToolKit.isFunction(filter)) {
                result = ToolKit.map(result, function(elem) {
                    if (!!(r = filter(elem))) {
                        return r === true ? elem : r;
                    }
                });
            } else {
                result = filter;
            }
            if (!result || !result.length) {
                break;
            }
        }
        return result;
    }

    ToolKit.extend(ToolKit.fs, {
        base: function(selector, context, results, isFilter) {
            var tokens = ToolKit.fs.tokenize(selector);
            var match, token, result, i = 0,
                list = [],
                len = tokens.length;
            for (; i < len; i++) {
                token = tokens[i];
                if (isFilter) {
                    result = [context];
                } else {
                    if (token[0].type in ToolKit.fs.find) {
                        match = token[0];
                        result = ToolKit.fs.find[match.type](match.matches[0], context);
                    } else {
                        result = ToolKit.fs.find["TAG"]("*", context);
                    }
                }
                ToolKit.merge(list, PrecisionFilter(token, result, match ? 1 : 0));
                if (isFilter) {
                    return list.length > 0;
                }
                push.apply(results = results || [], list);
                return results.length > 0 ? ToolKit.fs.uniqueSort(results) : results;
            }
        },
        init: function(selector, context, results) {
            results = results || [];
            context = context || document;
            if (!selector || typeof selector !== "string") {
                return results;
            }
            var elem, match, nodeType = context.nodeType;
            if (!(nodeType === 1 || nodeType === 9)) {
                return results;
            }
            if (!!(match = rquickExpr.exec(selector))) {
                if (match[1]) {
                    if (nodeType === 9) {
                        elem = context.getElementById(match[1]);
                        if (elem && elem.parentNode && elem.id === match[1]) {
                            results.push(elem);
                        }
                        return results;
                    } else {
                        if (context.ownerDocument && (elem = context.ownerDocument.getElementById(match[1])) && contains(context, elem) && elem.id === match[1]) {
                            results.push(elem);
                            return results;
                        }
                    }
                } else if (match[2]) {
                    push.apply(results, context.getElementsByTagName(match[2]));
                    return results;
                } else if (match[3] && support.getElementsByClassName && context.getElementsByClassName) {
                    push.apply(results, context.getElementsByClassName(match[3]));
                    return results;
                }
            }
            if (support.querySelectorAll && (support.rquerySelectorAll || !support.rquerySelectorAll.test(selector))) {
                var org = true,
                    tik = "tik",
                    newSelector;
                if (nodeType === 1 && context.nodeName.toLowerCase() !== "object") {
                    groups = ToolKit.fs.tokenize(selector);

                    if (!!(org = context.getAttribute("id"))) {
                        tik = org.replace(rescape, "\\$&");
                    } else {
                        context.setAttribute("id", tik);
                    }
                    tik = "[id='" + tik + "'] ";

                    i = groups.length;
                    while (i--) {
                        groups[i] = tik + ToolKit.fs.toSelector(groups[i]);
                    }
                    newSelector = groups.join(",");
                }
                if (newSelector || nodeType === 9) {
                    try {
                        push.apply(results, context.querySelectorAll(newSelector || selector));
                        return results;
                    } catch (_) {} finally {
                        if (!org) {
                            context.removeAttribute("id");
                        }
                    }
                }
            }
            return ToolKit.fs.base(selector, context, results);
        },
        compile: function(selector, match) {
            var cache = compileCache[selector];
            if (!cache) {
                match = match || ToolKit.fs.tokenize(selector);
                if (match.length !== 1 || (match[0].length != null || (match = match[0]).length !== 1)) {
                    ToolKit.syntaxError("The selector definition is wrong!");
                }
                if (match.type === "CONTEXT" || match.type === "BLANK") {
                    ToolKit.syntaxError("The selector definition is wrong! Types cannot be context or blank!");
                }
                if (!(match.type in ToolKit.fs.filter)) {
                    ToolKit.syntaxError("Sorry! Not yet defined types:" + match.type);
                }
                cache = ToolKit.fs.filter[match.type].apply(null, match.matches);
                cache.selector = selector;
                compileCache[selector] = cache;
            }
            return cache;
        },
        tokenize: function(selector, parseOnly) {
            var matched, match, tokens, type, soFar, groups, preFilters, cached = tokenCache[selector];
            if (cached) {
                return parseOnly ? 0 : cached.slice(0);
            }
            groups = [];
            soFar = selector;
            while (soFar) {
                if (!matched || (match = rcomma.exec(soFar))) {
                    if (match) {
                        soFar = soFar.slice(match[0].length) || soFar;
                    }
                    groups.push((tokens = []));
                }
                matched = false;
                if ((match = rcombinators.exec(soFar))) {
                    matched = match.shift();
                    tokens.push({
                        value: matched,
                        type: match[0].replace(rtrimV2, " ")
                    });
                    soFar = soFar.slice(matched.length);
                }
                for (type in ToolKit.fs.filter) {
                    if ((match = ToolKit.fs.match[type].exec(soFar)) && (!ToolKit.fs.filters[type] || (match = ToolKit.fs.filters[type](match)))) {
                        matched = match.shift();
                        tokens.push({
                            value: matched,
                            type: type,
                            matches: match
                        });
                        soFar = soFar.slice(matched.length);
                    }
                }
                if (!matched) {
                    break;
                }
            }
            return parseOnly ? soFar.length : soFar ? ToolKit.syntaxError(selector) : (tokenCache[selector] = groups).slice(0);
        },
        toSelector: function(tokens) {
            var
                i = 0,
                len = tokens.length,
                selector = "";
            for (; i < len; i++) {
                selector += tokens[i].value;
            }
            return selector;
        },
        uniqueSort: function(results) {
            var
                elem, list = [],
                i = 0,
                index = 0;
            hasDuplicate = !support.detectDuplicates;
            sortInput = !support.sortStable && results.slice(0);
            results.sort(sortOrder);
            if (hasDuplicate) {
                while ((elem = results[i++])) {
                    if (elem === results[i]) {
                        index = list.push(i);
                    }
                }
                while (index--) {
                    results.splice(list[index], 1);
                }
            }
            sortInput = null;
            return results;
        },
        matchesSelector: function(selector, context) {
            var match;
            selector = selector.replace(rattributeQuotes, "='$1']");
            if (
                support.matchesSelector && (!support.rmatchesSelector || support.rmatchesSelector.test(selector)) && (!support.rquerySelectorAll || !support.rquerySelectorAll.test(selector))) {
                try {
                    var result = support.matches.call(context, selector);
                    if (result || support.disconnectedMatch || context.document && context.document.nodeType !== 11) {
                        return result;
                    }
                } catch (e) {}
            }
            return ToolKit.fs.base(selector, context, null, true);
        }
    });

    var
        guid = 0,
        tookit = 0,
        rformElems = /^(?:input|select|textarea)$/i,
        rkeyEvent = /^key/,
        rmouseEvent = /^(?:mouse|pointer|contextmenu)|click/,
        rfocusMorph = /^(?:focusinfocus|focusoutblur)$/,
        rtypenamespace = /^([^.]*)(?:\.(.+)|)$/;

    function returnTrue() {
        return true;
    }

    function returnFalse() {
        return false;
    }

    function deleteFn(o, key) {
        try {
            delete o[key];
        } catch (_) {
            if (o && key) {
                o[key] = undefined;
            }
        }
    }
    ToolKit.event = {
        set: function(elem, type, data) {
            if (!ToolKit.event.support(elem)) {
                return null;
            }
            var chic, handlers, events, handle, cache = ToolKit.event.get(elem);
            if (!(events = cache["events"])) {
                events = cache["events"] = {};
            }
            if (!(handle = cache.handle)) {
                handle = cache.handle = function(e) {
                    if (ToolKit && (!e || ToolKit.event.triggered !== e.type)) {
                        return ToolKit.event.handle.apply(handle.elem, arguments);
                    }
                };
                handle.elem = elem;
            }
            chic = ToolKit.event.chic[type] || {};
            if (chic.type) {
                type = chic.type;
                chic = ToolKit.event.chic[type] || {};
            }
            data = ToolKit.extend(data, {
                chic: type
            });
            if (!(handlers = events[type])) {
                handlers = events[type] = [];
                if (!chic.setup || chic.setup.call(elem, data, handle) === false) {
                    ToolKit.addEvent(elem, type, handle);
                }
            }
            if (chic.add) {
                chic.add.call(elem, data);
            }
            handlers.push(data);
            ToolKit.event.global[type] = true;
            elem = null;
        },
        get: function(elem, type) {
            if (!ToolKit.event.support(elem)) {
                return null;
            }
            var
                kit = elem[ToolKit.kit] = elem[ToolKit.kit] || ++tookit,
                cache = ToolKit.event.cache[kit] = ToolKit.event.cache[kit] || {};
            if (!type || type === "*") {
                return cache;
            }
            cache["events"] = cache["events"] || {};
            if (type === "events" || type === "handle") {
                return cache[type];
            }
            return cache["events"][type];
        },
        has: function(elem, type) {
            if (!ToolKit.event.support(elem)) {
                return false;
            }
            var
                kit = elem[ToolKit.kit],
                cache = ToolKit.event.cache[kit];
            if (!type || !cache || type === "*") {
                return !!cache;
            }
            if (type === "events" || type === "handle" || !cache["events"]) {
                return !!cache[type];
            }
            return !!cache["events"][type];
        },
        cache: {},
        global: {},
        exclude: {
            "applet": true,
            "embed": true,
            "object": "clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"
        },
        support: function(elem) {
            var
                nodeType = +elem.nodeType || 1,
                noData = ToolKit.event.exclude[(elem.nodeName + "").toLowerCase()];
            return nodeType !== 1 && nodeType !== 9 ? false : !noData || noData !== true && elem.getAttribute("classid") === noData;
        },
        add: function(elem, type, handler, data) {
            if (!ToolKit.event.support(elem)) {
                return null;
            }
            handler.guid = handler.guid || ++guid;
            ToolKit.event.set(elem, type, {
                data: data,
                type: type,
                handler: handler,
                guid: handler.guid
            });
        },
        remove: function(elem, type, handler) {
            var events, cache = ToolKit.event.get(elem);
            if (!cache || !(events = cache["events"])) {
                return;
            }
            if (!type || type === "*") {
                return ToolKit.each(events, function(key) {
                    ToolKit.event.remove(elem, key, handler);
                });
            }
            var i = 0,
                data, handlers, orgType = type,
                chic = ToolKit.event.chic[type] || {};
            if (chic.type) {
                type = chic.type;
                chic = ToolKit.event.chic[type] || {};
            }
            if (!(handlers = events[type])) {
                return;
            }
            while (!!(data = handlers[i++])) {
                if ((orgType == data.type) && (!handler || handler.guid == data.guid)) {
                    handlers.splice(i, 1);
                    if (chic.remove) {
                        chic.remove.call(elem, data);
                    }
                }
            }
            if (!handlers.length && (!chic.teardown || chic.teardown.call(elem, cache.handle) === false)) {
                ToolKit.removeEvent(elem, type, cache.handle);
                deleteFn(events, type);
                if (ToolKit.isEmptyObject(events)) {
                    deleteFn(cache, "handle");
                    deleteFn(cache, "events");
                }
            }
        },
        trigger: function(event, data, elem, onlyHandlers) {
            var handle, ontype, cur, bubbleType, chic, tmp, i, eventPath = [elem || document],
                type = hasOwn.call(event, "type") ? event.type : event;

            cur = tmp = elem = elem || document;
            if (elem.nodeType === 3 || elem.nodeType === 8) {
                return;
            }
            if (rfocusMorph.test(type + ToolKit.event.triggered)) {
                return;
            }
            ontype = type.indexOf(":") < 0 && "on" + type;
            event = event[ToolKit.kit] ? event : new ToolKit.Event(type, typeof event === "object" && event);
            event.isTrigger = onlyHandlers ? 2 : 3;
            null;
            event.result = undefined;
            if (!event.target) {
                event.target = elem;
            }
            data = data == null ? [event] : ToolKit.makeArray(data, [event]);
            chic = ToolKit.event.chic[type] || {};
            if (!onlyHandlers && chic.trigger && chic.trigger.apply(elem, data) === false) {
                return;
            }
            if (!onlyHandlers && !chic.precise && !ToolKit.isWindow(elem)) {
                bubbleType = chic.type || type;
                if (!rfocusMorph.test(bubbleType + type)) {
                    cur = cur.parentNode;
                }
                for (; cur; cur = cur.parentNode) {
                    eventPath.push(cur);
                    tmp = cur;
                }
                if (tmp === (elem.ownerDocument || document)) {
                    eventPath.push(tmp.defaultView || tmp.parentWindow || window);
                }
            }
            i = 0;
            while (cur = eventPath[i++]) {
                event.type = i > 1 ? bubbleType : chic.type || type;
                handle = ToolKit.event.get(cur, event.type) && ToolKit.event.get(cur, "handle");
                if (handle) {
                    handle.apply(cur, data);
                }
                handle = ontype && cur[ontype];
                if (handle && handle.apply && ToolKit.event.support(cur)) {
                    event.result = handle.apply(cur, data);
                    if (event.result === false) {
                        event.alter();
                    }
                }
            }
            event.type = type;
            if (!onlyHandlers) {
                if ((!chic._default || chic._default.apply(eventPath.pop(), data) === false) && ToolKit.event.support(elem)) {
                    if (ontype && elem[type] && !ToolKit.isWindow(elem)) {
                        tmp = elem[ontype];
                        if (tmp) {
                            elem[ontype] = null;
                        }
                        ToolKit.event.triggered = type;
                        try {
                            elem[type]();
                        } catch (e) {}
                        ToolKit.event.triggered = undefined;
                        if (tmp) {
                            elem[ontype] = tmp;
                        }
                    }
                }
            }
            return event.result;
        },
        handle: function(event) {
            event = ToolKit.event.fix(event);
            var ret, handle, args = slice.call(arguments),
                handlers = ToolKit.event.get(this, event.type) || [],
                chic = ToolKit.event.chic[event.type] || {};
            args[0] = event;
            event.delegateTarget = this;
            var i = 0,
                handle, matched = ToolKit.event.handlers.call(this, event, handlers);
            if (matched == null) {
                return;
            }
            event.currentTarget = matched.elem;
            while ((handle = matched.handlers[i++]) && !event.abort()) {
                event.handle = handle;
                event.data = handle.data;
                ret = ((ToolKit.event.chic[handle.type] || {}).handle || handle.handler).apply(matched.elem, args);
                if (ret !== undefined) {
                    if ((event.result = ret) === false) {
                        event.alter();
                        event.termination();
                    }
                }
            }
            if (chic.commit) {
                chic.commit.call(this, event);
            }
            return event.result;
        },
        handlers: function(event, handlers) {
            var results = [],
                cur = event.target;
            if (cur.nodeType && (!event.button || event.type !== "click")) {
                if (cur === this) {
                    return {
                        elem: this,
                        handlers: handlers
                    };
                }
                for (; cur != this; cur = cur.parentNode || this) {
                    if (cur.nodeType === 1 && (cur.disabled !== true || event.type !== "click")) {
                        return {
                            elem: cur,
                            handlers: handlers
                        };
                    }
                }
                return null;
            }
            return {
                elem: this,
                handlers: handlers
            };
        },
        fix: function(event) {
            if (event[ToolKit.kit]) {
                return event;
            }
            var i, prop, copy, type = event.type,
                originalEvent = event,
                fixHook = this.fixHooks[type];

            if (!fixHook) {
                this.fixHooks[type] = fixHook = rmouseEvent.test(type) ? this.mouseHooks : rkeyEvent.test(type) ? this.keyHooks : {};
            }
            copy = fixHook.props ? this.props.concat(fixHook.props) : this.props;

            event = new ToolKit.Event(originalEvent);

            i = copy.length;
            while (i--) {
                prop = copy[i];
                event[prop] = originalEvent[prop];
            }
            if (!event.target) {
                event.target = originalEvent.srcElement || document;
            }
            if (event.target.nodeType === 3) {
                event.target = event.target.parentNode;
            }
            event.metaKey = !!event.metaKey;

            return fixHook.filter ? fixHook.filter(event, originalEvent) : event;
        },
        props: "altKey bubbles cancelable ctrlKey currentTarget eventPhase metaKey relatedTarget shiftKey target timeStamp view which".split(" "),
        fixHooks: {},
        keyHooks: {
            props: "char charCode key keyCode".split(" "),
            filter: function(event, original) {
                if (event.which == null) {
                    event.which = original.charCode != null ? original.charCode : original.keyCode;
                }

                return event;
            }
        },
        mouseHooks: {
            props: "button buttons clientX clientY fromElement offsetX offsetY pageX pageY screenX screenY toElement".split(" "),
            filter: function(event, original) {
                var body, eventDoc, doc, button = original.button,
                    fromElement = original.fromElement;
                if (event.pageX == null && original.clientX != null) {
                    eventDoc = event.target.ownerDocument || document;
                    doc = eventDoc.documentElement;
                    body = eventDoc.body;

                    event.pageX = original.clientX + (doc && doc.scrollLeft || body && body.scrollLeft || 0) - (doc && doc.clientLeft || body && body.clientLeft || 0);
                    event.pageY = original.clientY + (doc && doc.scrollTop || body && body.scrollTop || 0) - (doc && doc.clientTop || body && body.clientTop || 0);
                }
                if (!event.relatedTarget && fromElement) {
                    event.relatedTarget = fromElement === event.target ? original.toElement : fromElement;
                }
                if (!event.which && button !== undefined) {
                    event.which = (button & 1 ? 1 : (button & 2 ? 3 : (button & 4 ? 2 : 0)));
                }

                return event;
            }
        },
        chic: {
            load: {
                precise: true
            },
            focus: {
                trigger: function() {
                    if (this !== safeActiveElement() && this.focus) {
                        try {
                            this.focus();
                            return false;
                        } catch (e) {}
                    }
                }
            },
            blur: {
                trigger: function() {
                    if (this === safeActiveElement() && this.blur) {
                        this.blur();
                        return false;
                    }
                }
            },
            click: {
                trigger: function() {
                    if (ToolKit.nodeName(this, "input") && this.type === "checkbox" && this.click) {
                        this.click();
                        return false;
                    }
                },
                _default: function(event) {
                    return ToolKit.nodeName(event.target, "a");
                }
            },
            beforeunload: {
                commit: function(event) {
                    if (event.result !== undefined && event.originalEvent) {
                        event.originalEvent.returnValue = event.result;
                    }
                }
            }
        }
    };
    ToolKit.addEvent = document.addEventListener ?
        function(elem, type, handle) {
            if (elem.addEventListener) {
                elem.addEventListener(type, handle, false);
            }
        } : function(elem, type, handle) {
            if (elem.attachEvent) {
                elem.attachEvent("on" + type, handle);
            }
        };
    ToolKit.removeEvent = document.removeEventListener ?
        function(elem, type, handle) {
            if (elem.removeEventListener) {
                elem.removeEventListener(type, handle, false);
            }
        } : function(elem, type, handle) {
            var name = "on" + type;
            if (elem.detachEvent) {
                if (elem[name] === undefined) {
                    elem[name] = null;
                }
                elem.detachEvent(name, handle);
            }
        };
    ToolKit.Event = function(src, props) {
        if (!(this instanceof ToolKit.Event)) {
            return new ToolKit.Event(src, props);
        }
        if (src && src.type) {
            this.originalEvent = src;
            this.type = src.type;
        } else {
            this.type = src;
        }
        if (props) {
            ToolKit.extend(this, props);
        }
        this.timeStamp = src && src.timeStamp || +(new Date());
        this[ToolKit.kit] = true;
    };
    ToolKit.Event.prototype = {
        abort: returnFalse,
        alter: function() {
            var e = this.originalEvent;
            if (!e) {
                return;
            }
            if (e.alter) {
                e.alter();
            } else {
                e.returnValue = false;
            }
        },
        termination: function() {
            var e = this.originalEvent;
            this.abort = returnTrue;
            if (!e) {
                return;
            }
            if (e.termination) {
                e.termination();
            }
            e.cancelBubble = true;
        }
    };

    ToolKit.each({
        mouseenter: "mouseover",
        mouseleave: "mouseout",
        pointerenter: "pointerover",
        pointerleave: "pointerout"
    }, function(key, fix) {
        ToolKit.event.chic[key] = {
            type: fix,
            handle: function(event) {
                var ret, target = this,
                    related = event.relatedTarget,
                    handle = event.handle;
                if (!related || (related !== target && !ToolKit.contains(target, related))) {
                    event.type = handle.type;
                    ret = handle.handler.apply(this, arguments);
                    event.type = fix;
                }
                return ret;
            }
        };
    });

    var
        ContextToolKit, rquickExpr = /^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]*))$/;

    function manipulationTarget(elem, content) {
        return ToolKit.nodeName(elem, "table") && ToolKit.nodeName(content.nodeType !== 11 ? content : content.firstChild, "tr") ? elem.getElementsByTagName("tbody")[0] || elem.appendChild(elem.ownerDocument.createElement("tbody")) : elem;
    }
    ToolKit.fn = {
        kit: version,
        constructor: ToolKit,
        selector: null,
        context: document,
        length: 0,
        get: function(i, v) {
            i = +i + (i < 0 ? this.length : 0);
            return (i in this) ? this[i] : v;
        },
        toArray: function() {
            return slice.call(this);
        },
        push: push,
        sort: arr.sort,
        splice: arr.splice
    };
    ToolKit.fn.init = function(selector, context) {
        if (!selector) return this;
        var match, elem;
        this.selector = selector;
        if (typeof selector === "string") {
            if (selector[0] === "<" && selector[selector.length - 1] === ">" && selector.length > 2) {
                match = [null, selector, null];
            } else {
                match = rquickExpr.exec(selector);
            }
            if (match && (match[1] || !context)) {
                if (match[1]) {
                    context = context instanceof ToolKit ? context[0] : context;
                    ToolKit.merge(this, ToolKit.parseHTML(
                        match[1], context && context.nodeType ? context.ownerDocument || context : document, true));
                    if (rsingleTag.test(match[1]) && ToolKit.isPlainObject(context)) {
                        for (match in context) {
                            if (ToolKit.isFunction(this[match])) {
                                this[match](context[match]);
                            } else {
                                this.attr(match, context[match]);
                            }
                        }
                    }
                    return this;
                } else {
                    elem = document.getElementById(match[2]);
                    if (elem && elem.parentNode) {
                        this[0] = elem;
                        this.length = 1;
                    }
                    this.context = document;
                    return this;
                }
            }
            if (!context || context.kit === version) {
                return (context || ContextToolKit).find(selector);
            }
            return this.constructor(context).find(selector);
        }
        if (selector.nodeType) {
            this.context = this[0] = selector;
            this.length = 1;
            return this;
        }
        if (ToolKit.isFunction(selector)) {
            return ContextToolKit.ready !== undefined ? ContextToolKit.ready(selector) : selector(ToolKit);
        }
        if (selector.selector != null) {
            this.selector = selector.selector;
            this.context = selector.context;
        }
        return ToolKit.makeArray(selector, this);
    }
    ToolKit.fn.init.prototype = ToolKit.fn;

    ToolKit.extend(ToolKit, {
        contains: contains,
        css: ToolKit.fx.init,
        attr: ToolKit.ft.init,
        filterTag: function(context, tag) {
            tag = tag || "*";
            var result = context.getElementsByTagName ? context.getElementsByTagName(tag) : context.querySelectorAll ? context.querySelectorAll(tag) : null;
            if (result == null) {
                result = [];
                if (tag === "*" || ToolKit.nodeName(context, tag)) {
                    result.push(context);
                }
                for (context = context.firstChild; context; context = context.nextSibling) {
                    if (tag === "*" || ToolKit.nodeName(context, tag)) {
                        result.push(context);
                    }
                    concat.apply(result, ToolKit.filterTag(context, tag));
                };
                return result;
            }
            return tag === "*" && ToolKit.nodeName(context, tag) ? ToolKit.merge([context], result) : result;
        },
        nodeName: function(elem, tag) {
            tag = tag || "*";
            return elem && elem.nodeName && (tag === "*" || elem.nodeName.toLowerCase() === tag.toLowerCase());
        },
        val: function(elem) {
            if (!elem) {
                return null;
            }
            var val, hooks = ToolKit.ft.hooks[elem.type] || ToolKit.ft.hooks[elem.nodeName.toLowerCase()];
            if (hooks && "get" in hooks && (val = hooks.get(elem, "value")) != null) {
                return val;
            }
            val = elem.value;
            return typeof val === "string" ? val.replace(/\r/g, "") : val == null ? "" : val;
        },
        text: function(elem) {
            var result = "";
            if (!elem || !elem.nodeType) {
                return result;
            }
            var nodeType = elem.nodeType;
            if (nodeType === 1 || nodeType === 9 || nodeType === 11) {
                if (typeof elem.textContent === "string") {
                    result = elem.textContent;
                } else {
                    for (elem = elem.firstChild; elem; elem = elem.nextSibling) {
                        result += ToolKit.text(elem);
                    }
                }
            } else if (nodeType === 3 || nodeType === 4) {
                result = elem.nodeValue || "";
            }
            return result;
        },
        clone: function(elem, dataAndEvents, deepDataAndEvents) {
            var clone = elem.cloneNode(true);
            if (dataAndEvents) {
                var
                    i = 0,
                    len, type, node, cache, arr = ToolKit.filterTag(elem),
                    list = ToolKit.filterTag(clone);
                if (deepDataAndEvents) {
                    while (!!(node = arr[i++])) {
                        if (ToolKit.event.has(node, "events")) {
                            cache = ToolKit.event.get(node);
                            for (type in cache.events) {
                                ToolKit.removeEvent(list[i], type, cache.handle);
                            }
                            list[i][ToolKit.kit] = null;
                        }
                    }
                } else {
                    while (!!(node = arr[i++])) {
                        if (ToolKit.event.has(node, "events")) {
                            var handle = function(e) {
                                if (ToolKit && (!e || ToolKit.event.triggered !== e.type)) {
                                    return ToolKit.event.handle.apply(handle.elem, arguments);
                                }
                            };
                            cache = ToolKit.extend(true, {}, ToolKit.event.get(node));
                            handle.elem = list[i];
                            cache.handle = handle;
                            for (type in cache.events) {
                                ToolKit.addEvent(list[i], type, cache.handle);
                            }
                            ToolKit.event.cache[list[i][ToolKit.kit] = ++tookit] = cache;
                        }
                    }
                }
            }
            return clone;
        },
        find: function(selector, context, results) {
            results = results || [];
            var type = ToolKit.type(selector);
            if (type === "string") {
                return ToolKit.fs.init(selector, context, results);
            }
            if (type === "function") {
                var val;
                if ((val = selector.call(context, context, results)) != null && val.nodeType) {
                    results.push(val);
                }
                return results;
            }
            var list = ToolKit.merge([], selector);
            for (var i = 0, len = list.length; i < len; i++) {
                if (ToolKit.contains(context, list[i])) {
                    results.push(list[i]);
                }
            }
            return results;
        },
        filter: function(selector, context) {
            var type = ToolKit.type(selector);
            if (type === "string") {
                return ToolKit.fs.matchesSelector(selector, context);
            }
            if (type === "function") {
                return selector.call(context, context);
            }
            var list = ToolKit.merge([], selector);
            for (var i = 0, len = list.length; i < len; i++) {
                if (list[i] == context) return true;
            }
            return false;
        }
    });
    ToolKit.extend(ToolKit.fn, {
        eq: function(i) {
            i = +i + (i < 0 ? this.length : 0);
            return this.pushStack((i in this) ? [this[i]] : []);
        },
        first: function() {
            return this.eq(0);
        },
        last: function() {
            return this.eq(-1);
        },
        each: function(iterator) {
            return ToolKit.each(this, iterator);
        },
        end: function() {
            return this.prevObject || this.constructor();
        },
        map: function(iterator) {
            return this.pushStack(ToolKit.map(this, function(elem, i) {
                return iterator.call(elem, i, elem);
            }));
        },
        pushStack: function(elems) {
            var result = ToolKit.merge(this.constructor(), elems);
            result.prevObject = this;
            result.context = this.context;
            return result;
        }
    });
    ToolKit.extend(ToolKit.fn, {
        css: function(key, value) {
            var type = ToolKit.type(key);
            if (arguments.length === 1) {
                if (type === "string") {
                    return ToolKit.css(this[0], key);
                }
                if (type !== "object") {
                    return this;
                }
            }
            return this.each(function() {
                if (type === "object") {
                    return ToolKit.each(key, function(k, v) {
                        ToolKit.css(this, k, v);
                    }, this);
                }
                ToolKit.css(this, key, value);
            });
        },
        val: function(value) {
            if (arguments.length === 0) {
                return ToolKit.val(this[0]);
            }
            var isFunction = ToolKit.isFunction(value);
            return this.each(function(i) {
                if (this.nodeType !== 1) {
                    return;
                }
                var
                    val = value,
                    hooks = ToolKit.ft.hooks[elem.type] || ToolKit.ft.hooks[elem.nodeName.toLowerCase()];
                if (isFunction) {
                    val = value.call(this, i, ToolKit(this).val());
                }
                if (ToolKit.isArray(val)) {
                    val = ToolKit.map(val, function(value) {
                        return value == null ? "" : value + "";
                    });
                } else {
                    val = val == null ? val : val + "";
                }
                if (!hooks || !("set" in hooks) || hooks.set(this, val, "value") == null) {
                    this.value = val;
                }
            });
        },
        text: function(value) {
            if (arguments.length === 0) {
                return ToolKit.text(this[0]);
            }
            var isFunction = ToolKit.isFunction(value);
            return this.empty().each(function(i) {
                var val = value;
                if (isFunction) {
                    val = value.call(this, i, ToolKit(this).text());
                }
                val = val == null ? "" : val + "";
                this.appendChild(document.createTextNode(val));
            });
        },
        attr: function(key, value) {
            if (arguments.length === 1) {
                return ToolKit.attr(this[0], key);
            }
            return this.each(function() {
                ToolKit.attr(this, key, value);
            });
        },
        removeAttr: function(key) {
            return this.each(function() {
                ToolKit.ft.init(this, key, null);
            });
        },
        clone: function(dataAndEvents, deepDataAndEvents) {
            dataAndEvents = dataAndEvents == null ? false : dataAndEvents;
            deepDataAndEvents = deepDataAndEvents == null ? dataAndEvents : deepDataAndEvents;
            return this.map(function() {
                return ToolKit.clone(this, dataAndEvents, deepDataAndEvents);
            });
        },
        empty: function() {
            return this.each(function() {
                while (this.firstChild) {
                    this.removeChild(this.firstChild);
                }
                if (this.options && ToolKit.nodeName(this, "select")) {
                    this.options.length = 0;
                }
            });
        },
        remove: function(selector) {
            selector = selector || "*";
            if (selector == "*") {
                return this.removeAll();
            }
            var tik = this.filter(selector);
            if (tik.length > 0) {
                var result = this.pushStack(this.map(function() {
                    return ToolKit.inArray(this, tik) === -1 ? this : null;
                }));
                tik.removeAll();
                result.selector = this.selector;
                return result;
            }
            return this;
        },
        removeAll: function() {
            this.each(function() {
                if (this.parentNode) {
                    this.parentNode.removeChild(this)
                }
            });
            return this.constructor();
        }
    });
    ToolKit.each(["width", "height"], function(i, type) {
        ToolKit.fn[type] = function(v) {
            if (arguments.length === 0) {
                return ToolKit.css(this[0], type);
            }
            return this.each(function(e) {
                ToolKit.css(this, type, v);
            });
        }
    });

    var rclass = /[\t\r\n\f]/g,
        isHidden = function(elem) {
            return ToolKit.css(elem, "display") === "none" || !ToolKit.contains(elem.ownerDocument, elem);
        };
    ToolKit.extend(ToolKit.fn, {
        show: function() {
            return this.css("display", "block");
        },
        hide: function() {
            return this.css("display", "none");
        },
        toggle: function(state) {
            if (typeof state === "boolean") {
                return state ? this.show() : this.hide();
            }

            return this.each(function() {
                if (isHidden(this)) {
                    ToolKit(this).show();
                } else {
                    ToolKit(this).hide();
                }
            });
        },
        hasClass: function(value) {
            var result = false;
            if (ToolKit.isFunction(value)) {
                this.each(function() {
                    return !(result = ToolKit(this).hasClass(value.call(this, this.className)));
                });
                return result;
            }
            value = " " + value + " ";
            this.each(function() {
                return !(result = (this.nodeType === 1) && (" " + this.className + " ").replace(rclass, " ").indexOf(value) > -1);
            });
            return result;
        },
        addClass: function(value) {
            if (value && ToolKit.isFunction(value)) {
                return this.each(function() {
                    ToolKit(this).addClass(value.call(this, this.className));
                });
            }
            if (value && ToolKit.isString(value)) {
                var i, target, clazz, finalValue, classes = value.match(rnotwhite) || [];
                this.each(function() {
                    target = this.nodeType === 1 && (this.className ? (" " + this.className + " ").replace(rclass, " ") : " ");
                    if (!!target) {
                        i = 0;
                        while (!!(clazz = classes[i++])) {
                            if (target.indexOf(" " + clazz + " ") < 0) {
                                target += clazz + " ";
                            }
                        }
                        finalValue = ToolKit.trim(target);
                        if (this.className !== finalValue) {
                            this.className = finalValue;
                        }
                    }
                });
            }
            return this;
        },
        toggleClass: function(value, stateVal) {
            if (typeof stateVal === "boolean") {
                return stateVal ? this.addClass(value) : this.removeClass(value);
            }
            if (ToolKit.isFunction(value)) {
                return this.each(function() {
                    ToolKit(this).toggleClass(value.call(this, this.className, stateVal), stateVal);
                });
            }
            return this.each(function() {
                if (value == null || (this.nodeType === 1) && (" " + this.className + " ").replace(rclass, " ").indexOf(value) > -1) {
                    ToolKit(this).removeClass(value);
                } else {
                    ToolKit(this).addClass(value);
                }
            });
        },
        removeClass: function(value) {
            if (value && ToolKit.isFunction(value)) {
                return this.each(function() {
                    ToolKit(this).removeClass(value.call(this, this, this.className));
                });
            }
            if (value && ToolKit.isString(value)) {
                var i, target, clazz, finalValue, classes = value.match(rnotwhite) || [];
                this.each(function() {
                    target = this.nodeType === 1 && (this.className ? (" " + this.className + " ").replace(rclass, " ") : " ");
                    if (!!target) {
                        i = 0;
                        while (!!(clazz = classes[i++])) {
                            if (target.indexOf(" " + clazz + " ") >= 0) {
                                target = target.replace(" " + clazz + " ", " ");
                            }
                        }
                        finalValue = ToolKit.trim(target);
                        if (this.className !== finalValue) {
                            this.className = finalValue;
                        }
                    }
                });
            }
            return this;
        }
    });

    var
        rparentsprev = /^(?:parents|previous(?:All))/,
        guaranteedUnique = {
            contents: true,
            next: true,
            previous: true,
            lastChild: true,
            firstChild: true,
            childNodes: true
        };
    ToolKit.each({
        parent: function(elem) {
            return !!(elem = elem.parentNode) && (elem.nodeType !== 11) ? elem : null;
        },
        parents: function(elem) {
            return ToolKit.dir(elem, "parentNode", true);
        },
        next: function(elem) {
            return ToolKit.dir(elem, "nextSibling");
        },
        previous: function(elem) {
            return ToolKit.dir(elem, "previousSibling");
        },
        nextAll: function(elem) {
            return ToolKit.dir(elem, "nextSibling", true);
        },
        previousAll: function(elem) {
            return ToolKit.dir(elem, "previousSibling", true);
        },
        lastChild: function(elem) {
            return ToolKit.sibling(elem, "lastChild");
        },
        firstChild: function(elem) {
            return ToolKit.sibling(elem, "firstChild");
        },
        childNodes: function(elem) {
            return ToolKit.sibling(elem, "firstChild", true);
        },
        contents: function(elem) {
            return ToolKit.nodeName(elem, "iframe") ? elem.contentDocument || elem.contentWindow.document : ToolKit.sibling(elem, "firstChild", true);
        }
    }, function(key, callback) {
        ToolKit.fn[key] = function(selector) {
            var r = ToolKit.map(this, callback);
            if (selector) {
                r = ToolKit.map(r, function() {
                    if (ToolKit.filter(selector, this)) {
                        return this;
                    }
                });
            }
            if (this.length > 1) {
                if (!guaranteedUnique[key]) {
                    ToolKit.fs.uniqueSort(r);
                }
                if (rparentsprev.test(key)) {
                    r = r.reverse();
                }
            }
            return this.pushStack(r);
        }
    });

    var
        rscript = /^$|\/(?:java|ecma)script/i,
        rclear = /^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g;
    ToolKit.extend(ToolKit.fn, {
        append: function() {
            return this.domManip(arguments, function(elem) {
                if (this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9) {
                    var target = manipulationTarget(this, elem);
                    target.appendChild(elem);
                }
            });
        },
        prepend: function() {
            return this.domManip(arguments, function(elem) {
                if (this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9) {
                    var target = manipulationTarget(this, elem);
                    target.insertBefore(elem, target.firstChild);
                }
            });
        },
        before: function() {
            return this.domManip(arguments, function(elem) {
                if (this.parentNode) {
                    this.parentNode.insertBefore(elem, this);
                }
            });
        },
        after: function() {
            return this.domManip(arguments, function(elem) {
                if (this.parentNode) {
                    this.parentNode.insertBefore(elem, this.nextSibling);
                }
            });
        },
        domManip: function(list, callbak) {
            list = concat.apply([], list);
            var
                elem, scripts, fragment, i = 0,
                len = this.length - 1;
            if (len > -1) {
                fragment = buildFragment(list, this[0].ownerDocument, this);
                scripts = ToolKit.filterTag(fragment, "script");
                if (fragment.childNodes.length === 1) {
                    fragment = fragment.firstChild;
                }
                if (scripts.length) {
                    while (!!(elem = scripts[i++])) {
                        if (rscript.test(elem.type)) {
                            if (elem.src) {
                                ToolKit._evalUrl && ToolKit._evalUrl(elem.src);
                            } else {
                                ToolKit.globalEval((elem.text || elem.textContent || elem.innerHTML || "").replace(rclear, ""));
                            }
                        }
                    }
                }
            }
            return this.each(function(i) {
                elem = fragment;
                if (i < len) {
                    elem = ToolKit.clone(fragment, true, true);
                }
                callbak.call(this, elem, i);
            });
        }
    });
    ToolKit.extend(ToolKit.fn, {
        is: function(selector) {
            return this.filter(selector).length > 0;
        },
        not: function(selector) {
            return this.filter(":not(" + selector + ")");
        },
        find: function(selector) {
            var
                i = 0,
                len = this.length,
                results = [];
            for (i = 0; i < len; i++) {
                ToolKit.find(selector, this[i], results);
            }
            var tik = this.pushStack(len > 1 ? ToolKit.fs.uniqueSort(results) : results);
            tik.selector = this.selector && ToolKit.isString(this.selector) ? this.selector + " " + selector : selector;
            return tik;
        },
        filter: function(selector) {
            return this.pushStack(this.map(function() {
                return ToolKit.filter(selector, this) ? this : null;
            }));
        }
    });
    ToolKit.extend(ToolKit.fn, {
        hover: function(fnOver, fnOut) {
            return this.mouseenter(fnOver).mouseleave(fnOut || fnOver);
        },
        bind: function(type, handler, data) {
            if (!handler) {
                return this;
            }
            return this.each(function() {
                ToolKit.event.add(this, type, handler, data);
            });
        },
        unbind: function(type, handler) {
            return this.each(function() {
                ToolKit.event.remove(this, type, handler);
            });
        },
        trigger: function(type, data) {
            return this.each(function() {
                ToolKit.event.trigger(type, data, this);
            });
        },
        triggerHandler: function(type, data) {
            if (this.length > 0) {
                return ToolKit.event.trigger(type, data, this[0], true);
            }
        }
    });
    ToolKit.each(("blur focus focusin focusout load resize scroll unload click dblclick " + "mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave " + "change select submit keydown keypress keyup error contextmenu").split(" "), function(i, type) {
        ToolKit.fn[type] = function(fn, data) {
            return arguments.length > 0 ? this.bind(type, fn, data) : this.trigger(type);
        };
    });
    ToolKit.each(["ajaxStart", "ajaxStop", "ajaxComplete", "ajaxError", "ajaxSuccess", "ajaxSend"], function(i, type) {
        ToolKit.fn[type] = function(fn) {
            return this.bind(type, fn);
        };
    });
    ContextToolKit = new ToolKit.fn.init(document);

    var
        optionsCache = {},
        rnotwhite = (/\S+/g);

    function createOptions(options) {
        var object = optionsCache[options] = {};
        ToolKit.each(options.match(rnotwhite) || [], function(_, flag) {
            object[flag] = true;
        });
        return object;
    }

    ToolKit.Threads = function(options) {
        options = typeof options === "string" ? (optionsCache[options] || createOptions(options)) : ToolKit.extend({}, options);
        if (options.update) {
            if (typeof options.update !== "fuction") {
                options.update = null;
            }
        }
        if (options.callbak) {
            if (typeof options.callbak !== "fuction") {
                options.callbak = null;
            }
        }
        var
            index, islock, list = [],
            processing, fire = function(i, callbak) {
                if (i == index) {
                    return true;
                }
                processing = false;
                if (list && (i in list)) {
                    processing = true;
                    if (!callbak || callbak.call(tik, i, index) !== false) {
                        if (options.update) {
                            options.update.call(list[i]);
                        } else {
                            list[i].update();
                        }
                    }
                    index = i;
                }
                return !processing;
            },
            tik = {
                add: function() {
                    if (list) {
                        (function add(args) {
                            ToolKit.each(args, function(_, arg) {
                                if (arg && (options.update || typeof arg.update === "function")) {
                                    list.push(arg);
                                }
                            });
                        })(arguments);
                        if (index == null || index == -1 && !processing) {
                            islock = true;
                            fire(0);
                            islock = false;
                        }
                    }
                    return this;
                },
                remove: function() {
                    if (list) {
                        ToolKit.each(arguments, function(_, arg) {
                            var i;
                            while ((i = ToolKit.inArray(arg, list, i)) > -1) {
                                list.splice(i, 1);
                                if (i < index) {
                                    index--;
                                }
                            }
                        });
                    }
                    return this;
                },
                lock: function(i, callbak) {
                    if (this.locked()) {
                        return false;
                    }
                    islock = true;
                    if (fire(i, callbak || options.callbak)) {
                        if (options.stack) {
                            this.empty();
                        } else {
                            this.disable();
                        }
                    }
                    islock = false;
                    return true;
                },
                get: function(i) {
                    if (arguments.length === 0) {
                        return list[index];
                    }
                    i = +i + (i < 0 ? list.length : 0);
                    return list[i];
                },
                has: function(lyt) {
                    return lyt ? ToolKit.inArray(lyt, list) > -1 : !!(list && list.length);
                },
                locked: function() {
                    return !!islock;
                },
                empty: function() {
                    list = [];
                    index = -1;
                    return this;
                },
                disable: function() {
                    list = index = undefined;
                    return this;
                },
                disabled: function() {
                    return !list;
                },
                next: function() {
                    return this.lock(index + 1);
                },
                previous: function() {
                    return this.lock(index - 1);
                }
            };
        return ToolKit.improve(tik, options.threads);
    };
    ToolKit.Callbacks = function(options) {
        options = typeof options === "string" ? (optionsCache[options] || createOptions(options)) : ToolKit.extend({}, options);

        var
            fired, locked, firing, memory, index, i, len, list = [],
            stack = options.stack && [],
            fire = function(data) {
                memory = options.memory && data;
                i = index || 0;
                len = list.length;
                firing = true;
                for (; !locked && (i < len); i++) {
                    list[i].apply(data[0], data[1]);
                }
                fired = true;
                firing = false;
                if (list) {
                    if (stack) {
                        if (stack.length) {
                            fire(stack.shift());
                        }
                    } else if (memory) {
                        list = [];
                    } else {
                        tik.disable();
                    }
                }
            },
            tik = {
                add: function() {
                    if (list) {
                        var start = list.length;
                        (function add(args) {
                            ToolKit.each(args, function(_, arg) {
                                var type = ToolKit.type(arg);
                                if (type === "function") {
                                    if (!options.unique || !tik.has(arg)) {
                                        list.push(arg);
                                    }
                                } else if (arg && arg.length && type !== "string") {
                                    add(arg);
                                }
                            });
                        })(arguments);
                        if (firing) {
                            len = list.length;
                        } else if (memory) {
                            index = start;
                            fire(memory);
                        }
                    }
                    return this;
                },
                remove: function() {
                    if (list) {
                        ToolKit.each(arguments, function(_, arg) {
                            var index;
                            while ((index = ToolKit.inArray(arg, list, index)) > -1) {
                                list.splice(index, 1);
                                if (firing) {
                                    if (index <= len) {
                                        len--;
                                    }
                                    if (index <= i) {
                                        i--;
                                    }
                                }
                            }
                        });
                    }
                    return this;
                },
                has: function(fn) {
                    return fn ? ToolKit.inArray(fn, list) > -1 : !!(list && list.length);
                },
                empty: function() {
                    len = 0;
                    list = [];
                    return this;
                },
                disable: function() {
                    list = stack = memory = undefined;
                    return this;
                },
                disabled: function() {
                    return !list;
                },
                lock: function() {
                    locked = true;
                    stack = undefined;
                    if (!memory) {
                        tik.disable();
                    }
                    return this;
                },
                locked: function() {
                    return !!locked;
                },
                fireWith: function(context, args) {
                    if (list && (!fired || stack)) {
                        args = args || [];
                        args = [context, args.slice ? args.slice() : args];
                        if (firing) {
                            stack.push(args);
                        } else {
                            fire(args);
                        }
                    }
                    return this;
                },
                fire: function() {
                    tik.fireWith(this, arguments);
                    return this;
                },
                fired: function() {
                    return !!fired;
                }
            };
        return tik;
    };

    ToolKit.Deferred = function(callbak) {
        var
            tuples = [
                ["resolve", "done", ToolKit.Callbacks("memory"), "resolved"],
                ["abort", "fail", ToolKit.Callbacks("memory"), "error"],
                ["always", "progress", ToolKit.Callbacks("stack memory")]
            ],
            state = "pending",
            deferred = {},
            promise = {
                state: function() {
                    return state;
                },
                always: function() {
                    deferred.done(arguments).fail(arguments);
                    return this;
                },
                then: function( /* fnDone, fnFail, fnProgress */ ) {
                    var fns = arguments;
                    return ToolKit.Deferred(function(newDefer) {
                        ToolKit.each(tuples, function(i, tuple) {
                            var fn = ToolKit.isFunction(fns[i]) && fns[i];
                            deferred[tuple[1]](function() {
                                var returned = fn && fn.apply(this, arguments);
                                if (returned && ToolKit.isFunction(returned.promise)) {
                                    returned.promise().done(newDefer.resolve).fail(newDefer.abort).progress(newDefer.always);
                                } else {
                                    newDefer[tuple[0] + "With"](this === promise ? newDefer.promise() : this, fn ? [returned] : arguments);
                                }
                            });
                        });
                        fns = null;
                    }).promise();
                },
                promise: function(obj) {
                    return obj != null ? ToolKit.extend(obj, promise) : promise;
                }
            };
        ToolKit.each(tuples, function(i, tuple) {
            var list = tuple[2],
                stateString = tuple[3];
            promise[tuple[1]] = list.add;
            if (stateString) {
                list.add(function() {
                    state = stateString;
                }, tuples[i ^ 1][2].disable, tuples[2][2].lock);
            }
            deferred[tuple[0]] = function() {
                deferred[tuple[0] + "With"](this === deferred ? promise : this, arguments);
                return this;
            };
            deferred[tuple[0] + "With"] = list.fireWith;
        });
        promise.promise(deferred);
        if (callbak) {
            callbak.call(deferred, deferred);
        }
        return deferred;
    };
    var readyList;
    ToolKit.fn.ready = function(fn) {
        ToolKit.ready.promise().done(fn);
        return this;
    };
    ToolKit.extend(ToolKit, {
        isReady: false,
        readyWait: 1,
        ready: function(wait) {
            if (!document.body) {
                return setTimeout(ToolKit.ready);
            }
            ToolKit.isReady = true;
            readyList.resolveWith(document, [ToolKit]);
            if (ToolKit.fn.triggerHandler) {
                ToolKit(document).triggerHandler("ready");
                ToolKit(document).unbind("ready");
            }
        }
    });

    function detach() {
        if (document.addEventListener) {
            document.removeEventListener("DOMContentLoaded", completed, false);
            window.removeEventListener("load", completed, false);

        } else {
            document.detachEvent("onreadystatechange", completed);
            window.detachEvent("onload", completed);
        }
    }

    function completed() {
        if (document.addEventListener || event.type === "load" || document.readyState === "complete") {
            detach();
            ToolKit.ready();
        }
    }
    ToolKit.ready.promise = function(options) {
        if (!readyList) {

            readyList = ToolKit.Deferred();
            if (document.readyState === "complete") {
                setTimeout(ToolKit.ready);
            } else if (document.addEventListener) {
                document.addEventListener("DOMContentLoaded", completed, false);
                window.addEventListener("load", completed, false);
            } else {
                document.attachEvent("onreadystatechange", completed);
                window.attachEvent("onload", completed);
                var top = false;
                try {
                    top = window.frameElement == null && document.documentElement;
                } catch (e) {}

                if (top && top.doScroll) {
                    (function doScrollCheck() {
                        if (!ToolKit.isReady) {
                            try {
                                top.doScroll("left");
                            } catch (e) {
                                return setTimeout(doScrollCheck, 50);
                            }
                            detach();
                            ToolKit.ready();
                        }
                    })();
                }
            }
        }
        return readyList.promise(options);
    };

    var
        ajaxLocParts, ajaxLocation, r20 = /%20/g,
        rquery = (/\?/),
        rbracket = /\[\]$/,
        rCRLF = /\r?\n/g,
        rhash = /#.*$/,
        rts = /([?&])_=[^&]*/,
        rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i,
        rsubmittable = /^(?:input|select|textarea|keygen)/i,
        rheaders = /^(.*?):[ \t]*([^\r\n]*)\r?$/mg,
        // IE leaves an \r character at EOL
        rlocalProtocol = /^(?:about|app|app-storage|.+-extension|file|res|widget):$/,
        rnoContent = /^(?:GET|HEAD)$/,
        rprotocol = /^\/\//,
        rurl = /^([\w.+-]+:)(?:\/\/(?:[^\/?#]*@|)([^\/?#:]*)(?::(\d+)|)|)/,
        transports = {},
        prefilters = {
            "*": [returnTrue]
        },
        nonce = +(new Date()),
        allTypes = "*/".concat("*");
    try {
        ajaxLocation = location.href;
    } catch (e) {
        ajaxLocation = document.createElement("a");
        ajaxLocation.href = "";
        ajaxLocation = ajaxLocation.href;
    }
    ajaxLocParts = rurl.exec(ajaxLocation.toLowerCase()) || [];

    function ajaxExtend(target, src) {
        var deep, key, flatOptions = ToolKit.ajaxSettings.flatOptions || {};

        for (key in src) {
            if (src[key] !== undefined) {
                (flatOptions[key] ? target : (deep || (deep = {})))[key] = src[key];
            }
        }
        if (deep) {
            ToolKit.extend(true, target, deep);
        }
        return target;
    }

    function buildParams(prefix, obj, traditional, add) {
        var name;

        if (ToolKit.isArray(obj)) {
            ToolKit.each(obj, function(v, i) {
                if (traditional || rbracket.test(prefix)) {
                    add(prefix, v);
                } else {
                    buildParams(prefix + "[" + (typeof v === "object" ? i : "") + "]", v, traditional, add);
                }
            });

        } else if (!traditional && ToolKit.type(obj) === "object") {
            for (name in obj) {
                buildParams(prefix + "[" + name + "]", obj[name], traditional, add);
            }

        } else {
            add(prefix, obj);
        }
    }

    function ajaxConfig(options) {
        return function(dataTypeExpression, fn) {
            if (ToolKit.isFunction(dataTypeExpression)) {
                fn = dataTypeExpression;
                dataTypeExpression = "*";
            }
            var
                dataType, dataTypes = dataTypeExpression.toLowerCase().match(rnotwhite) || [];
            while (!!(dataType = dataTypes.shift())) {
                if (dataType.charAt(0) === "+") {
                    dataType = dataType.slice(1) || "*";
                    (options[dataType] = options[dataType] || []).unshift(fn);
                } else {
                    (options[dataType] = options[dataType] || []).push(fn);
                }
            }
        }
    }

    function ajaxMatchConfig(configs, ajax, options, asyncXHR) {
        var fn, result;
        return (function config(type) {
            var list = configs[type] || configs["*"] || [];
            for (var i = 0; !!(fn = list[i++]);) {
                if (!!(result = fn(ajax, options, asyncXHR))) {
                    if (ToolKit.isString(result)) {
                        ajax.dataTypes.unshift(result);
                        return config(result);
                    }
                    return result;
                }
            }
            return config("*");
        })(ajax.dataTypes[0]);
    }

    function ajaxHandleResponses(s, asyncXHR, responses) {
        var
            allType, dataType, contents = s.contents,
            dataTypes = s.dataTypes,
            type = dataTypes[0];
        if (type === "*") {
            allType = s.mimeType || asyncXHR.getResponseHeader("Content-Type");
            for (type in contents) {
                if (contents[type] && contents[type].test(allType)) {
                    dataTypes.unshift(type);
                    break;
                }
            }
        }
        if (dataTypes[0] in responses) {
            dataType = dataTypes[0];
        } else {
            for (type in responses) {
                if (!dataTypes[0] || s.converters[type + " " + dataTypes[0]]) {
                    dataType = type;
                    break;
                }
            }
            dataType = dataType || type;
        }
        if (dataType !== dataTypes[0]) {
            dataTypes.unshift(dataType);
        }
        return responses[dataType];
    }

    function ajaxConvert(s, response, asyncXHR, isSuccess) {
        var
            type, convert, converters = {},
            dataTypes = s.dataTypes.slice(),
            from = dataTypes.shift(),
            to = dataTypes.shift();
        if (to) {
            for (type in s.converters) {
                converters[type.toLowerCase()] = s.converters[type];
            }
        }
        if (isSuccess && s.dataFilter) {
            response = s.dataFilter(response, s.dataType);
        }
        do {
            if (s.responseFields[from]) {
                asyncXHR[s.responseFields[from]] = response;
            }
            convert = converters[from + " " + to] || converters["* " + from];
            if (!convert) {
                for (type in converters) {
                    type = type.split(" ");
                    if ((to === type[1]) && (convert = converters[type[0] + " " + to] || converters["* " + type[0]])) {
                        break;
                    }
                }
            }
            if (!!convert) {
                try {
                    response = convert(response) || response;
                } catch (e) {
                    return {
                        state: "parsererror",
                        error: e
                    };
                }
            } else {
                return {
                    state: "parsererror",
                    error: "No conversion from " + from + " to " + to
                };
            }
        }
        while (!!(from = to) && !!(to = dataTypes.shift()));
        return {
            state: "success",
            data: response
        };
    }

    ToolKit.extend(ToolKit, {
        active: 0,
        lastModified: {},
        etag: {},
        ajaxSettings: {
            url: ajaxLocation,
            type: "GET",
            dataType: "*",
            isLocal: rlocalProtocol.test(ajaxLocParts[1]),
            global: true,
            processData: true,
            async: true,
            contentType: "application/x-www-form-urlencoded; charset=UTF-8",
            /*
            timeout: 0,
            data: null,
            username: null,
            password: null,
            cache: null,
            traditional: false,
            headers: {},
            */
            accepts: {
                "*": allTypes,
                text: "text/plain",
                html: "text/html",
                xml: "application/xml, text/xml",
                json: "application/json, text/javascript",
                script: "text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"
            },
            contents: {
                xml: /xml/,
                html: /html/,
                json: /json/,
                script: /(?:java|ecma)script/
            },
            converters: {
                "* text": String,
                "text html": function(text) {
                    return text;
                },
                "text json": JSON.parse,
                "text xml": ToolKit.parseXML,
                "text script": ToolKit.globalEval
            },
            responseFields: {
                xml: "responseXML",
                text: "responseText",
                json: "responseJSON"
            },
            flatOptions: {
                url: true,
                context: true
            }
        },
        ajaxPrefilter: ajaxConfig(prefilters),
        ajaxTransport: ajaxConfig(transports),
        ajaxSetup: function(target, settings) {
            return settings ? ajaxExtend(ajaxExtend(target, ToolKit.ajaxSettings), settings) : ajaxExtend(ToolKit.ajaxSettings, target);
        },
        param: function(a, traditional) {
            var prefix, s = [],
                add = function(key, value) {
                    value = ToolKit.isFunction(value) ? value() : (value == null ? "" : value);
                    s[s.length] = encodeURIComponent(key) + "=" + encodeURIComponent(value);
                };
            if (traditional === undefined) {
                traditional = ToolKit.ajaxSettings && ToolKit.ajaxSettings.traditional;
            }
            if (ToolKit.isArray(a) || (a.version && !!(a = a.data) && !ToolKit.isPlainObject(a))) {
                ToolKit.each(a, function(v) {
                    add(v.name, v.value);
                });
            } else {
                for (prefix in a) {
                    buildParams(prefix, a[prefix], traditional, add);
                }
            }
            return s.join("&").replace(r20, "+");
        },
        ajax: function(url, options) {
            if (typeof url === "object") {
                options = url;
                url = undefined;
            }
            options = options || {};

            var
                parts, i, cacheURL, responseHeadersString, timeoutTimer, fireTKits, transport, responseHeaders, s = ToolKit.ajaxSetup({}, options),
                callbackContext = s.context || s,
                globalEventContext = s.context && (callbackContext.nodeType || callbackContext.kit) ? ToolKit(callbackContext) : ToolKit.event,
                deferred = ToolKit.Deferred(),
                completeDeferred = ToolKit.Callbacks("memory"),
                statusCode = s.statusCode || {},
                requestHeaders = {},
                requestHeadersNames = {},
                state = 0,
                strAbort = "canceled",
                asyncXHR = {
                    readyState: 0,
                    getResponseHeader: function(key) {
                        var match;
                        if (state === 2) {
                            if (!responseHeaders) {
                                responseHeaders = {};
                                while (!!(match = rheaders.exec(responseHeadersString))) {
                                    responseHeaders[match[1].toLowerCase()] = match[2];
                                }
                            }
                            match = responseHeaders[key.toLowerCase()];
                        }
                        return match == null ? null : match;
                    },
                    getAllResponseHeaders: function() {
                        return state === 2 ? responseHeadersString : null;
                    },
                    setRequestHeader: function(name, value) {
                        var lname = name.toLowerCase();
                        if (!state) {
                            name = requestHeadersNames[lname] = requestHeadersNames[lname] || name;
                            requestHeaders[name] = value;
                        }
                        return this;
                    },
                    overrideMimeType: function(type) {
                        if (!state) {
                            s.mimeType = type;
                        }
                        return this;
                    },
                    statusCode: function(map) {
                        var code;
                        if (map) {
                            if (state < 2) {
                                for (code in map) {
                                    statusCode[code] = [statusCode[code], map[code]];
                                }
                            } else {
                                asyncXHR.always(map[asyncXHR.status]);
                            }
                        }
                        return this;
                    },
                    abort: function(statusText) {
                        var finalText = statusText || strAbort;
                        if (transport) {
                            transport.abort(finalText);
                        }
                        done(0, finalText);
                        return this;
                    }
                };
            deferred.promise(asyncXHR).complete = completeDeferred.add;
            asyncXHR.success = asyncXHR.done;
            asyncXHR.error = asyncXHR.fail;
            s.url = ((url || s.url || ajaxLocation) + "").replace(rhash, "").replace(rprotocol, ajaxLocParts[1] + "//");
            s.type = options.method || options.type || s.method || s.type;
            s.dataTypes = ToolKit.trim(s.dataType || "*").toLowerCase().match(rnotwhite) || [""];
            if (s.crossDomain == null) {
                parts = rurl.exec(s.url.toLowerCase());
                s.crossDomain = !!(parts && (parts[1] !== ajaxLocParts[1] || parts[2] !== ajaxLocParts[2] || (parts[3] || (parts[1] === "http:" ? "80" : "443")) !== (ajaxLocParts[3] || (ajaxLocParts[1] === "http:" ? "80" : "443"))));
            }
            if (s.data && s.processData && typeof s.data !== "string") {
                s.data = ToolKit.param(s.data, s.traditional);
            }
            ajaxMatchConfig(prefilters, s, options, asyncXHR);
            fireTKits = s.global;
            if (fireTKits && ToolKit.active++ === 0) {
                ToolKit.event.trigger("ajaxStart");
            }
            s.type = s.type.toUpperCase();
            s.hasContent = !rnoContent.test(s.type);
            cacheURL = s.url;
            if (!s.hasContent) {
                if (s.data) {
                    cacheURL = (s.url += (rquery.test(cacheURL) ? "&" : "?") + s.data);
                    delete s.data;
                }
                if (s.cache === false) {
                    s.url = rts.test(cacheURL) ? cacheURL.replace(rts, "$1_=" + nonce++) : cacheURL + (rquery.test(cacheURL) ? "&" : "?") + "_=" + nonce++;
                }
            }
            if (s.ifModified) {
                if (ToolKit.lastModified[cacheURL]) {
                    asyncXHR.setRequestHeader("If-Modified-Since", ToolKit.lastModified[cacheURL]);
                }
                if (ToolKit.etag[cacheURL]) {
                    asyncXHR.setRequestHeader("If-None-Match", ToolKit.etag[cacheURL]);
                }
            }
            if (s.data && s.hasContent && s.contentType !== false || options.contentType) {
                asyncXHR.setRequestHeader("Content-Type", s.contentType);
            }
            asyncXHR.setRequestHeader("Accept", s.dataTypes[0] && s.accepts[s.dataTypes[0]] ? s.accepts[s.dataTypes[0]] + (s.dataTypes[0] !== "*" ? ", " + allTypes + "; q=0.01" : "") : s.accepts["*"]);
            for (i in s.headers) {
                asyncXHR.setRequestHeader(i, s.headers[i]);
            }
            if (s.beforeSend && (s.beforeSend.call(callbackContext, asyncXHR, s) === false || state === 2)) {
                return asyncXHR.abort();
            }
            strAbort = "abort";
            for (i in {
                    success: 1,
                    error: 1,
                    complete: 1
                }) {
                asyncXHR[i](s[i]);
            }
            transport = ajaxMatchConfig(transports, s, options, asyncXHR);
            if (!transport) {
                done(-1, "No Transport");
            } else {
                asyncXHR.readyState = 1;
                if (fireTKits) {
                    globalEventContext.trigger("ajaxSend", [asyncXHR, s]);
                }
                if (s.async && s.timeout > 0) {
                    timeoutTimer = setTimeout(function() {
                        asyncXHR.abort("timeout");
                    }, s.timeout);
                }

                try {
                    state = 1;
                    transport.send(requestHeaders, done);
                } catch (e) {
                    if (state < 2) {
                        done(-1, e);
                    } else {
                        throw e;
                    }
                }
            }

            function done(status, nativeStatusText, responses, headers) {
                var isSuccess, success, error, response, modified, statusText = nativeStatusText;
                if (state === 2) {
                    return;
                }
                state = 2;
                if (timeoutTimer) {
                    clearTimeout(timeoutTimer);
                }
                transport = undefined;
                responseHeadersString = headers || "";
                asyncXHR.readyState = status > 0 ? 4 : 0;
                isSuccess = status >= 200 && status < 300 || status === 304;
                response = responses && ajaxHandleResponses(s, asyncXHR, responses);;
                response = ajaxConvert(s, response, asyncXHR, isSuccess);
                if (isSuccess) {
                    if (s.ifModified) {
                        modified = asyncXHR.getResponseHeader("Last-Modified");
                        if (modified) {
                            ToolKit.lastModified[cacheURL] = modified;
                        }
                        modified = asyncXHR.getResponseHeader("etag");
                        if (modified) {
                            ToolKit.etag[cacheURL] = modified;
                        }
                    }
                    if (status === 204 || s.type === "HEAD") {
                        statusText = "nocontent";
                    } else if (status === 304) {
                        statusText = "notmodified";
                    } else {
                        statusText = response.state;
                        success = response.data;
                        error = response.error;
                        isSuccess = !error;
                    }
                } else {
                    error = statusText;
                    if (status || !statusText) {
                        statusText = "error";
                        if (status < 0) {
                            status = 0;
                        }
                    }
                }
                asyncXHR.status = status;
                asyncXHR.statusText = (nativeStatusText || statusText) + "";
                if (isSuccess) {
                    deferred.resolveWith(callbackContext, [success, statusText, asyncXHR]);
                } else {
                    deferred.abortWith(callbackContext, [asyncXHR, statusText, error]);
                }
                asyncXHR.statusCode(statusCode);
                statusCode = undefined;

                if (fireTKits) {
                    globalEventContext.trigger(isSuccess ? "ajaxSuccess" : "ajaxError", [asyncXHR, s, isSuccess ? success : error]);
                }
                completeDeferred.fireWith(callbackContext, [asyncXHR, statusText]);

                if (fireTKits) {
                    globalEventContext.trigger("ajaxComplete", [asyncXHR, s]);
                    if (!(--ToolKit.active)) {
                        ToolKit.event.trigger("ajaxStop");
                    }
                }
            }
            return asyncXHR;
        }
    });

    ToolKit.each(["get", "post"], function(i, method) {
        ToolKit[method] = function(url, data, callback, type) {
            if (ToolKit.isFunction(data)) {
                type = type || callback;
                callback = data;
                data = undefined;
            }
            return ToolKit.ajax({
                url: url,
                type: method,
                data: data,
                dataType: type || "json",
                success: callback
            });
        };
    });
    ToolKit._evalUrl = function(url) {
        return ToolKit.ajax({
            url: url,
            type: "GET",
            dataType: "script",
            async: false,
            global: false
        });
    };

    function createStandardXHR() {
        try {
            return new window.XMLHttpRequest();
        } catch (e) {}
    }

    function createActiveXHR() {
        try {
            return new window.ActiveXObject("Microsoft.XMLHTTP");
        } catch (e) {
            try {
                return new window.ActiveXObject("Msxml2.XMLHTTP");
            } catch (e) {}
        }
    }
    ToolKit.ajaxSettings.xhr = window.ActiveXObject !== undefined ?
        function() {
            return !this.isLocal && /^(get|post|head|put|delete|options)$/i.test(this.type) && createStandardXHR() || createActiveXHR();
        } : createStandardXHR;

    var xhrId = 0,
        xhrCallbacks = {},
        xhrSupported = ToolKit.ajaxSettings.xhr();
    if (window.ActiveXObject) {
        ToolKit(window).bind("unload", function() {
            for (var key in xhrCallbacks) {
                xhrCallbacks[key](undefined, true);
            }
        });
    }
    support.cors = !!xhrSupported && ("withCredentials" in xhrSupported);
    xhrSupported = support.ajax = !!xhrSupported;

    ToolKit.ajaxPrefilter("script", function(s) {
        if (s.cache === undefined) {
            s.cache = false;
        }
        if (s.crossDomain) {
            s.type = "GET";
            s.global = false;
        }
        return true;
    });
    ToolKit.ajaxTransport("script", function(s) {
        if (s.crossDomain) {
            var script, head = document.head || ToolKit("head")[0] || document.documentElement;
            return {
                send: function(_, callback) {
                    script = document.createElement("script");
                    script.async = true;
                    if (s.scriptCharset) {
                        script.charset = s.scriptCharset;
                    }
                    script.src = s.url;
                    script.onload = script.onreadystatechange = function(_, isAbort) {
                        if (isAbort || !script.readyState || /loaded|complete/.test(script.readyState)) {
                            script.onload = script.onreadystatechange = null;
                            if (script.parentNode) {
                                script.parentNode.removeChild(script);
                            }
                            script = null;
                            if (!isAbort) {
                                callback(200, "success");
                            }
                        }
                    };
                    head.insertBefore(script, head.firstChild);
                },

                abort: function() {
                    if (script) {
                        script.onload(undefined, true);
                    }
                }
            };
        }
    });

    if (xhrSupported) {
        ToolKit.ajaxTransport(function(options) {
            if (!options.crossDomain || support.cors) {
                var callback;
                return {
                    send: function(headers, complete) {
                        var i, xhr = options.xhr(),
                            id = ++xhrId;
                        xhr.open(options.type, options.url, options.async, options.username, options.password);
                        if (options.xhrFields) {
                            for (i in options.xhrFields) {
                                xhr[i] = options.xhrFields[i];
                            }
                        }
                        if (options.mimeType && xhr.overrideMimeType) {
                            xhr.overrideMimeType(options.mimeType);
                        }
                        if (!options.crossDomain && !headers["X-Requested-With"]) {
                            headers["X-Requested-With"] = "XMLHttpRequest";
                        }
                        for (i in headers) {
                            if (headers[i] !== undefined) {
                                xhr.setRequestHeader(i, headers[i] + "");
                            }
                        }
                        xhr.send((options.hasContent && options.data) || null);
                        callback = function(_, isAbort) {
                            var status, statusText, responses;
                            if (callback && (isAbort || xhr.readyState === 4)) {
                                delete xhrCallbacks[id];
                                callback = undefined;
                                xhr.onreadystatechange = null;
                                if (isAbort) {
                                    if (xhr.readyState !== 4) {
                                        xhr.abort();
                                    }
                                } else {
                                    responses = {};
                                    status = xhr.status;
                                    if (typeof xhr.responseText === "string") {
                                        responses.text = xhr.responseText;
                                    }
                                    try {
                                        statusText = xhr.statusText;
                                    } catch (e) {
                                        statusText = "";
                                    }
                                    if (!status && options.isLocal && !options.crossDomain) {
                                        status = responses[options.responseFields[options.dataTypes[0]]] ? 200 : 404;
                                    } else if (status === 1223) {
                                        status = 204;
                                    }
                                }
                            }
                            if (responses) {
                                complete(status, statusText, responses, xhr.getAllResponseHeaders());
                            }
                        };

                        if (!options.async) {
                            callback();
                        } else if (xhr.readyState === 4) {
                            setTimeout(callback);
                        } else {
                            xhr.onreadystatechange = xhrCallbacks[id] = callback;
                        }
                    },
                    abort: function() {
                        if (callback) {
                            callback(undefined, true);
                        }
                    }
                };
            }
        });
    }

    ToolKit(function() {
        var val, div, body, container;

        body = document.getElementsByTagName("body")[0];
        if (!body || !body.style) {
            return;
        }
        div = document.createElement("div");
        container = document.createElement("div");
        container.style.cssText = "position:absolute;border:0;width:0;height:0;top:0;left:-9999px";
        body.appendChild(container).appendChild(div);

        if (div.style.zoom !== undefined) {
            div.style.cssText = "display:inline;margin:0;border:0;padding:1px;width:1px;zoom:1;";
            support.inlineBlockNeedsLayout = val = div.offsetWidth === 3;
            if (val) {
                body.style.zoom = 1;
            }
        }
        body.removeChild(container);
    });

    window.ToolKit = window.$ = ToolKit;
    return ToolKit;
})(window);
View Code

 

posted @ 2016-06-15 17:26  工具包  阅读(800)  评论(0编辑  收藏  举报