
var CARD_WIDTH = 310;
var CARD_HEIGHT = 200;
var SPACE_X = 20;
var SPACE_Y = 20;
var NUM_COLUMNS = 3;
var INFO_PADDING = 15;

document.version = "test4";
// document.is_debug_mode = true;
document.is_first_version = false;

function create_basic_table()
{
    var table = document.createElement("table");
    table.style.display = "block";
    table.style.borderSpacing = "0px";
    table.cellSpacing = "0px";
    table.cellPadding = "0px";
    table.border= "0px";
    var thead = document.createElement("thead");
    thead.style.height = "0px";
    var tfoot = document.createElement("tfoot");
    tfoot.style.height = "0px";
    var tbody = document.createElement("tbody");
    table.appendChild(thead);
    table.appendChild(tfoot);
    table.appendChild(tbody);

    table.add_row = function(){
        var row = document.createElement("tr");
        tbody.appendChild(row);
        return row;
    };
    table.add_cell = function(){
        var row = tbody.lastChild;
        var cell = document.createElement("td");
        row.appendChild(cell);
        return cell;
    };
    return table;
}

function create_spacer(w, h)
{
    var d = document.createElement("img");
    d.src = "empty.gif";
    d.style.width = w + "px";
    d.style.height = h + "px";
    return d;
};

function create_text_button(text, action)
{
    var div = document.createElement("div");

    div.style.padding = "3px 3px 3px 3px";
    div.style.display = "inline";
    div.style.backgroundColor = "black";
    div.style.color = "white";
    div.style.cursor = "pointer";
    div.innerHTML = text;

    div.onclick = action;
    return div;
}


function init(initial_action)
{
    var body = document.getElementById("body");

    var origin = document.getElementById("origin");
    origin.initial_action = initial_action;

    // if(document.is_debug_mode)
        // origin.is_logged_in = true;

    // Make the scrollable part.
    {
        var scrollable = document.createElement("div");
        origin.scrollable = scrollable;
        scrollable.style.position = "absolute";
        scrollable.style.top = "0px";
        scrollable.style.bottom = "0px";
        scrollable.style.left = "0px";
        scrollable.style.right = "0px";
        scrollable.style.width = "100%";
        scrollable.style.height = "100%";
        scrollable.style.overflow = "auto";
        origin.appendChild(scrollable);
    }

    // Make a centered div.
    var centered = document.createElement("div");
    {
        centered.style.width = "970px";
        centered.style.position = "absolute";

        centered.style.top = "0px";
        origin.scrollable.appendChild(centered);

        origin.centered = centered;
    }

    // Make the subpage.
    {
        var subpage = document.createElement("div");
        origin.subpage = subpage;
        subpage.style.position = "absolute";
        subpage.style.top = "0px";
        subpage.style.left = "0px";
        centered.appendChild(subpage);
    }

    // Show the logo.
    {
        var logo = document.createElement("img");
        logo.src = "LOGO/logo.png";
        logo.style.position = "absolute";
        logo.style.top = "32px";
        logo.style.left = "140px";
        logo.style.width = "956px";
        logo.style.height = "110px";
        centered.appendChild(logo);
    }

    init_request_system();

    function perform_initial_action()
    {
        if(initial_action == "login")
        {
            show_login_box();
        }
    }

    redisplay(perform_initial_action);
}

function redisplay(continuation)
{
    var origin = document.getElementById("origin");

    function step1()
    {
        // Make the menu.
        request_and_show_menu(step2);
    }

    function step2()
    {
        // Load the initial sub-page.
        request_and_show_initial_subpage(step3);
    }

    function step3()
    {
        function resize()
        {
            var w = window.innerWidth;
            if(w === undefined)
                w = document.body.offsetWidth;

            var x = (w - 1100)/2;
            if(x < 0) x = 0;

            origin.centered.style.left = x+"px";

            if(origin.menu)
                origin.menu.style.left = x+36+"px";
        }

        resize();
        window.onresize = resize;

        if(continuation)
            continuation();
    }

    step1();
}

function is_visible_based_on_tags(tag_ids)
{
    var origin = document.getElementById("origin");

    if(origin.is_logged_in)
        return true;

    if(tag_ids == undefined)
        return false;

    for(var menu_index in origin.menu.data)
    {
        var menu = origin.menu.data[menu_index];

        for(var submenu_index in menu.submenus)
        {
            var submenu = menu.submenus[submenu_index];

            if(submenu.is_active)
            {
                if(tag_ids[submenu.id])
                    return true;
            }
        }
    }

    return false;
}

function request_and_show_initial_subpage(continuation)
{
    var origin = document.getElementById("origin");

    function g(m)
    {
        origin.page_data = m.data;
        format_page(m.data);

        if(continuation)
            continuation();
    }
    var slot_id = document.broker.register_slot(g);

    var message = new Message("server", slot_id, {"action":"get_initial_page"});
    send_request(message);
}

