﻿/*********************************************************/
/***** Class to load a page in the admin area ************/
/*********************************************************/
var Pageloader = new Class({
    Implements: [Options, Events],
    //--- Options.
    options: {
        container: 'content',
        method: 'post',
        errorMessage: 'Det lykkedes ikke at loade siden, fortsætter dette problem bedes du kontakte udbyderen af systemet!'
    },

    //--- Initialize the class.
    initialize: function (options) {
        this.setOptions(options);
        $(this.options.container).set('text', '');
    },

    //--- Function to load the page.
    loadPage: function (url, rel) {
        var waiter = new Spinner($(this.options.container));
        var req = new Request.HTML({
            url: url,
            method: this.options.method,
            onRequest: function () {
                waiter.show();
            },
            onSuccess: function (html) {
                $(this.options.container).adopt(html);
                if ($(rel) != null) {
                    //--- Lav treeview
//                    var mytree = new Treeview();
//                    mytree.loadTree(rel);

                    //--- Laver højreklik menu på treeview
                    var context = new ContextMenu({
                        targets: '.link', //--- Menu kun tilgængelig på elementer med class=".link"
                        menu: 'contextmenu',
                        actions: {
                            copy: function (element, ref) { //--- copy action changes the element's color to red and disables the menu
                                element.setStyle('color', 'red');
                                //ref.disable();
                            },
                            edit: function (element, ref) {
                                document.id('iframe').setProperty('src', element.get('href'));
                            },
                            'delete': function (element, ref) {
//                                var urlToDelete = $$('ul#contextmenu li a').get('rel')[1] + element.get('href').split('/')[3]
//                                var req = new Request({
//                                    method: 'post',
//                                    url: urlToDelete,
//                                    onSuccess: function (resp) {
//                                        if (resp) {
//                                            var menuUrl = resp.split(',')[0];
//                                            var frontUrl = resp.split(',')[1];
//                                            var menuId = resp.split(',')[2];

//                                            $('iframe').setProperty('src', frontUrl);
//                                            loadMenu(menuUrl, frontUrl, menuId);
//                                        }
//                                    }
//                                })
//                                req.send();

                                //alert($$('ul#contextmenu li a').get('rel')[1] + element.get('href').split('/')[3]);
                                //$('iframe').setProperty('src', '/Admin/Front');
                                //loadMenu('/Admin/Sitemenu/1', '/admin/Front', 'sitetree');
                            }
                        },
                        offsets: { x: -5, y: -5 }
                    });
                }
                waiter.destroy();
            } .bind(this),

            onFailure: function () {
                $(this.options.container).set('text', this.options.errorMessage);
                waiter.destroy();
            } .bind(this)
        });
        req.send();
    }
});

/*****************************************/
/***** Class to generate tabs ************/
/*****************************************/

var Tabs = new Class({
    Implements: [Options, Events],
    options: {
        selectedTabCssClass: 'selectedTab',
        selectedSectionCssClass: 'selectedTabSection',
        firstShow: 0
        /*onShow: $empty,
        onHide: $empty*/
    },
    tabs: [],
    initialize: function(containers, tabs, options) {
        this.setOptions(options);
        $$(tabs).each(function(tab, index) {
            this.addSection(tab, $$(containers)[index]);
        }, this);
        this.show(this.options.firstShow);
    },

    addSection: function(tab, container) {
        this.tabs.include(tab);
        tab.store('container', container);
        this.attach(tab);
    },

    attach: function(tab) {
        tab.addEvent('click', function(event) {
            event.preventDefault();
            this.show(this.tabs.indexOf(tab));
        } .bind(this));
    },

    show: function(index) {
        if (this.current === index) return;
        this.tabs.each(function(tab, i) {
            var container = tab.retrieve('container');
            if (index === i) {
                tab.addClass(this.options.selectedTabCssClass);
                container.addClass(this.options.selectedSectionCssClass);
                container.setStyle('display', 'block');
                this.fireEvent('onShow', [i, tab, container]);
            }
            else {
                tab.removeClass(this.options.selectedTabCssClass);
                container.removeClass(this.options.selectedSectionCssClass);
                container.setStyle('display', 'none');
                if (this.current === i || this.current != null)
                    this.fireEvent('onHide', [i, tab, container]);
            }
        }, this);
        this.current = index;
    }
});

var AjaxTabs = new Class({
    Extends: Tabs,
    options: {
        cache: true,
        urls: []
    },

    show: function(index, force) {
        var tab = this.tabs[index];
        var url = this.options.urls[index] || tab.get('href');
        if (!url || force || (this.options.cache && tab.retrieve('loaded'))) {
            this.parent(index);
        }
        else {
            this.fetchTabContent(index, url);
        }
    },

    fetchTabContent: function(index, url) {
        var tab = this.tabs[index];
        var container = tab.retrieve('container');
        var request = tab.retrieve('tabAjax');
        if (!request) {
            request = new Request.HTML({
                update: container,
                method: 'get',
                url: url,
                onSuccess: function() {
                    this.show(index, true);
                    tab.store('loaded');
                } .bind(this)
            });
            tab.store('tabAjax', request);
        }
        request.send();
    }
});

/**************************************************/
/***** Class to to generate a treeview ************/
/**************************************************/
var Itl = {
    name: 'ITL A/S'
};

