// no worries, code will be cleaned up later.. ;)


//
// global variables
//
var jg; // jsGraphics object
var mousePosX = 0;
var mousePosY = 0;
var currentPopIn = Array(0, 0, 0, 0);

function cloudInit() {
    // bind grpahics to div
    jg = new jsGraphics('circle');
    jg_content = new jsGraphics('canvas');
    drawCircle();
    setOpacity(getEl('circle'), circleOpacity);
	document.onclick = onClick;
	document.onmousemove = onMouseMove;
}

function onClick() {
    void(0);
}

function onMouseMove(event) {
    if (! collides(mousePosX, mousePosY, currentPopIn)) {
        hide('circle');
        hide('canvas');
    }
    updateMousePos(event);
}

function cloud(el, links) {
    el.timeOutID = setTimeout(function() {wheel(el, links)},
        circleOpenDelay);
}

function cloudCancel(el) {
    clearInterval(el.timeOutID);
}

function wheel(el, links) {
    var pos = getAbsPos(el);
    jg_content.clear();

    // clear interval if the is one
    if (el.timeOutID)
        clearInterval(el.timeOutID);

    // deactivate link
    el.blur();

    // draw big circle
    var linkSize = getSize(el);

    var circlePos = Array();
    var xCentre = pos['x'] + linkSize['x'] / 2;
    var yCentre = pos['y'] + linkSize['y'] / 2;

    // make sure circle is on page
    var pageSize = getPageSize();
    if ((xCentre - circleSize / 2) < 0)
        xCentre = 0 + circleSize / 2;
    if ((yCentre - circleSize / 2) < 0)
        yCentre = 0 + circleSize / 2;
    if ((xCentre + circleSize / 2) > pageSize['x'])
        xCentre = pageSize['x'] - circleSize / 2;
    if ((yCentre + circleSize / 2) > pageSize['y'])
        yCentre = pageSize['y'] - circleSize / 2;

    var xCircle = xCentre - circleSize / 2;
    var yCircle = yCentre - circleSize / 2;

    placeEl('circle', xCircle, yCircle);
    show('circle');

    currentPopIn = Array(xCircle, yCircle, xCircle + circleSize,
        yCircle + circleSize);

    // draw cloud content

    var xArrowStart = xCentre;
    var yArrowStart = yCentre - 10;
    var xArrowEnd = xCentre;
    var yArrowEnd = yCentre - circleSize / 2 + 30;

    var xLink = xCentre;
    var yLink = yCentre - circleSize / 2 + 30;

    var link_count = links.length;

    // loop through links
    for (i = 0; i < link_count; i++) {

        // draw arrows
        var angle = 360 / link_count * i;

        rot = rotate(xArrowStart, yArrowStart, xCentre, yCentre, angle);
        var xArrowStartRotated = Math.round(rot['x']);
        var yArrowStartRotated = Math.round(rot['y']);

        rot = rotate(xArrowEnd, yArrowEnd, xCentre, yCentre, angle);
        var xArrowEndRotated = Math.round(rot['x']);
        var yArrowEndRotated = Math.round(rot['y']);

        rot = rotate(xLink, yLink, xCentre, yCentre, angle);
        var xLinkRotated = rot['x'];
        var yLinkRotated = rot['y'];

        jg_content.setStroke(1);
        jg_content.setColor(circleLinesColour);
        jg_content.drawLine(xArrowStartRotated, yArrowStartRotated,
            xArrowEndRotated, yArrowEndRotated);

        // draw links
        jg_content.setFont("sans-serif","13px");
        jg_content.drawStringRect('<a href="' + links[i]['url'] + '">'
            + links[i]['title'] + "</a>", xLinkRotated - circleSize / 6,
            yLinkRotated - 5, circleSize / 3, "center");
    }

    jg_content.setColor(circleCentreColour);
    jg_content.fillEllipse(xCentre - 10, yCentre - 10, 20, 20);

    jg_content.paint();
    show('canvas');
}

function drawCircle() {
    jg.setColor(circleColour);
    jg.fillEllipse(0, 0, circleSize, circleSize);
    jg.paint();
}

//
// general use functions
//

function collides(x, y, area) {
	// v1.0
    if ((x >= area[0]) && (x <= area[2]) && (y >= area[1])
        && (y <= area[3])) return true;
}