function format_page(page_data)
{
    var origin = document.getElementById("origin");
    var subpage = origin.subpage;

    // alert(JSON.stringify(page_data));

    clear_page();

    var occupied = new Object();
    var lowest_real_y = new Object();

    var next_x = 0;
    var next_y = 0;
    var real_y = 0;

    function get_lowest_real_y_in_row(y)
    {
        var r = 0;

        for(var i = 0; i < NUM_COLUMNS; ++i)
        {
            var lry = lowest_real_y[[i, y]];
            if(lry === undefined) continue;
            if(lry > r) r = lry;
        }

        return r;
    }

    function advance()
    {
        for(;;)
        {
            if(!occupied[[next_x, next_y]])
                break;

            next_x++;
            if(next_x >= NUM_COLUMNS)
            {
                next_x = 0;
                real_y = get_lowest_real_y_in_row(next_y);
                next_y++;
            }
        }
    }

    function is_free(x, y, sx, sy)
    {
        if(x > 0 && x + sx > NUM_COLUMNS)
            return false;

        var occ = false;
        for(var i = x; i < x+sx; ++i)
        {
            for(var j = y; j < y+sy; ++j)
            {
                if(occupied[[i,j]])
                    return false;
            }
        }

        return true;
    }

    function find_space(sx, sy)
    {
        var x = next_x;
        var y = next_y;
        var ry = real_y;

        for(;;)
        {
            if(is_free(x, y, sx, sy))
                return [x,y,ry];

            x++;
            if(x >= NUM_COLUMNS)
            {
                x = 0;
                ry = get_lowest_real_y_in_row(y);
                y++;
            }

            if(y >= 1000)
            {
                alert("The image formatting algorithm failed. Perhaps one of the images has an invalid shape (too small or too large)?");
                break;
            }
        }
    }

    for(var m_index in page_data)
    {
        var m = page_data[m_index];

        if(!is_visible_based_on_tags(m.tag_ids))
            continue;

        if(!origin.is_logged_in && m.is_hidden)
            continue;

        if(m.is_expanded)
        {
            var w = m.image_width;
            var h = m.image_height + m.info_height + INFO_PADDING;
            var sx = ((w + SPACE_X + CARD_WIDTH - 1)/(SPACE_X + CARD_WIDTH))|0;
            var sy = ((h + SPACE_Y + CARD_HEIGHT - 1)/(SPACE_Y + CARD_HEIGHT))|0;
            var pos = find_space(sx, sy);
            var x = pos[0];
            var y = pos[1];
            var ry = pos[2];

            for(var i = 0; i < sx; ++i)
            {
                for(var j = 0; j < sy; ++j)
                {
                    occupied[[x+i,y+j]] = true;

                    if(j+1==sy)
                        lowest_real_y[[x+i,y+j]] = ry+h+SPACE_Y;
                    else
                        lowest_real_y[[x+i,y+j]] = ry+CARD_HEIGHT+SPACE_Y;
                }
            }

            place_poster3(m, x, ry);
        }
        else
        {
            advance();
            var x = next_x;
            var y = next_y;
            var ry = real_y;
            occupied[[x,y]] = true;
            lowest_real_y[[x,y]] = real_y+CARD_HEIGHT+SPACE_Y;
            var card = place_card3(m, x, ry);

            (function(m){
                card.on_click_event = function()
                {
                    for(var m2_index in page_data)
                    {
                        var m2 = page_data[m2_index];
                        m2.is_expanded = false;
                    }

                    m.is_expanded = true;
                    format_page(page_data);
                }
            })(m);
        }

    }

    var pos = find_space(3, 1);
    var x = pos[0];
    var y = pos[1];
    var ry = pos[2];

    var s = create_spacer(1, 1);
    s.style.position = "absolute";
    s.style.top = 190+ry+20+"px";
    s.style.left = "0";
    subpage.appendChild(s);
}

document.preloaded = new Array();
function preload(src)
{
    var img = new Image();
    img.src = src;
    document.preloaded.push(img);
}

function disable_select(el)
{
    // This function turns off text-selection of an object.
    el.onmousedown = function(e) { return false; };
    el.onselectstart = function(e) { return false; };
}