Itl.Tree = new Class({
    Implements: [Options, Events],
    options: {
        url: '',
        method: 'post',
        container: 'mytree',
        img: {
            imagePath: '/content/tree/',
            imageOpen: 'tree_open.png',
            imageClosed: 'tree_closed.png',
            imageNone: 'tree_none.gif',
            imageLoader: 'tree_loader.gif'
        },
        useContextmenu: false,
        useReordering: false,
        reorderPostUrl: ''
    },

    initialize: function (options) {
        this.setOptions(options);
        this.loadData(0, $(this.options.container));
    },

    loadData: function (parentId, injectTo) {
        var dataUrl = this.options.url;

        var request = new Request.JSON({
            url: dataUrl,
            method: this.options.method,
            onRequest: function () {
                if (parentId > 0) this.toggleLoader(injectTo);
            } .bind(this),
            onComplete: function (nodes) {
                this.requestReady(nodes, injectTo, parentId);
            } .bind(this)
        }, this).send('id=' + parentId);
    },

    //--- Data has been received, create treeview object and inject it into the container
    requestReady: function (nodes, injectTo, parentId) {
        var ul = this.createTree(nodes, injectTo, parentId);
        ul.inject(injectTo);

        //--- Tilføjer sortering til side menu.
        this.reorderMenu(this.options.reorderPostUrl, '#' + ul.get('id'));

        //--- Method was called from toggleNode, call it back so the node gets toggled
        if (parentId) {
            this.toggleNode(injectTo);
        }

        //--- Turn off the loader icon
        if (parentId > 0) this.toggleLoader(injectTo);

        //--- Tilføjer sortering til side menu.
        //        if (this.options.useReordering) {
        //            var ulId = '';
        //            document.id(this.options.container).getElements('ul').each(function (ulItem) {
        //                //ulId += ',#' + ulItem.getProperty('id');
        //                ulId = '#' + ulItem.getProperty('id');
        //            });

        //            this.reorderMenu(this.options.reorderPostUrl, ulId.substring(1, ulId.length));
        //        }
    },

    //--- Create the root of the treeview
    createTree: function (nodes, injectTo, parentId) {
        //if (parentId == 0) {
        //    var imgdiv = new Element('div', { 'styles': { 'margin': '5px 0 0 5px'} }).inject(injectTo);
        //    var homeImg = new Element('img', { 'src': '/content/icons/16x16/home.png', 'styles': { 'vertical-align': 'middle', 'padding-right': '2px'} }).inject(imgdiv);
        //    var link = new Element('a', { 'class': 'link', 'styles': { 'cursor': 'default'} }).set('text', 'Index').inject(imgdiv);
        //}
        var ul = new Element('ul', { 'id': 'tree' });

        nodes.each(function (node) {
            var li = this.createTreeNode(node);
            li.inject(ul);

            if (parentId > 0) {
                ul.setProperties({ 'class': 'sub', 'id': 'tree' + node.ItemId });
            }
        }, this);

        //--- Tilføjer context menu til treeview.
        //(function () {
        //    this.contextMenu();
        //} .bind(this)).delay(50);

        //--- Retunere den nyoprettede ul liste.
        return ul;
    },

    //--- Create a single treenode.
    createTreeNode: function (node) {
        var li = new Element('li', { 'alt': node.ItemId, 'class': 'context' });
        var imgArrow = new Element('img', { 'class': 'arrow' }).inject(li);
        var link = new Element('a', { 'href': node.Link, 'class': 'link' }).inject(li);
        var span = new Element('span').setProperty('id', 'item' + node.ItemId).set('text', node.Name).inject(link);
        var imgItem = new Element('div', { 'class': node.cssClass }).inject(span, 'top');

        //--- Hvis der findes undermenuer loades billed-pil.
        if (node.Childs != null) {
            imgArrow.setProperty('src', this.options.img.imagePath + this.options.img.imageClosed);
        }
        else {
            imgArrow.setProperty('src', this.options.img.imagePath + this.options.img.imageNone);
        }

        //--- Tilføjer click event til links
        link.addEvent('click', function (e) {
            e.stop();
            $$('li a').each(function (injectTo) {
                injectTo.setStyle('font-weight', '');
            });
            li.getElement('a').setStyle('font-weight', 'bold');

            this.loadContent(link.get('href'));
        } .bind(this));

        //--- Tilføj click event på billed pil.
        imgArrow.addEvent('click', function (e) {
            e.stop();
            this.toggleNode(li);
        } .bind(this));

        return li;
    },

    loadContent: function (href) {
        this.fireEvent('loadContent', [href], 50);
    },

    contextMenu: function () {
        var context = new ContextMenu({
            targets: '.context', //--- Menu kun tilgængelig på elementer med class="context"
            menu: 'contextmenu',
            actions: {
                add: function (element, ref) { //--- copy action changes the element's color to red and disables the menu
                    alert('oprettelse ' + element.getFirst('a').get('href'));
                },
                copy: function (element, ref) { //--- copy action changes the element's color to red and disables the menu
                    alert('kopiering');
                },
                edit: function (element, ref) {
                    alert('redigering');
                },
                'delete': function (element, ref) {
                    alert('sletning');
                    //alert('/' + element.getProperty('href').split('/')[1] + '/' + $(contextMenuId).getElement('.delete').getProperty('rel').split('/')[2] + '/' + element.getProperty('href').split('/')[3]);
                    //var urlToDelete = '/' + element.getProperty('href').split('/')[1] + '/' + $(contextMenuId).getElement('.delete').getProperty('rel').split('/')[2] + '/' + element.getProperty('href').split('/')[3]
                    //var req = new Request({
                    //    method: 'post',
                    //    url: urlToDelete,
                    //    onSuccess: function (resp) {
                    //        if (resp) {
                    //            element.getParent().dispose();
                    //            $('iframe').setProperty('src', '/' + element.get('href').split('/')[1] + '/Index');
                    //        }
                    //    }
                    //})
                    //req.send();
                }
            },
            offsets: { x: -5, y: -5 }
        });
    },

    //--- Reordering treeview
    reorderMenu: function (reorderPostUrl, ulId) {
        document.ondragstart = function () {
            return false;
        };
        var sb = new Sortables(ulId, {
            constrain: true,
            clone: true,
            revert: true,
            //handle: '.moveitem',

            onStart: function (elm) {
                elm.setStyles({ 'background': '#add8e6' });
            },

            onComplete: function (elm) {
                elm.setStyle('background', 'transparent');

                var sortorder = '';
                var parent = elm.getParent('ul');
                //alert(parent.get('id'));

                parent.getChildren('li').each(function (li) {
                    sortorder += li.get('alt') + ',';
                });

                var req = new Request({
                    url: reorderPostUrl,
                    method: 'post',
                    autoCancel: true,
                    data: 'sortorder=' + sortorder
                    /*onRequest: function () {
                    //$('message-box').set('text', 'Updating the sort order in the database.');
                    alert('Opdatere databasen');
                    },
                    onSuccess: function (resp) {
                    //$('message-box').set('text', 'Database has been updated.');
                    alert(resp);
                    }*/
                });
                req.send();
            }
        });
    },

    //--- Turn loader icon on/off
    toggleLoader: function (node) {
        var img = node.getFirst('a').getFirst('span').getFirst('div');
        if (img) {
            //img.setProperties({ 'src': this.options.img.imagePath + this.options.img.imageLoader });
            img.toggleClass('loader');
            //img.setProperties({ 'src': this.options.img.imagePath + this.options.img.imageOpen });
            img.toggleClass('folder');
        }
    },

    //--- Function to expand or collpase node.
    toggleNode: function (elm) {
        var ul = elm.getFirst("ul");

        if (!ul) {
            this.loadData(elm.get("alt"), elm);
        }

        if (ul) {
            if (ul.getStyle('display') == 'block') {
                ul.setStyle('display', 'none');
                elm.getFirst('img').setProperties({ 'src': this.options.img.imagePath + this.options.img.imageClosed });
            } else {
                ul.setStyle('display', 'block');
                elm.getFirst('img').setProperties({ 'src': this.options.img.imagePath + this.options.img.imageOpen });
            }
        }

        //if (ul.getStyle('display') == 'block') {
        //    this.collapseNode(ul, elm.getFirst('img'));
        //} else {
        //    this.expandNode(ul, elm.getFirst('img'));
        //}
    },

    //--- Function to expand node.
    expandNode: function (ul, img) {
        ul.setStyle('display', 'block');
        img.setProperties({ 'src': this.options.img.imagePath + this.options.img.imageOpen });
        Cookie.write(ul.getProperty('id'), true, { duration: 1, path: '/' });
    },

    //--- Function to collpase node.
    collapseNode: function (ul, img) {
        ul.setStyle('display', 'none');
        img.setProperties({ 'src': this.options.img.imagePath + this.options.img.imageClosed });
        Cookie.dispose(ul.getProperty('id'), { path: '/' });
    }
});