function getEl(id) {
	// v1.0
	var el = document.getElementById
		? document.getElementById(id)
		: document.all[id];
	return el;
}

function getAbsPos(el) {
	// v1.0
    // http://www.quirksmode.org/js/findpos.html is your friend
	pos = new Array();
	if (el.offsetParent) {
		pos['x'] = el.offsetLeft
		pos['y'] = el.offsetTop
		while (el = el.offsetParent) {
			pos['x'] += el.offsetLeft
			pos['y'] += el.offsetTop
		}
	}
	return pos;
}

function getInnerWidth() {
    // v1.0
    // inspired by http://www.quirksmode.org/viewport/compatibility.html
    var inner = new Array();
    if (self.innerHeight) {
        inner['x'] = self.innerWidth;
        inner['y'] = self.innerHeight;
    }
    else if (document.documentElement
        && document.documentElement.clientHeight) {
        inner['x'] = document.documentElement.clientWidth;
        inner['y'] = document.documentElement.clientHeight;
    }
    else if (document.body) {
        inner['x'] = document.body.clientWidth;
        inner['y'] = document.body.clientHeight;
    }
    return inner;
}

function getPageSize() {
    // v1.1
    // requires:
    // - getInnerWidth()
    // inspired by http://www.quirksmode.org/viewport/compatibility.html
    var b = document.body;
    var inner = getInnerWidth();
    var size = new Array;
    if (b.scrollHeight > b.offsetHeight) {
        size['x'] = b.scrollWidth;
        size['y'] = b.scrollHeight;
    } else {
        size['x'] = b.offsetWidth;
        size['y'] = b.offsetHeight;
    }
    if (size['x'] < inner['x']) size['x'] = inner['x'];
    if (size['y'] < inner['y']) size['y'] = inner['y'];
    return size;
}

function getSize(el) {
	// v1.0
	size = new Array();
	size['x'] = el.offsetWidth
	size['y'] = el.offsetHeight
	return size;
}

function hide(id){
	// v1.0
	var el = getEl(id);
	el.style['visibility'] = 'hidden';
}

function mouseX(evt) {
	// v1.0
	if (!evt)
		evt = window.event;
	if (evt.pageX)
		return evt.pageX;
	else if (evt.clientX)
		return evt.clientX
			+ (document.documentElement.scrollLeft
			? document.documentElement.scrollLeft
			: document.body.scrollLeft);
	else
		return 0;
}

function mouseY(evt) {
	// v1.0
	if (!evt)
		evt = window.event;
	if (evt.pageY)
		return evt.pageY;
	else if (evt.clientY)
		return evt.clientY
			+ (document.documentElement.scrollTop
			? document.documentElement.scrollTop
			: document.body.scrollTop);
	else
		return 0;
}

function placeEl(id, x, y) {
	// v1.0
	var el = getEl(id);
	el.style['left'] = x + 'px';
	el.style['top'] = y + 'px';
}

function replaceElContent(id, markup) {
	// v1.0
	var el = getEl(id);
	if (el && typeof el.innerHTML != "undefined")
		el.innerHTML = markup;
}

function rotate(x, y, xCentre, yCentre, angle) {
    // v1.0
    var coordinates = new Array();
    angle = angle * Math.PI / 180;
    coordinates['x'] = xCentre + Math.cos(angle) * (x - xCentre)
        - Math.sin(angle) * (y - yCentre);
    coordinates['y'] = yCentre + Math.sin(angle) * (x - xCentre)
        + Math.cos(angle) * (y - yCentre);
    return coordinates;
}

function updateMousePos(evt) {
	// v1.0
	// mouse tracking code heavily inspired by stephen chapman's work
	mousePosX = parseInt(mouseX(evt));
	mousePosY = parseInt(mouseY(evt));
}

function setOpacity(element, alpha) {
    // taken from http://snipplr.com/view/707/setopacity/
    var style = element.style;
    if(style.MozOpacity != undefined) { //Moz and older
        style.MozOpacity = alpha;
    }
    else if(style.filter != undefined) { //IE
        style.filter = "alpha(opacity=0)";
        element.filters.alpha.opacity = (alpha * 100);
    }
    else if(style.opacity != undefined) { //Opera
        style.opacity = alpha;
    }
}

function show(id){
	// v1.0
	var el = getEl(id);
	el.style['visibility'] = 'visible';
}