function show_credits()
{
    var origin = document.getElementById("origin");

    if(origin.popup)
        origin.removeChild(origin.popup);

    var box = document.createElement("div");
    fade_in(box);
    origin.popup = box;
    box.style.position = "absolute";
    box.style.top = "300px";
    box.style.left = "300px";
    box.style.backgroundColor = "#4d4d4d";
    box.style.backgroundImage = "url('images/credits_leeg.png')";
    box.style.width = "281px";
    box.style.height = "181px";
    origin.appendChild(box);
    move_to_middle(box, 281, 181);

    var cross = make_cross();
    cross.style.position = "absolute";
    cross.style.right = "5px";
    cross.style.top = "5px";
    box.appendChild(cross);

    cross.on_click_event = function(e)
    {
        if(origin.popup)
            origin.removeChild(origin.popup);
        origin.popup = null;
    }

    var div = document.createElement("div");
    div.style.width = "241px";
    div.style.color = "white";
    div.style.textAlign = "center";
    var s = "WEBSITE DESIGN: <a class='credit_link' href='http://www.thisisplanetearth.net'>PLANET~EARTH</a><br/>";
    s += "<br/>";
    s += "ENGINEERING: <a class='credit_link' href='http://www.interactome.nl'>JAN DE SONNEVILLE</a> &amp;<br/>";
    s += "<a class='credit_link' href='http://www.libtag.com'>KEES-JAN VAN DER KOLK</a><br/>";
    s += "<br/>";
    s += "&copy; 2009 KARAKTER CONCEPTS AND<br/>";
    s += "DESIGNS FOR VIRTUAL WORLDS<br/>";
    div.innerHTML = s;
    place(div, 20, 70, box);
}

function show_login_box()
{
    var origin = document.getElementById("origin");

    if(origin.popup)
        origin.removeChild(origin.popup);

    var box = document.createElement("div");
    fade_in(box);
    origin.popup = box;
    box.style.position = "absolute";
    box.style.top = "300px";
    box.style.left = "300px";
    box.style.backgroundColor = "#4d4d4d";
    box.style.backgroundImage = "url('images/login_formulier_leeg.png')";
    box.style.width = "281px";
    box.style.height = "181px";
    origin.appendChild(box);
    move_to_middle(box, 281, 181);

    var cross = make_cross();
    cross.style.position = "absolute";
    cross.style.right = "5px";
    cross.style.top = "5px";
    box.appendChild(cross);

    cross.on_click_event = function(e)
    {
        if(origin.popup)
            origin.removeChild(origin.popup);
        origin.popup = null;
    }

    var name_input = document.createElement("input");
    name_input.type = "text";
    name_input.style.display = "block";
    name_input.style.color = "black";
    name_input.style.position = "absolute";
    name_input.style.top = "50px";
    name_input.style.left = "80px";
    box.appendChild(name_input);

    var input = document.createElement("input");
    input.type = "password";
    input.style.display = "block";
    input.style.color = "black";
    input.style.position = "absolute";
    input.style.top = "80px";
    input.style.left = "80px";
    box.appendChild(input);

    var text = document.createElement("div");
    text.style.color = "white";
    text.style.display = "block";
    text.style.position = "absolute";
    text.style.top = "110px";
    text.style.left = "80px";
    box.appendChild(text);

    if(document.is_debug_mode)
    {
        input.value = "nootmies";
        name_input.value = "aap";
    }

    name_input.onkeydown = function(e)
    {
        if(e.keyCode == 13)
        {
            input.focus();
        }
    }

    function execute()
    {
        var m = {};
        m.action = "login";
        m.name = name_input.value;
        m.password = input.value;

        function g(m)
        {
            if(m.data.error)
            {
                text.innerHTML = "login failed: "+m.data.error;
                name_input.focus();
                return;
            }

            if(origin.popup)
                origin.removeChild(origin.popup);
            origin.popup = null;
            origin.is_logged_in = true;
            redisplay();
        }

        var slot_id = document.broker.register_slot(g);
        var message = new Message("server", slot_id, m);
        send_request(message);
    }

    input.onkeydown = function(e)
    {
        if(e.keyCode == 13)
        {
            execute();
        }
    }

    var b = make_button("images/ok-normal.png", "images/ok-roll.png", execute);
    place(b, 168, 140, box);

    name_input.focus();
}

function clear_page()
{
    var origin = document.getElementById("origin");
    var subpage = origin.subpage;

    while(subpage.childNodes.length > 0)
        subpage.removeChild(subpage.childNodes[0]);
}

function place_poster3(m, x, ry)
{
    var origin = document.getElementById("origin");
    var subpage = origin.subpage;

    var poster = make_poster3(m);
    poster.style.position = "absolute";
    poster.style.left = 130+(CARD_WIDTH+SPACE_X)*x+"px";
    poster.style.top = 190+ry+"px";
    subpage.appendChild(poster);

    return poster;
}

function place_card3(m, x, ry)
{
    var origin = document.getElementById("origin");
    var subpage = origin.subpage;

    var card = make_card3(m);
    card.style.position = "absolute";
    card.style.left = 130+x*(SPACE_X+CARD_WIDTH)+"px";
    card.style.top = 190+ry+"px";
    subpage.appendChild(card);

    return card;
}