/**************************************************/
/***** Class to to generate a treeview ************/
/**************************************************/
var Treeview = new Class({
    Implements: [Options, Events],
    options: {
        url: '',
        method: 'post',
        container: 'mytree',
        rootName: '',
        img: {
            imagePath: '/content/tree/',
            imageOpen: 'tree_open.png',
            imageClosed: 'tree_closed.png',
            imageNone: 'tree_none.gif'
        },
        useJsonCall: false,
        useContextmenu: false,
        useReordering: false,
        reorderPostUrl: ''
    },

    initialize: function (url, controllerName, contextMenuId, options) {
        this.setOptions(options);
        this.loadData(url, controllerName, contextMenuId, this.options.container);
    },

    loadData: function (url, controllerName, contextMenuId, container) {
        var data;
        var request = new Request.JSON({
            url: url,
            method: this.options.method,
            onComplete: function (jsonObj) {
                this.buildTree(jsonObj, controllerName, contextMenuId, $(container));
                if (this.options.useReordering) {
                    var ulId = '';
                    document.id(container).getElements('ul').each(function (ulItem) {
                        ulId += ',#' + ulItem.getProperty('id');
                    });

                    this.reorderMenu(this.options.reorderPostUrl, ulId.substring(1, ulId.length));
                }
            } .bind(this)
        }, this).send();
    },

    buildTree: function (data, controllerName, contextMenuId, elm) {
        if (elm.get('tag') == 'div') {
            //elm.set('html', '');
        }

        var ul = new Element('ul', { 'id': 'tree' }).inject(elm);

        data.each(function (item) {
            var li = new Element('li', { 'alt': item.ItemId }).inject(ul);
            var imgArrow = new Element('img', { 'class': 'arrow' }).inject(li);
            var className = 'link';
            if (item.Link == '/data' || item.Link == 'javascript:void(0);') {
                className = 'linkno';
            }
            var link = new Element('a', { 'href': item.Link, 'class': className }).inject(li);
            var span = new Element('span').set('text', item.Name).inject(link);
            //var moveImg = new Element('img', { 'class': 'moveitem', 'styles': { 'cursor': 'move' }, 'class': 'item', 'src': '/Content/icons/16x16/move.png' }).inject(span, 'top');
            var imgItem = new Element('img', { 'class': 'item', 'src': '/Content/icons/16x16/' + item.Icon.Icon }).inject(span, 'top');

            if (elm.get('tag') == 'li') {
                ul.setProperties({ 'class': 'sub', 'id': 'tree' + item.ItemId });
            }

            //--- Hvis der findes undermenuer loades disse.
            if (item.Childs != null) {
                if (item.Childs.length > 0) {
                    this.buildTree(item.Childs, controllerName, contextMenuId, li);
                    var subul = li.getElement('ul');

                    if (Cookie.read(subul.getProperty('id')) == null) {
                        subul.setStyle('display', 'none');
                        imgArrow.setProperty('src', this.options.img.imagePath + this.options.img.imageClosed);
                    }
                    else {
                        subul.setStyle('display', 'block');
                        imgArrow.setProperty('src', this.options.img.imagePath + this.options.img.imageOpen);
                    }
                }
                else {
                    imgArrow.setProperty('src', this.options.img.imagePath + this.options.img.imageNone);
                }
            }
            else {
                imgArrow.setProperty('src', this.options.img.imagePath + this.options.img.imageNone);
            }

            //--- Tilføjer click event til links
            link.addEvent('click', function (e) {
                e.stop();
                $$('li a').each(function (elm) {
                    elm.setStyle('font-weight', '');
                });
                li.getElement('a').setStyle('font-weight', 'bold');

                //                $$('li a.link').each(function (elm) {
                //                    elm.removeClass('activeright');
                //                });
                //                $$('li a.link span').each(function (elm) {
                //                    elm.removeClass('activeleft');
                //                });
                //                li.getElement('.link').addClass('activeright');
                //                li.getElement('span').addClass('activeleft');

                //if (this.options.useJsonCall) {
                $('iframe').setProperty('src', link.getProperty('href'));
                //}
                //else {
                //    var request = new Request.JSON({
                //        url: link.getProperty('href'),
                //        method: this.options.method,
                //        onComplete: function (jsonObj) {
                //            return jsonObj;
                //        } .bind(this)
                //    }, this).send();
                //}
            });

            //--- Tilføj click event på billed pil.
            imgArrow.addEvent('click', function () {
                this.toggleNode(subul, imgArrow);
            } .bind(this));
        }, this);

        if (this.options.useContextmenu) {
            var context = new ContextMenu({
                targets: '.link', //--- Menu kun tilgængelig på elementer med class=".link"
                menu: contextMenuId,
                actions: {
                    copy: function (element, ref) { //--- copy action changes the element's color to red and disables the menu
                        element.setStyle('color', 'red');
                    },
                    edit: function (element, ref) {
                        document.id('iframe').setProperty('src', element.get('href'));
                    },
                    editprofile: function (element, ref) {
                        document.id('iframe').setProperty('src', $(contextMenuId).getElement('.editprofile').getProperty('rel') + element.getProperty('href').split('/')[3]);
                    },
                    'delete': function (element, ref) {
                        if (!confirm('Er du sikke på du vil slette?')) return false;
                        var urlToDelete = '/' + element.getProperty('href').split('/')[1] + '/' + $(contextMenuId).getElement('.delete').getProperty('rel').split('/')[2] + '/' + element.getProperty('href').split('/')[3]
                        var req = new Request({
                            method: 'post',
                            url: urlToDelete,
                            onSuccess: function (resp) {
                                if (resp) {
                                    element.getParent().dispose();
                                    $('iframe').setProperty('src', '/' + element.get('href').split('/')[1] + '/Index');
                                }
                            }
                        })
                        req.send();
                    }
                },
                offsets: { x: -5, y: -5 }
            });
        }
    },

    reorderMenu: function (reorderPostUrl, ulId) {
        document.ondragstart = function () {
            return false;
        };
        var sb = new Sortables(ulId, {
            constrain: true,
            clone: true,
            revert: true,
            handle: '.item',

            onStart: function (elm) {
                elm.setStyles({ 'background': '#add8e6' });
            },

            onComplete: function (elm) {
                elm.setStyle('background', 'transparent');

                var sortorder = '';
                var parent = elm.getParent('ul');

                parent.getChildren('li').each(function (li) {
                    sortorder += li.get('alt') + ',';
                });

                var req = new Request({
                    url: reorderPostUrl,
                    method: 'post',
                    autoCancel: true,
                    data: 'sortorder=' + sortorder
                    /*onRequest: function () {
                    //$('message-box').set('text', 'Updating the sort order in the database.');
                    alert('Opdatere databasen');
                    },
                    onSuccess: function (resp) {
                    //$('message-box').set('text', 'Database has been updated.');
                    alert(resp);
                    }*/
                });
                req.send();
            }
        });
    },

    //--- Function to expand or collpase node.
    toggleNode: function (ul, img) {
        if (ul.getStyle('display') == 'block') {
            this.collapseNode(ul, img);
        } else {
            this.expandNode(ul, img);
        }
    },

    //--- Function to expand node.
    expandNode: function (ul, img) {
        ul.setStyle('display', 'block');
        img.setProperties({ 'src': this.options.img.imagePath + this.options.img.imageOpen });
        Cookie.write(ul.getProperty('id'), true, { duration: 1, path: '/' });
    },

    //--- Function to collpase node.
    collapseNode: function (ul, img) {
        ul.setStyle('display', 'none');
        img.setProperties({ 'src': this.options.img.imagePath + this.options.img.imageClosed });
        Cookie.dispose(ul.getProperty('id'), { path: '/' });
    }
});

