﻿
//=======================================================================
//sprite engine - nick fallon 
// 30/12/09 - added z-coordinate for true 3d Rotation
//=======================================================================
//features: 
//- layering
//- alpha-transparency (png)
//- simple movement (optional)
//- isometric positioning and ordering (optional)
//- 3D positioning and rotation (optional)
//- zoom - default is 1. try adding 0.1 for zoom-in..

//name - must be a unique name
//xpos - xcoord (in pixels) of the sprite, (0,0) is top-left.
//ypos - ycoord (in pixels) of the sprite, (0,0) is top-left.
//zpos - Only used for 3D coords
//width - width in pixels
//height - height in pixels
//imagepath - local path to the sprite image
//xspd - animation movement speed (xcoord)
//yspd - animation movement speed (ycoord)
//zindex - layer number(overridden if isometric positioning is used for this sprite)
//-- ISO fields - optional use -- 
//xiso - isometric positioning and ordering xcoord. if xiso > 0, it's used.
//yiso - isometric positioning and ordering ycoord. if xiso > 0, it's used.
//isoheight - height of object above ground level
//-- end ISO fields -- 
//enabled - the sprite is only rendered if it is enabled. (1=on; 0=off)
//repeatimage - if the width/height are larger than the image, (1)repeat it or (0)stretch it (1=repeat;0=stretch)
//zoom = 1 for actual size (zoom in by decimals eg. 1.1 for smooth zooming!)


//3D rotation angles
var angx = 0.0003;
var angy = 0.0024;
var angz = 0.001;
var s = Math.sin;
var c = Math.cos;
var originx = 0;
var originy = 200;

function Sprite(name, xpos, ypos, zpos, width, height, imagepath, xspd, yspd, zindex, xiso, yiso, isoheight, enabled, repeatimage, zoom) {
    this.name = name;
    this.xpos = xpos;
    this.ypos = ypos;
    this.zpos = zpos;
    this.width = width;
    this.height = height;
    this.imagepath = imagepath;
    this.xspd = xspd;
    this.yspd = yspd;
    this.zindex = zindex;
    this.xiso = xiso;
    this.yiso = yiso;
    this.isoheight = isoheight;
    this.enabled = enabled;
    this.repeatimage = repeatimage;
    this.zoom = zoom;

}



//method of class sprite for simple animations
function animate(spritenum) {


    with (this) {

        //3D rotation

        //rotate xy plane
        var xa = xpos * c(angx) - ypos * s(angx);
        var ya = xpos * s(angx) + ypos * c(angx);
        var za = zpos * 1.0;
        //rotate yz plane
        var xb = xa;
        var yb = ya * c(angy) - za * s(angy);
        var zb = ya * s(angy) + za * c(angy);
        //rotate zx plane
        var xc = xb * c(angz) + zb * s(angz);
        var yc = yb;
        var zc = -xb * s(angz) + zb * c(angz);
        //store the rotated coord
        xpos = xc;
        ypos = yc;
        zpos = zc;

        //adjust the zoom according to z-plane posn
        zoom = ((300 - zpos) / 400) + 0.5;


        //auto-glide (if required)
        xpos += xspd * zoom;
        ypos += yspd * zoom;
        /*
        if (ypos > (screen.width)) {
        ypos = 0 - width;
        }
        if (ypos < 0 - width) {
        ypos = (screen.width);
        }
        */
        //isometric positioning and z-ordering, if required
        if (xiso != 0) {
            //start at origin of isometric map        
            xpos = xorig;
            ypos = yorig;
            //iso height adjustment (0 means floor level)
            xpos -= isoheight;
            //set xpos and ypos
            xpos += (xiso * +(factor * zoom));
            ypos += (xiso * -((factor * zoom) * 2));
            xpos += (yiso * +(factor * zoom));
            ypos += (yiso * +((factor * zoom) * 2));
            //set zindex
            zindex = ((xpos + isoheight) * 1000) + ypos;
        }
    }

}

function clicksprite(name, xpos, ypos) {

    //find the clicked sprite
    //the input parms are the bare minimum info we need to identify the clicked sprite.

    var mysprite;

    for (x in sprites) {
        mysprite = sprites[x];

        //if it's a menu item (ie. it's name starts with 'catalog') then position the menu-select cursor over it
        if ((xpos == mysprite.xpos) && (ypos == mysprite.ypos)) {

            //store this spritename as selected_name
            selected_name = mysprite.name;

            //alert(mysprite.ypos);

            //alert(parseInt(xpos + originx));

        }

    }

}


//method of class sprite
function render() {
    //return a paragraph to be injected into the innerHTML of the canvas object

    with (this) {
        if (enabled == 1) {
            var sRender = ''
            if (repeatimage == 0) {
                //no repeat image (stretch image)
                sRender += '<img src=' + imagepath + ' ';
            }
            else {
                //repeat image
                sRender += '<p ';
            }
            sRender += 'onmousedown="clicksprite(\'' + this.name + '\',' + this.xpos + ',' + this.ypos + ');" ';  //call clicksprite when a sprite is clicked.
            //sRender += 'onmouseover="
            sRender += 'style=';
            sRender += 'z-index:' + zindex + ';';
            if (repeatimage == 0) {
                //no repeat image - stretch the image instead. (nothing required)
            }
            else {
                //repeat image
                sRender += 'background-image:url(' + imagepath + ');';
                sRender += 'background-repeat:repeat;';
            }
            sRender += 'width:' + (width * zoom) + 'px;';
            sRender += 'height:' + (height * zoom) + 'px;';
            sRender += 'position:absolute;';
            sRender += 'top:' + parseInt(xpos + originx) + 'px;';
            sRender += 'left:' + (ypos + originy) + 'px;';
            sRender += '';
            sRender += '';
            sRender += '';
            sRender += '>';

            return sRender;
        }
        else {
            return ''; //this sprite disabled (not rendered)
        }
    }
}

//this makes these methods into class methods (lower memory consumption)
Sprite.prototype.animate = animate;
Sprite.prototype.render = render;