function get_window_size()
{
    var w = window.innerWidth;
    if(w === undefined)
        w = document.body.offsetWidth;

    var h = window.innerHeight;
    if(h === undefined)
        h = document.body.offsetHeight;

    return [w,h];
}

function move_to_middle(node, width, height)
{
    [W,H] = get_window_size();

    node.style.position = "absolute";
    node.style.top = (H-height)/2 + "px";
    node.style.left = (W-width)/2 + "px";
}

function show_filter_box()
{
    var origin = document.getElementById("origin");

    function complete(categories)
    {
        if(origin.popup)
            origin.removeChild(origin.popup);

        var box = document.createElement("div");
        fade_in(box);
        origin.popup = box;
        box.style.position = "absolute";
        box.style.backgroundColor = "#4d4d4d";
        box.style.backgroundImage = "url('images/filter_formulier_leeg.png')";
        box.style.width = "381px";
        box.style.height = "447px";
        box.style.color = "white";
        move_to_middle(box, 381, 447);

        var cross = make_cross();
        cross.style.position = "absolute";
        cross.style.right = "5px";
        cross.style.top = "5px";
        box.appendChild(cross);

        cross.on_click_event = function(e)
        {
            if(origin.popup)
                origin.removeChild(origin.popup);
            origin.popup = null;
        };

        (function()
        {
            var category_input = document.createElement("select");
            category_input.style.color = "black";
            category_input.name = "category";
            for(var category_index in categories)
            {
                var category = categories[category_index];
                var option = document.createElement("option");
                option.value = ""+category.id;
                option.innerHTML = category.title;
                category_input.appendChild(option);
            }
            place(category_input, 70, 40, box);

            var tag_input = document.createElement("input");
            tag_input.style.color = "black";
            tag_input.name = "tag";
            tag_input.type = "text";
            place(tag_input, 70, 72, box);

            var tag_image_input = document.createElement("input");
            tag_image_input.style.color = "black";
            tag_image_input.name = "tag_image";
            tag_image_input.type = "file";
            tag_image_input.style.width = "50px";
            place(tag_image_input, 70, 104, box);

            function submit()
            {
                var m = {};
                m.action = "add_filter";
                m.name = tag_input.value;
                m.category = category_input.value;

                function g(m)
                {
                    if(m.data.error)
                    {
                        alert(m.data.error);
                        return;
                    }
                    redisplay();
                }
                var slot_id = document.broker.register_slot(g);

                var message = new Message("server", slot_id, m);
                message.add_element(tag_image_input);

                origin.removeChild(box);
                origin.popup = undefined;

                send_request(message);
            }

            var button = make_button("images/addfilter.png", "images/addfilter_rollover.png", submit);
            place(button, 280, 144, box);
        })();

        function create_filter_input()
        {
            var filter_input = document.createElement("select");
            filter_input.style.color = "black";
            filter_input.name = "filter";
            for(var category_index in categories)
            {
                var category = categories[category_index];

                for(var tag_index in category.submenus)
                {
                    var tag = category.submenus[tag_index];
                    var option = document.createElement("option");
                    option.value = ""+tag.id;
                    option.innerHTML = category.title + " - " + tag.title;
                    filter_input.appendChild(option);
                }

            }
            return filter_input;
        }

        (function()
        {
            var filter_input = create_filter_input();
            place(filter_input, 70, 215, box);

            function submit()
            {
                var m = {};
                m.action = "delete_filter";
                m.id = filter_input.value;

                function g(m)
                {
                    if(m.data.error)
                    {
                        alert(m.data.error);
                        return;
                    }

                    redisplay();
                }
                var slot_id = document.broker.register_slot(g);

                var message = new Message("server", slot_id, m);

                origin.removeChild(box);
                origin.popup = undefined;

                send_request(message);
            }

            var button = make_button("images/deletefilter.png", "images/deletefilter_rollover.png", submit);
            place(button, 280, 250, box);

        })();

        (function()
        {
            var filter_input = create_filter_input();
            place(filter_input, 70, 345, box);

            var tag_image_input = document.createElement("input");
            tag_image_input.style.color = "black";
            tag_image_input.name = "tag_image";
            tag_image_input.type = "file";
            place(tag_image_input, 70, 377, box);

            function submit()
            {
                var m = {};
                m.action = "edit_filter";
                m.id = filter_input.value;

                function g(m)
                {
                    if(m.data.error)
                    {
                        alert(m.data.error);
                        return;
                    }
                    redisplay();
                }
                var slot_id = document.broker.register_slot(g);

                var message = new Message("server", slot_id, m);
                message.add_element(tag_image_input);

                origin.removeChild(box);
                origin.popup = undefined;

                send_request(message);
            }

            var button = make_button("images/editfilter.png", "images/editfilter_rollover.png", submit);
            place(button, 280, 417, box);
        })();

        origin.appendChild(box);
    }

    function g(m)
    {
        complete(m.data);
    }

    var slot_id = document.broker.register_slot(g);
    var message = new Message("server", slot_id, {"action":"get_menu"});
    send_request(message);
}