/*********************************************************/
/***** Class to generate layout for admin pages **********/
/*********************************************************/
var PageLayout = new Class({
    Implements: [Options, Events],

    options: {
        containerElm: '',
        headerElm: '',
        footerElm: '',
        contentContainerElm: '',
        indexElm: '',
        splitterElm: '',
        draggerElm: '',
        contentElm: '',
        indexWidth: 200
    },

    initialize: function (options) {
        this.setOptions(options);
        if (!this.container) {
            this.render();
            this.dragBorder();
        }
        window.addEvent('resize', this.resize.bind(this));

        $('panel-header-open').addEvent('click', function (e) {
            e.stop();
            $('left-collapsed').setStyle('display', 'block');
            $('left').setStyle('display', 'none');
            this.toggleIndex(false);
        } .bind(this));

        $('panel-header-closed').addEvent('click', function (e) {
            e.stop();
            $('left').setStyle('display', 'block');
            $('left-collapsed').setStyle('display', 'none');
            this.toggleIndex(true);
        } .bind(this));
    },

    dragBorder: function () {
        var dragElement = $(this.options.draggerElm);
        //var overlay = new Spinner('iframe');
        this.dragSplitter = new Drag.Move(dragElement, {
            snap: 0,
            limit: { x: [this.options.indexWidth, (window.getSize().x / 2)] },
            modifiers: { x: 'left', y: false },
            onBeforeStart: function (el) {
                el.set('opacity', '.50');
                $('ifarmeOverlay').setStyle('display', 'block');
            },
            onComplete: function (el) {
                var newXvalue = dragElement.getCoordinates().left
                $(this.options.indexElm).setStyle('width', newXvalue - 7);
                $(this.options.contentElm).setStyles({ left: $(this.options.draggerElm).getCoordinates().right }).setBoxWidth(window.getWidth() - 5 - (newXvalue));
                el.set('opacity', '1');
                $('ifarmeOverlay').setStyle('display', 'none');
            } .bind(this)
        });
    },

    toggleIndex: function (indexOpen) {
        if (!indexOpen) {
            this.oldIndexWidth = $(this.options.indexElm).getCoordinates().right;
            //--- Sætter bredde på index container
            $(this.options.indexElm).setStyle('background', 'transparent url(/Content/admin/panel-closed-bg.png) repeat-y').setBoxWidth(30);
            //--- Sætter venstre afstand på dragger
            $(this.options.draggerElm).setStyles({ 'left': 30, 'cursor': 'default' });
            //--- Sætter bredde på indholds container
            $(this.options.contentElm).setStyle('left', 35).setBoxWidth(window.getSize().x - 35);
            //--- Sætter top på panel-icon
            $$('.panel-icon').setStyle('top', $(this.options.indexElm).getBoxSize()[1] / 2 - 50);
            this.dragSplitter.detach();
        } else {
            //--- Sætter bredde på index container
            $(this.options.indexElm).setStyle('background', '#fff').setBoxWidth(this.oldIndexWidth);
            //--- Sætter venstre afstand på dragger
            $(this.options.draggerElm).setStyles({ 'left': this.oldIndexWidth, 'cursor': 'e-resize' });
            //--- Sætter bredde på indholds container
            $(this.options.contentElm).setStyle('left', this.oldIndexWidth + 5).setBoxWidth(window.getSize().x - this.oldIndexWidth - 5);
            this.dragSplitter.attach();
        }
    },

    render: function () {
        //--- Størelse på browser vindue.
        var ws = window.getSize();
        //--- Størelse på header div.
        if (this.options.headerElm)
            var hs = $(this.options.headerElm).getSize();
        //--- Størelse på footer div.
        if (this.options.footerElm)
            var fs = $(this.options.footerElm).getSize();
        //--- Størelse på index div.
        var is = $(this.options.indexElm).getSize();

        //--- Sætter styles på container.
        $(this.options.containerElm).setBoxSize(ws.x, ws.y);
        //--- Sætter styles på header.
        if (this.options.headerElm)
            $(this.options.headerElm).setBoxSize(ws.x, hs.y);
        //--- Sætter styles på footer.
        if (this.options.footerElm)
            $(this.options.footerElm).setBoxSize(ws.x, fs.y);

        var hfHeight = 0;
        if (this.options.headerElm || this.options.footerElm)
            hfHeight = hs.y + fs.y

        //--- Sætter styles på indholds container.
        $(this.options.contentContainerElm).setBoxSize(ws.x, ws.y - hfHeight);
        //--- Sætter styles på index.
        $(this.options.indexElm).setBoxSize(this.options.indexWidth, ws.y - hfHeight);
        //--- Sætter styles på menu-container felt i index
        $('menu-container').setBoxHeight(ws.y - hfHeight - 150);
        $('menu').setBoxHeight(ws.y - hfHeight - 185);
        //--- Sætter styles på dragger
        $(this.options.draggerElm).setStyles({
            left: $(this.options.indexElm).getStyle('width').toInt() + 7,
            top: (hs) ? hs.y:0
        }).setBoxHeight(ws.y - hfHeight);
        //--- Sætter styles på indhold
        $(this.options.contentElm).setStyles({
            left: $(this.options.indexElm).getStyle('width').toInt() + 12,
            top: (hs) ? hs.y:0
        }).setBoxSize(ws.x - ($(this.options.indexElm).getStyle('width').toInt() + 12), ws.y - hfHeight);
        //--- Sætter styles på indholds felt i indhold
        $(this.options.contentElm).getElementById('iframe').setBoxHeight(ws.y - hfHeight);
    },

    resize: function () {
        //--- Størelse på browser vindue.
        var ws = window.getSize();
        //--- Størelse på header div.
        if (this.options.headerElm)
            var hs = $(this.options.headerElm).getSize();
        //--- Størelse på footer div.
        if (this.options.footerElm)
            var fs = $(this.options.footerElm).getSize();
        //--- Størelse på index div.
        var is = $(this.options.indexElm).getSize();

        //--- Sætter størrelse på container
        $(this.options.containerElm).setBoxSize(ws.x, ws.y);
        //--- Sætter størrelse på header
        if (this.options.headerElm)
            $(this.options.headerElm).setBoxSize(ws.x, hs.y);
        //--- Sætter størrelse på footer
        if (this.options.footerElm)
            $(this.options.footerElm).setBoxSize(ws.x, fs.y);

        var hfHeight = 0;
        if (this.options.headerElm || this.options.footerElm)
            hfHeight = hs.y + fs.y

        //--- Sætter størrelse på indholds container
        $(this.options.contentContainerElm).setBoxSize(ws.x, ws.y - hfHeight);
        //--- Sætter størrelse på index
        $(this.options.indexElm).setBoxHeight(ws.y - hfHeight);
        //--- Sætter størrelse på indholds felt i index
        $('menu-container').setBoxHeight(ws.y - hfHeight - 150);
        $('menu').setBoxHeight(ws.y - hfHeight - 185);
        //--- Sætter størrelse på dragger
        $(this.options.draggerElm).setBoxHeight(ws.y - hfHeight);
        //--- Sætter størrelse på indhold
        $(this.options.contentElm).setBoxSize(ws.x - (is.x + 5), ws.y - hfHeight);
        //--- Sætter størrelse på indholds felt i indhold
        $(this.options.contentElm).getElementById('iframe').setBoxHeight(ws.y - hfHeight);
        //--- Kalder drag funktion.
        this.dragBorder();
    }
});