function make_button(normal, roll, action)
{
    var button = document.createElement("img");
    button.src = normal;
    button.onclick = action;
    button.style.cursor = "pointer";

    button.onmouseover = function(e)
    {
        button.src = roll;
        button.style.cursor = "pointer";
    };
    button.onmouseout = function(e)
    {
        button.src = normal;
    };

    return button;
}

function place(node, x, y, parent)
{
    node.style.position = "absolute";
    node.style.left = x+"px";
    node.style.top = y+"px";

    if(parent)
        parent.appendChild(node);
}

function show_edit_box(card)
{
    if(card === null) // Value null means: make a new project.
    {
        card = {};
        card.data = {};
        card.data.name = "My project";
        card.data.text = "A short description of the project.";
        card.data.tag_ids = {};
        card.data.id = -1; // Value -1 means: make a new project.
    }

    var origin = document.getElementById("origin");

    function complete(categories)
    {
        if(origin.popup)
            origin.removeChild(origin.popup);

        var box = document.createElement("div");
        fade_in(box);
        origin.popup = box;
        box.style.position = "absolute";
        box.style.backgroundColor = "#4d4d4d";
        box.style.backgroundImage = "url('images/project_formulier_leeg.png')";
        box.style.width = "321px";
        box.style.height = "622px";
        move_to_middle(box, 321, 622);

        var cross = make_cross();
        cross.style.position = "absolute";
        cross.style.right = "5px";
        cross.style.top = "5px";
        box.appendChild(cross);

        cross.on_click_event = function(e)
        {
            if(origin.popup)
                origin.removeChild(origin.popup);
            origin.popup = null;
        };

        var name_input = document.createElement("input");
        name_input.style.color = "black";
        name_input.name = "name";
        name_input.type = "text";
        name_input.value = card.data.name;
        place(name_input, 20, 70, box);

        var text_input = document.createElement("textarea");
        text_input.style.color = "black";
        text_input.innerHTML = card.data.text;
        text_input.style.width = "280px";
        text_input.style.height = "110px";
        place(text_input, 20, 110, box);

        var front_input = document.createElement("input");
        front_input.style.color = "black";
        front_input.name = "front";
        front_input.type = "file";
        place(front_input, 20, 250, box);

        var back_input = document.createElement("input");
        back_input.style.color = "black";
        back_input.name = "back";
        back_input.type = "file";
        place(back_input, 20, 288, box);

        var large_input = document.createElement("input");
        large_input.style.color = "black";
        large_input.name = "large";
        large_input.type = "file";
        place(large_input, 20, 328, box);

        var title_input = document.createElement("input");
        title_input.style.color = "black";
        title_input.name = "title";
        title_input.type = "file";
        place(title_input, 20, 368, box);

        var input = document.createElement("select");
        input.multiple = "multiple";
        input.style.color = "black";
        input.name = "tags";
        input.style.width = "280px";
        input.style.height = "120px";
        place(input, 20, 450, box);

        for(var category_index in categories)
        {
            var category = categories[category_index];

            for(var tag_index in category.submenus)
            {
                var tag = category.submenus[tag_index];

                var option = document.createElement("option");
                option.value = tag.id.toString();
                option.innerHTML = category.title + " - " + tag.title;
                if(card.data.tag_ids[tag.id])
                    option.selected = true;
                input.appendChild(option);
                tag.option = option;
            }
        }

        function submit()
        {
            var m = {};
            m.action = "edit_project";
            m.id = card.data.id;
            m.name = name_input.value;
            m.text = text_input.value;

            m.tag_ids = {};
            for(var category_index in categories)
            {
                var category = categories[category_index];

                for(var tag_index in category.submenus)
                {
                    var tag = category.submenus[tag_index];

                    if(tag.option.selected)
                    {
                        m.tag_ids[tag.id] = 1;
                    }
                }
            }

            // alert(JSON.stringify(m));

            function g(m)
            {
                if(m.data.error)
                {
                    alert(m.data.error);
                    return;
                }

                request_and_show_initial_subpage();
            }
            var slot_id = document.broker.register_slot(g);

            var message = new Message("server", slot_id, m);

            message.add_element(front_input);
            message.add_element(back_input);
            message.add_element(large_input);
            message.add_element(title_input);

            origin.removeChild(box);
            origin.popup = undefined;

            send_request(message);
        }

        var button = make_button("images/ok-normal.png", "images/ok-roll.png", submit);
        place(button, 210, 590, box);

        origin.appendChild(box);
    }

    function g(m)
    {
        complete(m.data);
    }

    var slot_id = document.broker.register_slot(g);
    var message = new Message("server", slot_id, {"action":"get_menu"});
    send_request(message);
}

function make_card3(m)
{
    var origin = document.getElementById("origin");

    var card = document.createElement("div");
    card.data = m;
    card.style.width = "330px";
    card.style.height = "220px";
    card.style.position = "absolute";

    var image0 = document.createElement("img");
    image0.src = m.card_url;

    var has_back = false;
    var image1 = document.createElement("img");
    if(!(m.back_url == "" || m.back_url == null))
    {
        image1.src = m.back_url;
        has_back = true;
    }

    var box = make_flip_box(image0, image1, 310, 200, "#c0bbb8");
    box.style.top = "10px";
    box.style.left = "10px";
    box.style.position = "absolute";
    card.appendChild(box);

    box.on_click_event = function(e)
    {
        if(card.on_click_event)
            card.on_click_event(e);
    };

    if(has_back)
    {
        var corner_normal = document.createElement("img");
        corner_normal.src = "KAART HOEKJES/hoekje_nonactief.png";
        corner_normal.style.position = "absolute";
        corner_normal.style.width = "30px";
        corner_normal.style.height = "30px";
        corner_normal.style.top = "10px";
        corner_normal.style.right = "10px";
        card.appendChild(corner_normal);

        var corner_roll = document.createElement("img");
        corner_roll.src = "KAART HOEKJES/hoekje_actief.png";
        corner_roll.style.position = "absolute";
        corner_roll.style.width = "30px";
        corner_roll.style.height = "30px";
        corner_roll.style.top = "10px";
        corner_roll.style.right = "10px";
        corner_roll.style.visibility = "hidden";
        card.appendChild(corner_roll);

        var corner_sensor = document.createElement("div");
        corner_sensor.style.position = "absolute";
        corner_sensor.style.width = "30px";
        corner_sensor.style.height = "30px";
        corner_sensor.style.top = "10px";
        corner_sensor.style.right = "10px";
        disable_select(corner_sensor);
        card.appendChild(corner_sensor);

        var corner_sensor_image = document.createElement("img");
        corner_sensor_image.src = "empty.gif";
        corner_sensor_image.style.position = "absolute";
        corner_sensor_image.style.width = "30px";
        corner_sensor_image.style.height = "30px";
        corner_sensor_image.style.top = "0px";
        corner_sensor_image.style.left = "0px";
        corner_sensor_image.onmouseover = function(e)
        {
            corner_roll.style.visibility = "visible";
            corner_normal.style.visibility = "hidden";
        };
        corner_sensor_image.onmouseout = function(e)
        {
            corner_roll.style.visibility = "hidden";
            corner_normal.style.visibility = "visible";
        };
        corner_sensor_image.onclick = function(e)
        {
            card.flip_side();
        };
        corner_sensor.appendChild(corner_sensor_image);

        card.visible_side = 0;

        card.flip_side = function()
        {
            box.flip(250);
        }
    }

    disable_select(card);

    if(origin.is_logged_in)
    {
        var edit_button = document.createElement("img");
        edit_button.src = "images/edit.png";
        edit_button.style.position = "absolute";
        edit_button.style.top = "20px";
        edit_button.style.left = "20px";
        card.appendChild(edit_button);
        edit_button.onclick = function(e)
        {
            show_edit_box(card);
        };

        if(card.data.is_hidden)
        {
            var show_button = document.createElement("img");
            show_button.src = "images/show.png";
            show_button.style.position = "absolute";
            show_button.style.top = "50px";
            show_button.style.left = "20px";
            card.appendChild(show_button);
            show_button.onclick = function(e)
            {
                function g(m)
                {
                    request_and_show_initial_subpage();
                }

                var slot_id = document.broker.register_slot(g);
                var message = new Message("server", slot_id, {"action":"show", "id":card.data.id});
                send_request(message);
            };
        }
        else
        {
            var hide_button = document.createElement("img");
            hide_button.src = "images/hide.png";
            hide_button.style.position = "absolute";
            hide_button.style.top = "50px";
            hide_button.style.left = "20px";
            card.appendChild(hide_button);
            hide_button.onclick = function(e)
            {
                function g(m)
                {
                    request_and_show_initial_subpage();
                }

                var slot_id = document.broker.register_slot(g);
                var message = new Message("server", slot_id, {"action":"hide", "id":card.data.id});
                send_request(message);
            };
        }

        var delete_button = document.createElement("img");
        delete_button.src = "images/delete.png";
        delete_button.style.position = "absolute";
        delete_button.style.top = "80px";
        delete_button.style.left = "20px";
        card.appendChild(delete_button);
        delete_button.onclick = function(e)
        {
            function g(m)
            {
                request_and_show_initial_subpage();
            }

            var slot_id = document.broker.register_slot(g);
            var message = new Message("server", slot_id, {"action":"delete", "id":card.data.id});
            send_request(message);
        };

        var left_button = document.createElement("img");
        left_button.src = "images/shift_left.png";
        left_button.style.position = "absolute";
        left_button.style.top = "170px";
        left_button.style.left = "20px";
        card.appendChild(left_button);
        left_button.onclick = function(e)
        {
            function g(m)
            {
                request_and_show_initial_subpage();
            }

            var slot_id = document.broker.register_slot(g);
            var message = new Message("server", slot_id, {"action":"shift_left", "id":card.data.id});
            send_request(message);
        };

        var right_button = document.createElement("img");
        right_button.src = "images/shift_right.png";
        right_button.style.position = "absolute";
        right_button.style.top = "170px";
        right_button.style.right = "20px";
        card.appendChild(right_button);
        right_button.onclick = function(e)
        {
            function g(m)
            {
                request_and_show_initial_subpage();
            }

            var slot_id = document.broker.register_slot(g);
            var message = new Message("server", slot_id, {"action":"shift_right", "id":card.data.id});
            send_request(message);
        };
    }

    return card;
}