/*********************************************************/
/***** Class to generate context menu ********************/
/*********************************************************/
var ContextMenu = new Class({
    //implements
    Implements: [Options, Events],

    //options
    options: {
        actions: {},
        menu: 'contextmenu',
        stopEvent: true,
        targets: 'body',
        trigger: 'contextmenu',
        offsets: { x: 0, y: 0 },
        /*onShow: $empty,
        onHide: $empty,
        onClick: $empty,*/
        fadeSpeed: 200
    },

    //initialization
    initialize: function (options) {
        //set options
        this.setOptions(options)

        //option diffs menu
        this.menu = $(this.options.menu);
        this.targets = $$(this.options.targets);

        //fx
        this.fx = new Fx.Tween(this.menu, { property: 'opacity', duration: this.options.fadeSpeed });

        //hide and begin the listener
        this.hide().startListener();

        //hide the menu
        this.menu.setStyles({ 'position': 'absolute', 'top': '-900000px', 'display': 'block' });
    },

    //get things started
    startListener: function () {
        /* all elemnts */
        this.targets.each(function (el) {
            /* show the menu */
            el.addEvent(this.options.trigger, function (e) {
                //enabled?
                if (!this.options.disabled) {
                    //prevent default, if told to
                    if (this.options.stopEvent) { e.stop(); }
                    //record this as the trigger
                    this.options.element = $(el);
                    //position the menu
                    this.menu.setStyles({
                        top: (e.page.y + this.options.offsets.y),
                        left: (e.page.x + this.options.offsets.x),
                        position: 'absolute',
                        'z-index': '2000'
                    });
                    //show the menu
                    this.show();
                }
            } .bind(this));
        }, this);

        /* remove click events from menu items */
        this.menu.getElements('a').each(function(item){
            item.removeEvents();
        });

        /* add click events from menu items */
        this.menu.getElements('a').each(function (item) {
            item.addEvent('click', function (e) {
                if (!item.hasClass('disabled')) {
                    this.execute(item.get('href').split('#')[1], $(this.options.element));
                    this.fireEvent('click', [item, e]);
                }
            } .bind(this));
        }, this);

        //hide on body click
        $(document.body).addEvent('click', function () {
            this.hide();
        } .bind(this));
    },

    //show menu
    show: function () {
        this.fx.start(1);
        this.fireEvent('show');
        this.shown = true;
        return this;
    },

    //hide the menu
    hide: function () {
        if (this.shown) {
            this.fx.start(0);
            this.fireEvent('hide');
            this.shown = false;
        }
        return this;
    },

    //disable an item
    disableItem: function (item) {
        this.menu.getElements('a[href$=' + item + ']').addClass('disabled');
        return this;
    },

    //enable an item
    enableItem: function (item) {
        this.menu.getElements('a[href$=' + item + ']').removeClass('disabled');
        return this;
    },

    //diable the entire menu
    disable: function () {
        this.options.disabled = true;
        return this;
    },

    //enable the entire menu
    enable: function () {
        this.options.disabled = false;
        return this;
    },

    //execute an action
    execute: function (action, element) {
        if (this.options.actions[action]) {
            this.options.actions[action](element, this);
        }
        return this;
    }

});

/************************************************************/
/***** Class to generate overlay on page ********************/
/************************************************************/
var Overlay = new Class({
    Implements: [Options, Events],

    options: {
        id: 'overlay',
        color: '#000',
        duration: 500,
        opacity: 0.5,
        zIndex: 5000/*,
		onClick: $empty,
		onClose: $empty,
		onHide: $empty,
		onOpen: $empty,
		onShow: $empty
		*/
    },

    initialize: function (container, options) {
        this.setOptions(options);
        this.container = document.id(container);
        this.overlay = new Element('div', {
            id: this.options.id,
            opacity: 0,
            styles: {
                position: 'absolute',
                background: this.options.color,
                left: 0,
                top: 0,
                'z-index': this.options.zIndex
            },
            events: {
                click: function () {
                    this.fireEvent('click');
                } .bind(this)
            }
        }).inject(this.container);

        this.tween = new Fx.Tween(this.overlay, {
            duration: this.options.duration,
            link: 'cancel',
            property: 'opacity',
            onStart: function () {
                var size = this.container.getScrollSize();
                this.overlay.setStyles({
                    width: size.x,
                    height: size.y
                });
            } .bind(this),
            onComplete: function () {
                this.fireEvent(this.overlay.get('opacity') == this.options.opacity ? 'show' : 'hide');
            } .bind(this)
        });
    },
    open: function () {
        this.fireEvent('open');
        this.tween.start(this.options.opacity);
    },
    close: function () {
        this.fireEvent('close');
        this.tween.start(0);
    }
});


/*********************************************************/
/***** Class to generate popup window ********************/
/*********************************************************/
var Popup = new Class({
    Implements: [Options, Events],
    options: {
        width: 800,
        height: 500,
        top: 0,
        left: 0,
        headline: 'Overskrift',
        overlayId: 'pageOverlay',
        fullpageId: 'pageFullpage',
        popupId: 'windowContainer',
        url: ''
    },

    initialize: function (options) {
        this.setOptions(options);
        this.hidePopup();
        //this.createOverlay(this.options.overlayId, 'darken');
        //this.createFullPage(this.options.fullpageId);
    },

    create: function (html) {
        this.windowContainer = new Element('div', {
            'id': this.options.popupId,
            'class': 'resizeWindow',
            'styles': {
                'width': this.options.width,
                'display': 'block',
                'text-align': 'left',
                'display': 'none',
                'z-index': '1000000000'
            }
        }).inject(document.body); //.inject($(this.options.overlayId));

        //this.windowTop = new Element('div', { 'id': 'windowTop' }).inject(this.windowContainer);
        //this.topSpan = new Element('span').set({ 'text': this.options.headline }).inject(this.windowTop);
        this.windowTop = new Element('div', { 'id': 'windowTop' }).inject(this.windowContainer);
        this.windowClose = new Element('div', { 'id': 'windowClose' }).inject(this.windowContainer).addEvent('click', this.hidePopup.bind(this));
        this.windowMiddle = new Element('div', { 'id': 'windowMiddle', 'class': 'resizeWindow' }).inject(this.windowContainer);
        this.myIFrame = new IFrame({
            id: 'iframe_content',
            src: this.options.url,
            width: '100%',
            height: this.options.height,
            frameborder: '0',
            scrolling: 'no'
        }).inject(this.windowMiddle);
        //this.windowMiddle.adopt(html);
        //this.resizeHandle = new Element('div', { 'id': 'windowResize' }).inject(this.windowContainer);
        var ws = window.getSize();
        if (this.options.top > 0 || this.options.left > 0) {
            this.windowContainer.setPosition({ x: this.options.left, y: this.options.top });
        }
        else {
            this.windowContainer.setPosition({ x: ws.x / 2 - (this.options.width / 2), y: ws.y / 2 - (this.options.height / 2) });
        }
        this.windowContainer.makeDraggable({ handle: this.windowTop, limit: { 'x': [0, 3000], 'y': [0, 3000]} });
        //$$('.resizeWindow').makeResizable({ handle: this.resizeHandle });

        this.windowContainer.setStyle('display', 'block');
    },

    showPopup: function (html) {
        this.create(html);
    },

    hidePopup: function () {
        if ($(this.options.popupId) != null) {
            $(this.options.popupId).dispose();
        }

        $(this.options.overlayId).setStyle('visibility', 'hidden');

        //if ($(this.options.overlayId) != null)
        //    $(this.options.overlayId).dispose();
        //if ($(this.options.fullpageId) != null)
        //    $(this.options.fullpageId).dispose();
        //this.removeOverlay();
    }
});