function make_poster3(m)
{
    var origin = document.getElementById("origin");

    var poster = document.createElement("div");
    w = m.image_width;
    h = m.image_height;
    poster.style.width = (w+20)+"px";
    poster.style.height = (h+20)+"px";
    poster.style.position = "absolute";

    var image = document.createElement("img");
    image.src = m.image_url;
    image.style.position = "absolute";
    image.style.width = w + "px";
    image.style.height = h + "px";
    image.style.top = "10px";
    image.style.left = "10px";
    image.onclick = function(e)
    {
        m.is_expanded = false;
        format_page(origin.page_data);
    };
    poster.appendChild(image);

    var info = document.createElement("img");
    info.src = m.info_url;
    info.style.position = "absolute";
    info.style.width = m.info_width + "px";
    info.style.height = m.info_height + "px";
    info.style.top = h+10+INFO_PADDING+"px";
    info.style.left = "10px";
    poster.appendChild(info);

    if(0)
    {
        var hires = document.createElement("img");
        hires.src = "images/HiRes-knop.png";
        hires.style.position = "absolute";
        hires.style.width = "50px";
        hires.style.height = "21px";
        hires.style.top = h+10+"px";
        hires.style.right = "10px";
        poster.appendChild(hires);
    }

    disable_select(poster);
    disable_select(info);

    // fade_in(image); // Removed upon request. The fading causes an annoying flickering, apparently.

    return poster;
}