Element.implement({
    getBorderSizes: function() {
        var s = [];
        s[0] = this.getStyle('border-top-width').toInt();
        s[1] = this.getStyle('border-right-width').toInt();
        s[2] = this.getStyle('border-bottom-width').toInt();
        s[3] = this.getStyle('border-left-width').toInt();
        return s;
    },
    getMarginSizes: function() {
        var s = [];
        s[0] = this.getStyle('margin-top').toInt();
        s[1] = this.getStyle('margin-right').toInt();
        s[2] = this.getStyle('margin-bottom').toInt();
        s[3] = this.getStyle('margin-left').toInt();
        return s;
    },
    getBoxSize: function(el) {
        var size = [0, 0];
        var m = this.getMarginSizes();
        size[1] = this.offsetHeight + (m[0] + m[2]);
        size[0] = this.offsetWidth + (m[1] + m[3]);
        return size;
    },
    setBoxHeight: function(h) {
        var b = this.getBorderSizes();
        var m = this.getMarginSizes();
        h = (h - (b[0] + b[2]) - (m[0] + m[2]));
        this.setStyle('height', h);
    },
    setBoxWidth: function(w) {
        var b = this.getBorderSizes();
        var m = this.getMarginSizes();
        w = (w - (b[1] + b[3]) - (m[1] + m[3]));
        this.setStyle('width', w);
    },
    setBoxSize: function(w, h) {
        var b = this.getBorderSizes();
        var m = this.getMarginSizes();
        h = (h - (b[0] + b[2]) - (m[0] + m[2]));
        w = (w - (b[1] + b[3]) - (m[1] + m[3]));
        this.setStyle('height', h);
        this.setStyle('width', w);
    }
});

/*
---

name: Loop

description: Runs a class method on a periodical

license: MIT-style license.

authors: Ryan Florence <http://ryanflorence.com>

docs: http://moodocs.net/rpflo/mootools-rpflo/Loop

requires:
- Core/Class

provides: [Loop]

...
*/

var Loop = new Class({
    loopCount: 0,
    isLooping: false,
    loopMethod: function () { },

    setLoop: function (fn, delay) {
        wasLooping = this.isLooping;
        if (wasLooping) this.stopLoop();
        this.loopMethod = fn;
        this.loopDelay = delay || 3000;
        if (wasLooping) this.startLoop();
        return this;
    },

    stopLoop: function () {
        this.isLooping = false;
        clearInterval(this.periodical);
        return this;
    },

    startLoop: function (delay, now) {
        if (!this.isLooping) {
            this.isLooping = true;
            if (now) this.looper();
            this.periodical = this.looper.periodical(delay || this.loopDelay, this);
        };
        return this;
    },

    resetLoop: function () {
        this.loopCount = 0;
        return this;
    },

    looper: function () {
        this.loopCount++;
        this.loopMethod(this.loopCount);
        return this;
    }

});

/*
---

name: "SlideShow"

description: "Extensible mid-level class that manages transitions of elements that share the same space, typically for slideshows, tabs, and galleries."

license: "MIT-style license."

authors: "Ryan Florence <http://ryanflorence.com>"

requires:
- Core/Fx.Tween
- Core/Slick.Parser
- Loop/Loop

provides:
- SlideShow

...
*/