function show_menu_and_enable_all(menu_data)
{
    var origin = document.getElementById("origin");

    if(origin.menu)
        origin.removeChild(origin.menu);

    var self = document.createElement("div");
    self.data = menu_data;

    self.style.position = "absolute";
    self.style.top = "200px";
    self.style.left = "36px";
    self.style.lineHeight = "10px";
    origin.appendChild(self);
    origin.menu = self;

    {
        var s = document.createElement("div");
        s.style.display = "block";
        self.appendChild(s);

        var cb = document.createElement("img");
        show_all_checkbox = cb;
        cb.style.display = "inline";
        s.appendChild(cb);

        var img = document.createElement("img");
        show_all_image = img;
        img.src = "images/showall.png";
        img.style.display = "inline";
        img.style.marginLeft = "5px";
        s.appendChild(img);

        show_all_is_active = true;

        show_all_show_state = function()
        {
            if(show_all_is_active)
                show_all_checkbox.src = "menu/checkbox/checkbox_actief.png";
            else
                show_all_checkbox.src = "menu/checkbox/checkbox_nonactief.png";
        };

        show_all_show_state();

        function click(e)
        {
            show_all_is_active = !show_all_is_active;
            show_all_show_state();

            for(var menu_index in menu_data)
            {
                var menu = menu_data[menu_index];

                for(var submenu_index in menu.submenus)
                {
                    var submenu = menu.submenus[submenu_index];

                    submenu.is_active = show_all_is_active;
                    submenu.show_state();
                    format_page(origin.page_data);
                }
            }

            if(!e) e = window.event;
            if(e.stopPropagation) e.stopPropagation();
            e.cancelBubble = true;
            return false;
        }

        s.onclick = click;
        show_all_image.onclick = click;
        show_all_checkbox.onclick = click;

        s.style.cursor = "pointer";
        show_all_image.style.cursor = "pointer";
        show_all_checkbox.style.cursor = "pointer";
    }

    {
        self.appendChild(create_spacer(1, 20));
    }

    for(var menu_index in menu_data)
    {
        var menu = menu_data[menu_index];

        var img = document.createElement("img");
        img.src = menu.image_url;
        img.style.display = "block";
        img.style.padding = "0px";
        img.style.paddingTop = "4px";
        self.appendChild(img);

        (function (menu){
            for(var submenu_index in menu.submenus)
            {
                var submenu = menu.submenus[submenu_index];

                submenu.is_active = true;

                var s = document.createElement("div");
                s.style.display = "block";
                s.style.paddingTop = "8px";
                s.style.lineHeight = "10px";
                self.appendChild(s);

                var cb = document.createElement("img");
                submenu.checkbox = cb;
                cb.style.display = "inline";
                cb.style.padding = "0px";
                cb.style.margin = "0px";
                s.appendChild(cb);

                var img = document.createElement("img");
                submenu.image = img;
                img.src = submenu.image_url;
                img.style.display = "inline";
                img.style.marginLeft = "5px";
                img.style.marginTop = "0px";
                img.style.marginBottom = "0px";
                img.style.marginRight = "0px";
                img.style.padding = "0px";
                s.appendChild(img);

                (function(submenu){
                    submenu.show_state = function()
                    {
                        if(submenu.is_active)
                            submenu.checkbox.src = "menu/checkbox/checkbox_actief.png";
                        else
                            submenu.checkbox.src = "menu/checkbox/checkbox_nonactief.png";
                    };

                    function click(e)
                    {
                        if(submenu.is_active)
                            submenu.is_active = false;
                        else
                            submenu.is_active = true;

                        submenu.show_state();

                        if(!submenu.is_active)
                        {
                            show_all_is_active = false;
                            show_all_show_state();
                        }

                        format_page(origin.page_data);

                        if(!e) e = window.event;
                        if(e.stopPropagation) e.stopPropagation();
                        e.cancelBubble = true;
                        return false;
                    }

                    s.onclick = click;
                    submenu.checkbox.onclick = click;
                    submenu.image.onclick = click;

                    s.style.cursor = "pointer";
                    submenu.checkbox.style.cursor = "pointer";
                    submenu.image.style.cursor = "pointer";

                })(submenu);

                submenu.show_state();
            }
        })(menu);

        self.appendChild(create_spacer(1, 42));
    }

    self.appendChild(create_spacer(1, 20));

    if(!origin.is_logged_in)
    {
        if(false) // As requested, we do not show a login button. However, the user can visit the login.html page to log in.
        {
            var b = make_button("images/login.png", "images/login_rollover.png", function(e){show_login_box();});
            b.style.display = "block";
            self.appendChild(b);
        }
    }
    else
    {
        function logout_action(e)
        {
            var m = {};
            m.action = "logout";

            function g(m)
            {
                origin.is_logged_in = false;
                if(origin.popup)
                    origin.removeChild(origin.popup);
                origin.popup = null;
                redisplay();
            }

            var slot_id = document.broker.register_slot(g);
            var message = new Message("server", slot_id, m);
            send_request(message);
        };

        var b = make_button("images/log_out.png", "images/log_out_rollover.png", logout_action);
        b.style.display = "block";
        self.appendChild(b);
    }

    {
        self.appendChild(create_spacer(1, 6));
//        var b = make_button("images/credits_normal.png", "images/credits_rollover.png", function(e){show_credits();});
//        b.style.display = "block";
//        self.appendChild(b);
    }

    if(origin.is_logged_in)
    {
        function do_add_card(e)
        {
            show_edit_box(null);
        }

        var b = make_button("images/addcard_small.png", "images/addcard_small_rollover.png", do_add_card);
        b.style.position = "absolute";
        b.style.left = "0px";
        b.style.top = "-50px";
        self.appendChild(b);
    }

    if(origin.is_logged_in)
    {
        var b = make_button("images/filtereditor.png", "images/filtereditor_rollover.png", show_filter_box);
        b.style.position = "absolute";
        b.style.left = "0px";
        b.style.top = "-80px";
        self.appendChild(b);
    }
}

function make_cross()
{
    function doit(e)
    {
        if(cross.on_click_event)
            cross.on_click_event(e);
    };

    var cross = make_button("images/kruisje_grijs.png", "images/kruisje_wit.png", doit);
    return cross;
}

function request_and_show_menu(done)
{
    function g(m)
    {
        var data = m["data"];
        show_menu_and_enable_all(data);

        if(done)
            done();
    }

    var slot_id = document.broker.register_slot(g);
    var message = new Message("server", slot_id, {"action":"get_menu"});
    send_request(message);
}