(function () {

    var SlideShow = this.SlideShow = new Class({

        Implements: [Options, Events, Loop],

        options: {
            /*
            onShow: function(){},
            onShowComplete: function(){},
            onReverse: function(){},
            onPlay: function(){},
            onPause: function(){},
            */
            delay: 7000,
            transition: 'crossFade',
            duration: 500,
            autoplay: false,
            dataAttribute: 'data-slideshow',
            selector: '> *',
            initialSlideIndex: 0
        },

        transitioning: false,
        reversed: false,

        initialize: function (element, options, noSetup) {
            this.element = document.id(element);
            this.setOptions(options);
            if (!noSetup) this.setup();
        },

        setup: function (options) {
            if (options) this.setOptions(options);
            this.slides = this.element.getElements(this.options.selector);
            this.setupElement().setupSlides();
            this.current = this.current || this.slides[this.options.initialSlideIndex];
            this.index = this.current.retrieve('slideshow-index');
            this.setLoop(this.show.pass(this.reversed ? 'previous' : 'next', this), this.options.delay);
            if (this.options.autoplay) this.play();
            return this;
        },

        show: function (slide, options) {
            if (slide == 'next' || slide == 'previous') slide = this[slide + 'Slide']();
            if (typeof slide == 'number') slide = this.slides[slide];
            if (slide == this.current || this.transitioning) return this;

            this.transitioning = true;
            this.current.store('slideshow:oldStyles', this.current.get('style'));

            var transition = (options && options.transition) ? options.transition : slide.retrieve('slideshow-transition'),
			duration = (options && options.duration) ? options.duration : slide.retrieve('slideshow-duration'),
			previous = this.current.setStyle('z-index', 1),
			next = this.reset(slide).setStyle('z-index', 0),
			nextIndex = this.index = next.retrieve('slideshow-index')
            slideData = {
                previous: { element: previous, index: previous.retrieve('slideshow-index') },
                next: { element: next, index: nextIndex }
            };

            this.fireEvent('show', slideData);

            SlideShow.transitions[transition]({
                previous: previous,
                next: next,
                duration: duration,
                instance: this
            });

            (function () {
                previous.setStyle('display', 'none');
                this.fireEvent('showComplete', slideData);
                this.transitioning = false;
            }).bind(this).delay(duration);

            this.current = next;
            return this;
        },

        play: function () {
            this.startLoop();
            this.fireEvent('play');
            return this;
        },

        pause: function () {
            this.stopLoop();
            this.fireEvent('pause');
            return this;
        },

        reverse: function () {
            this.setLoop(this.show.pass(this.reversed ? 'next' : 'previous', this), this.options.delay);
            this.reversed = !this.reversed;
            this.fireEvent('reverse');
            return this;
        },

        setupElement: function () {
            this.storeData(this.element);
            this.options.duration = this.element.retrieve('slideshow-duration');
            this.options.transition = this.element.retrieve('slideshow-transition');
            this.options.delay = this.element.retrieve('slideshow-delay');
            if (this.element.getStyle('position') == 'static') this.element.setStyle('position', 'relative');
            return this;
        },

        setupSlides: function () {
            this.slides.each(function (slide, index) {
                slide.store('slideshow-index', index).store('slideshow:oldStyles', slide.get('style'));
                this.storeData(slide);
                slide.setStyle('display', (this.current || index == this.options.initialSlideIndex) ? '' : 'none');
            }, this);
            return this;
        },

        storeData: function (element) {
            var ops = this.options;
            // default options
            element.store('slideshow-transition', ops.transition);
            element.store('slideshow-duration', ops.duration);
            if (element == this.element) element.store('slideshow-delay', ops.delay);
            // override from data attribute
            var data = element.get(this.options.dataAttribute);
            if (!data) return this;
            Slick.parse(data).expressions[0].each(function (option) {
                element.store('slideshow-' + option.tag, option.pseudos[0].key);
            });
            return this;
        },

        reset: function (slide) {
            return slide.set('style', slide.retrieve('slideshow:oldStyles'));
        },

        nextSlide: function () {
            return this.slides[this.index + 1] || this.slides[0];
        },

        previousSlide: function () {
            return this.slides[this.index - 1] || this.slides.getLast();
        },

        toElement: function () {
            return this.element;
        }

    });

    SlideShow.transitions = {};

    SlideShow.defineTransition = function (name, fn) {
        SlideShow.transitions[name] = fn;
    };

    SlideShow.defineTransitions = function (transitions) {
        Object.each(transitions, function (item, index) {
            SlideShow.defineTransition(index, item);
        });
    };

})();

// element extensions

Element.Properties.slideshow = {

    set: function (options) {
        this.get('slideshow').setup(options);
        return this;
    },

    get: function () {
        var instance = this.retrieve('slideshow');
        if (!instance) {
            instance = new SlideShow(this, {}, true);
            this.store('slideshow', instance);
        }
        return instance;
    }

};

Element.implement({

    playSlideShow: function (options) {
        this.get('slideshow').setup(options).play();
        return this;
    },

    pauseSlideShow: function () {
        this.get('slideshow').pause();
        return this;
    }

});

// 19 transitions :D
SlideShow.defineTransitions({

    none: function (data) {
        data.previous.setStyle('display', 'none');
        return this;
    },

    fade: function (data) {
        data.previous.set('tween', { duration: data.duration }).fade('out');
        return this;
    },

    crossFade: function (data) {
        data.previous.set('tween', { duration: data.duration }).fade('out');
        data.next.set('tween', { duration: data.duration }).fade('in');
        return this;
    },

    fadeThroughBackground: function (data) {
        var half = data.duration / 2;
        data.next.set('tween', { duration: half }).fade('hide');
        data.previous.set('tween', {
            duration: half,
            onComplete: function () { data.next.fade('in'); }
        }).fade('out');
        return this;
    }

});

(function () {

    function getStyles(direction) {
        return {
            property: (direction == 'left' || direction == 'right') ? 'left' : 'top',
            inverted: (direction == 'left' || direction == 'up') ? 1 : -1
        };
    }

    function go(type, styles, data) {
        var tweenOptions = { duration: data.duration, unit: '%' };
        if (type == 'blind') {
            data.next.setStyle('z-index', 2);
        }
        if (type != 'slide') {
            data.next
			    .set('tween', tweenOptions)
			    .setStyle(styles.property, 100 * styles.inverted + '%');
            data.next.tween(styles.property, 0);
        }
        if (type != 'blind') {
            data.previous
			    .set('tween', tweenOptions)
			    .tween(styles.property, -(100 * styles.inverted));
        }
    }

    ['left', 'right', 'up', 'down'].each(function (direction) {

        var capitalized = direction.capitalize(),
		    blindName = 'blind' + capitalized,
		    slideName = 'slide' + capitalized;

        [
			['push' + capitalized, (function () {
			    var styles = getStyles(direction);
			    return function (data) {
			        go('push', styles, data);
			    }
			} ())],

			[blindName, (function () {
			    var styles = getStyles(direction);
			    return function (data) {
			        go('blind', styles, data);
			    }
			} ())],

			[slideName, (function () {
			    var styles = getStyles(direction);
			    return function (data) {
			        go('slide', styles, data);
			    }
			} ())],

			[blindName + 'Fade', function (data) {
			    this.fade(data)[blindName](data);
			    return this;
			} ]
		].each(function (transition) {
		    SlideShow.defineTransition(transition[0], transition[1]);
		});
    });

})();
