var cacheAngles = [];

var basketImages = {
    "basket": ["/img/products/add-to-basket-off.gif", "/img/products/add-to-basket-on.gif"],
    "exchange": ["/img/products/exchange-for-this-off.gif", "/img/products/exchange-for-this-on.gif"]
}, basketState = "basket";

Request.tweetmeme = new Class({
    // return json data with extended information of a place / location.
    Extends: Request.JSONP,
    options: {
        url: "http://api.tweetmeme.com/url_info.jsonc?url={location}"
    },
    initialize: function(location, options) {
        this.parent(options);
        this.options.url = this.options.url.substitute({location: location});
    },
    success: function(data, script) {
        this.parent(data, script);
    }
});

Request.bitly = new Class({
    // return a crunched url via bit.ly
    Extends: Request.JSONP,
    options: {
        log: !true,
        bitly: {
            api: "R_e744c730bdde44a7eacc88cb892074e7",
            login: "webtogs2"
        },
        url: "http://api.bit.ly/v3/shorten?login={login}&apiKey={api}&longUrl={longUrl}&format=json"
    },
    initialize: function(loc, options) {
        this.parent(options);
        this.options.bitly.longUrl = loc;
        this.options.url = this.options.url.substitute(this.options.bitly);
    },
    success: function(data, script) {
        this.parent(data, script);
    }
});



var Product = new Class({
    Implements: [Options, Events],
    options: {
        liveStockCheck: true,
        liveStockEvery: 10, // seconds
        id: $empty(),
        selectedSize: "",
        selectedColour: $empty(),
        selectedVersion: $empty(),
        lead: "",
        estimate: "",
        sizes: [],
        colours: [],
        versions: [],
        leadsTable: [],
        leadsEstimates: [],
        captions: false,
        cacheAngles: [],
        cacheBoxAngles: []
    },
    initialize: function(options) {
        this.setOptions(options);
        this.startMonitor();
        this.outOfStock(); // 27/05/2009 15:27:02
    },
    set: function() {
        // internal setter for options that can take a json or a simple pair
        switch ($type(arguments[0])) {
            case "object":
                this.setOptions(arguments[0]);
            break;
            default:
                if (arguments.length == 2) {
                    var newo = {}
                        newo[arguments[0]] = arguments[1];

                    this.setOptions(newo);
                } else {
                    C.log("incorrect number of arguments");
                }
            break;
            case "false":
                return false;
            break;
        }
    },
    get: function(key) {
        // this.options getter, 1.2 stylee...
        return this.options[key];
    },
    getVersion: function(id) {
        // returns full container object
        return JSON.decode(this.options.versions[id]);
    },
    showSelectedColour: function() {
        // update colour name to screen, reset colour swatches.
        var c = this.get("selectedColour"), s = (this.get("selectedSize").length) ? ", " : "";
        $("newColour").set("text", c.trim() + s);
        $$("div.colours").each(function(el) {
            if (el.get("data-colour") != c && el.hasClass("colourIconOn"))
                el.removeClass("colourIconOn");
            else if (el.get("data-colour") == c && !el.hasClass("colourIconOn"))
                el.addClass("colourIconOn");
        });

        this.showSelectedSize();
        // fix for longer names
        var paneHeight = $("newColour").getParent().getCoordinates()['height'];

        if (paneHeight > 30) {
            c = c.substr(0, 25) + "...";
            $("newColour").set("text", c.trim() + s);
        }
    },
    showSelectedSize: function() {
        // update text and also change size boxes.
        var s = this.get("selectedSize"), c = this.get("selectedColour"), newSize = (s.length) ? "Size: <strong>" + s + "</strong>" : "";


        $("newSizeMsg").set("text", "Currently selected:");
        $("newSize").set("html", newSize); // ok to buy now

        $$("div.sizeIconOn").each(function(el) {
            var foo = el.getParent().getParent().getParent().getParent().getParent().getParent().getPrevious().get("data-colour");
            if (el.getText() != s || foo != c)
                el.removeClass("sizeIconOn").addClass("sizeIconOff");

        });

    },
    colourClick: function(el) {
        // clicked on a colour swatch
        var oldColour = this.get("selectedColour");
        this.set("selectedColour", el.get("data-colour"));

        // fix background
        $$("div.colour_grid").removeClass("colour_gridOn");
        el.getNext().addClass("colour_gridOn");

        $("orderNow").setStyle("background", "transparent");
        // workaround selecting size with colour swap
        if (this.get("selectedSize") != "" && this.get("selectedSize") != "One Size") {
            if (this.checkStock(this.get("selectedSize")).allow == false) {
                this.set({
                    selectedSize: "",
                    selectedVersion: $empty()
                });

                this.saveStockStatus("", "");
                this.restoreStockStatus();
                this.showSelectedSize();
                $("add2basket").set("src", basketImages[basketState][0]);
            }
        }

        if (this.get("selectedSize") == "One Size") {
            // do we have the stock?
            var requestedVersion = el.get("data-id"), version = this.getVersion(requestedVersion), _this = this;
            if ((version.stock <= 0 && version.nc >= 0 ) || version.disabled == 'true') {
                el.fade(1,.5);
                // myEventBubble(el, "Sorry, colour<br /> is out of stock.");
                this.set({
                    selectedVersion: version.cid
                });

                $("add2basket").set("src", basketImages[basketState][1]);


                this.showSelectedSize();
                this.showSelectedColour();

            } else {
                this.set({
                    "selectedVersion": version.cid
                });
            }



        }

        if (this.get("selectedSize") != "")
            this.showStockStatus(this.get("selectedVersion").toInt());

        this.showSelectedColour();
        $("productImage").set("src", "/pimages/" + this.options.id + "/" + el.get("data-id") + "/product_full.jpg").set("data-zoomer", false).eliminate("data-zoomer").removeEvents("mousemove").removeEvents("mouseleave");

        // update medium view targets
        var newTarget = '/pimages/' + this.get("id") + "/" + el.get("data-id") + "/product_main.jpg";
        $("PL").set("href", newTarget);
        // $("PL2").set("href", newTarget);

        // get angled shots.
        this.getAngles();
        this.buildSizes();
    },
    colourSetEvents: function() {
        var _this = this;
        // define click and mouseover on colour swatches
        $$(".colours").addEvents({
            dblclick: function(e) {
                new Event(e).stop();
                return false;
            },
            click: function() {
                if (this.allowClick === false)
                    return false;

                this.allowClick = false;

                _this.colourClick(this);

                // mz.loadImage($("productImage"));

                (function() {
                    this.allowClick = true;
                }).delay(500, this);
            },
            mouseenter: function() {
                this.addClass("colourIconOn");
            },
            mouseleave: function() {
                if (_this.get("selectedColour") != this.get("data-colour"))
                    this.removeClass("colourIconOn");
            }
        });

        $$("div.colour_grid").addEvents({
            mouseenter: function() {
                if (!this.hasClass("colour_gridOn"))
                    this.addClass("colour_gridOn");
            },
            mouseleave: function() {
                if (_this.get("selectedColour") != this.getPrevious().get("data-colour"))
                    this.removeClass("colour_gridOn");
            }

        });
    },
    checkStock: function(size, colour) {
        // returns a yes/no on allowing to buy a size from current colour.
        var containers = new Hash(this.get('versions'));
        var allow = false, _this = this, l = this.get("startLead"), mid = false, neg = false;

        colour = (!$type(colour)) ? _this.get("selectedColour") : colour;
        containers.each(function(va, k) {
            if (allow)
                return false;
            var v = JSON.decode(va);
            if (v.colour == colour && v.size == size) {
                if (v.stock > 0 && v.disabled != 'true')
                    allow = true;
                l = v.lead;
                neg = v.nc;
                mid = v.cid;
            }
        });

        return {
            allow: allow,
            lead: l,
            cid: mid,
            nc: neg
        }
    },
    showStockStatus: function(cid) {

        if ($type(cid) == "number") {
            var thisContainer = this.getVersion(cid), thisEstimate = this.get("leadsEstimates")[thisContainer.lead];
            var leadMessage = "<span style='color: #3CCC49;background:url(/img/in-stock-ok.gif) no-repeat center right; padding-right: 25px;'>In Stock</span>";
            var dispatchMessage = "(Will be dispatched <span class='bold'>"+((thisEstimate == "Today" || thisEstimate == "Tomorrow") ? thisEstimate : "on "+thisEstimate)+"</span>)";
            if (thisContainer.disabled != "true") {
                // nc fix
                if (thisContainer.nc < 0 && thisContainer.lead != 1) {
                    leadMessage = "<span style='color: #e8ba40;background:url(/img/in-stock-way.gif) no-repeat center right; padding-right: 25px;'>On The Way</span>";
                    dispatchMessage = "(Will be dispatched <span class='bold'>within "+this.get("leadsTable")[thisContainer.lead]+"</span>)";
                } // end fix.

                // no stock
                if (thisContainer.nc <= 0 && thisContainer.stock <= 0) {
                    leadMessage = "<span style='color: #f33b3b;background:url(/img/in-stock-not.gif) no-repeat center right; padding-right: 25px;'>Out Of Stock</span>";
                    dispatchMessage = (this.get("traffic") != "red") ? "(... but we may have more on the way)" : "(... and we won't be getting any more)";
                }
            }
            else {
                leadMessage = "<span style='color: #f33b3b;background:url(/img/in-stock-not.gif) no-repeat center right; padding-right: 25px;'>Out Of Stock</span>";
                dispatchMessage = (this.get("traffic") != "red") ? "(... but we may have more on the way)" : "(... and we won't be getting any more)";
            }
        }
        else {
            var leadMessage = "", dispatchMessage = "";
        }

        $("lead").set("html", leadMessage);
        $("when").set("html", dispatchMessage);
    },
    saveStockStatus: function(lead, estimate) {
        this.set("lead", lead);
        this.set("estimate", estimate);
    },
    restoreStockStatus: function() {
        $("lead").set("html", this.get("lead"));
        $("when").set("html", this.get("estimate"));
    },
    buildSize: function(status, size, lead, cid, nc) {
        // create a size icon and return it as an object
        cid = cid.toInt();
        var _this = this;
        if (size == "One Size") {
            if (_this.checkStock(_this.get("selectedSize")).allow != false)
                $("add2basket").set("src", basketImages[basketState][1]);
            return false;
        }

        if (size.contains("zip") || size.contains("zp")) {
            status = status + " sizeIconZip";
            size = size.replace("Lzp", "Left Zip").replace("Rzp", "Right Zip");
        }

        return new Element("div", {"class": "SB curImage left " + status}).set("text", size).set("rel", cid).addEvents({
            click: function() {
                if (status == "sizeIconNo")
                    return false;
                _this.set("selectedSize", size);
                _this.set("selectedVersion", cid);
                _this.showSelectedSize();
                _this.saveStockStatus($("lead").innerHTML, $("when").innerHTML);

                var prv = this.getParent("div.colour_grid").getPrevious();
                if (_this.get("selectedColour") != prv.get("data-colour"))
                    prv.fireEvent("click");

                if ($("add2basket").get("src").contains("off"))
                    $("add2basket").set("src", basketImages[basketState][1]);
            },
            mouseenter: function() {
                _this.saveStockStatus($("lead").innerHTML, $("when").innerHTML);
                if (this.hasClass("sizeIconNo")) {
                    _this.showStockStatus(cid);
                    // myEventBubble(this, "Sorry, this size<br /> is out of stock.");
                    return false;
                }

                this.addClass("sizeIconOn");

                _this.showStockStatus(cid);

            },
            mouseleave: function() {
                var prv = this.getParent("div.colour_grid").getPrevious().get("data-colour");
                if (this.getText() != _this.get("selectedSize") || _this.get("selectedColour") != prv)
                    this.removeClass("sizeIconOn");
                _this.restoreStockStatus();

            }
        });
    },
    buildSizes: function() {
        // build the sizes available for current colour dynamically.
        var sizes = new Hash(this.get('sizes'));
        var versions = new Hash(this.get('versions'));
        var colours = new Hash(this.get('colours'));
        var _this = this;

        colours.each(function(vv, kk) {
            var target = $$("div.sizeBoxes").filter(function(sb) {
                if (sb.get("rel") == kk)
                    return sb;
            })[0];

            if (!target)
                return false;

            target.empty();
            sizes.each(function(v, k) {
                // 06/07/2010 16:48:41 fix for chrome so it does not reorder object properties if numeric key
                var k = k.replace("_", "");
                // end fix - sending prefix _ via php for $sizes
                var sc = _this.checkStock(k, kk);
                var statusClass = (sc.allow) ? "sizeIconOff" : "sizeIconNo";
                if (_this.get("selectedVersion") != false && _this.get("selectedSize") == k && _this.get("selectedColour") == kk)
                    statusClass = "sizeIconOn";
                if (!sc.allow && !sc.cid)
                    return false;
                var sizeBox = _this.buildSize(statusClass, k, sc.lead, sc.cid, sc.nc);
                if (sizeBox)
                    sizeBox.inject(target);
                else {
                    target.getPrevious().setStyles({
                        "font-size": "14px",
                        "font-weight": "bold"
                    });

                    target.getParent().addClass("cur").removeEvents().addEvent("click", function() {
                        var prv = this.getParent().getParent().getParent().getParent().getPrevious();
                        if (_this.get("selectedColour") != prv.get("data-colour"))
                            prv.fireEvent("click");
                    });

                }
            });

        });

        // $("sizes").empty();

        if (sizes.length < 2) // one size!
            return false;


    },
    toBasket: function(el) {
        // add the currently selected item to basket

        if ($("lead").getText().contains("Out Of Stock")) {
            myEventBubble($("add2basket"), "Sorry, item <br />not in stock!");
            return false;
        }

        if (!this.get("selectedVersion")) {
            $("add2basket").tooltip("Please select your size first.", {
                className: "what3",
                topOffset: 44,
                topStartOffset: 150,
                opacity: .95,
                delay: 3000,
                innerStyle: "padding: 5px; padding-top: 14px;line-height: 1.3; font-weight: bold"
            });
            return false;
        }

        if (basketState == "exchange") {
            if (window.opener && window.opener.document) {
                var uid = Cookie.read("uid");
                var txt = window.opener.document.getElements("textarea").filter(function(el) {
                    return el.uid == uid;
                });

                if (!txt.length)
                    txt = window.opener.document.getElement("textarea");
                else
                    txt = txt[0];

                if (txt) {
                    var initial = (txt.get("value") == txt.retrieve("initialValue")) ? null : txt.get("value");

                    txt.fireEvent("change", {
                        id: this.get("id"),
                        sku: this.get("selectedVersion")
                    });

                    toggleModal("#fff");
                    (function() {
                        Cookie.dispose("exchanging");
                        Cookie.dispose("uid");
                        window.close();
                        try {
                            window.opener.focus();
                        }
                        catch(e) {

                        }
                    }).delay(1000);
                    return 0;
                }
            }
        }

        togBasket.add(this.get("id"), this.get("selectedVersion"), 1);

        togBasket.show(el);
        // togBasket.showTotal();

    }, // end add2basket
    togBox: function(el) {
        var _this = this, imageEvent;
        el.modalBox({
            id: "lightPane",
            width: (Browser.Engine.trident4) ? 692 : 685,
            height: 645,
            title: _this.get("productName")+ " in "+ _this.get("selectedColour")

        });


        imageEvent = (function() {
            var lightPane = $("modalBody");
            if (!lightPane)
                return false;



            new Asset.image(el.get("href"), {
                "class": "xpi",
                onload: function() {

                    this.removeEvents().setStyle("opacity", 0).inject(lightPane, "top").fade(0,1);

                    if ($("closelight"))
                        $("closelight").smartDispose();
                    var closelight = new Element("div", {id: "closelight"}).setStyles({
                        width: 60,
                        float: "right",
                        background: "#fff",
                        "font-size": "14px",
                        "font-weight": "bold",
                        "z-index": 1000001000,
                        "text-align": "center"
                    }).injectTop(lightPane);

                    var angleEvents = function(preloadText) {
                        closelight.empty().set("html", preloadText);
                        $$(".miniangle").each(function(el) {
                            var fullSize = (el.get("src").contains("THUMB"))
                                         ? el.get("src").replace(/THUMB/, "FULL")
                                         : el.get("src").replace(/icon/, "main");

                            if (!$type(preload[el.id]))
                                preload[el.id] = new Asset.image(fullSize, {"class": "xpi"});

                            el.removeEvents().addEvents({
                                "click": function() {
                                    document.getElement(".xpi").replaceWith(preload[el.id].clone().fade(0,1));
                                }, // click end
                                "mouseenter": function() {
                                    this.addClass("Selectedimage");
                                },
                                "mouseleave": function() {
                                    this.removeClass("Selectedimage");
                                }
                            }).addClass("curImage").addClass("Plainimage");
                        }); // each
                    };

                    var preload = _this.get("cacheBoxAngles");

                    if (!$type(preload[_this.get("selectedColour")]))
                    new Ajax("/angles.php?a=mini&id="+_this.get("id")+"&version="+_this.get("selectedColour"), {
                        method: "get",
                        onComplete: function() {
                            preload[_this.get("selectedColour")] = this.response.text;
                            _this.set("cacheBoxAngles", preload);
                            angleEvents(this.response.text);
                        }
                    }).request(); // angles.
                    else
                        angleEvents(preload[_this.get("selectedColour")]);



                } // onload
            }); // fullimage
        }).delay(1000); // animation wait.
    },
    togBoxAttach: function() {
        var _this = this;
        $$("a[rel=lightbox]").each(function(el) {
            el.addEvent("click", function(e) {
                // intercept click
                var e = new Event(e).stop();

                if ($("zoomLarger"))
                    $("productImage").fireEvent("mouseleave");

                if (document.id("zoomer"))
                    document.id("zoomer").destroy();

                _this.togBox(el);
            });
        });
    },
    getAngles: function() {
        // gets the angled shots
        $("angles").setStyle("opacity", 0);

        var _this = this;

        if (cacheAngles.length > 0) {
            var cached = cacheAngles.filter(function(el) {
                if (el.colour == _this.get("selectedColour"))
                    return el;
            });

            if (cached.length) {
                $("angles").set("html", cached[0].text).fade(0,1);
                angles();
                return false;
            }
        }

        var ang = $("angles");

        new Ajax("/angles.php?id="+this.get("id")+"&version="+this.get("selectedColour"), {
            update: ang,
            method: "get",
            postData: "",
            onComplete: function() {

                if (ang && ang.getFirst())
                    ang.fade(0,1).getFirst().store("Selected", true);

                angles();
                cacheAngles.push({colour: _this.get("selectedColour"), text: this.response.text});
                // C.log(cacheAngles, _this.get("selectedColour"));
            }
        }).request();

    }, // end getAngles
    liveUpdate: function() {
        // attached to addtobasket mouseover event
        if (this.get("liveStockCheck") != true)
            return false;

        var _this = this;
        new Request({
            url: "/accountAjax.php",
            method: "get",
            onComplete: function() {
                var newStock = JSON.decode(this.response.text);
                var containers = _this.get('versions');
                var newcontainers = newStock.versions;

                // find out what has changed and if it affects the purchase
                if (!_this.get("selectedVersion")) {
                    // C.log("nothing, resetting");
                    // nothing selected anyway, does not matter, we can update all.
                    _this.set("versions", newcontainers);
                    _this.buildSizes();
                }
                else {
                    // they have something selected. see if it is affected
                    if (newcontainers[_this.get("selectedVersion")] != containers[_this.get("selectedVersion")]) {
                        // yes.
                        var sizeSelected = document.getElement(".SB[rel="+_this.get("selectedVersion")+"]");
                        if ($type(sizeSelected)) {
                            myEventBubble(sizeSelected, "Stock changed<br />please review.");
                            (function() {
                                if ($("myBubble"))
                                    $("myBubble").set("tween", {
                                        onComplete: function() {
                                            $("myBubble").destroy();
                                        }
                                    }).fade(1,0);
                            }).delay(3000);
                        }

                        _this.set({
                            "selectedVersion": $empty(),
                            "selectedSize": "",
                            "versions": newcontainers,
                            "lead": ""
                        });
                        _this.buildSizes();
                        _this.showSelectedSize();
                        _this.showStockStatus(_this.get("selectedVersion").toInt());
                    } else {
                        _this.set("versions", newcontainers);
                        _this.buildSizes();
                    }
                }

            }
        }).send("a=livestock&id="+this.get("id"));
    },
    stockReview: function() {
        // appraisal of current stock situation, greying out etc.
        var sizes = new Hash(this.get('sizes'));
        var _this = this;
        if (sizes.length == 1) {
            this.set("selectedSize", "One Size");
            // $("cas").set("text", "This item comes in: ");
            $$(".colours").each(function(el) {
                if (_this.getVersion(el.get("data-id")).stock <= 0)
                    el.fade(1, 0.5)
            });
        }
    },
    startMonitor: function() {
        // live updates of stock every nn seconds.
        if (this.get("liveStockCheck")) {
            (function() {
                this.liveUpdate();
            }).periodical(this.get("liveStockEvery")*1000, this);
        }
    },
    outOfStock: function() {
        var _this = this;



        $("outofstock").getElement("a").addEvents({
            click: function(e) {
                var e = new Event(e).stop();

                var OOSvers = [], versions = new Hash(_this.get("versions"));
                versions.each(function(ver) {
                   var ver = JSON.decode(ver);
                   if ((ver.stock <= 0 && ver.nc >= 0 )|| ver.disabled == "true")
                        OOSvers.push(ver);
                });

                var bodyText = "", boxheight = 222;

                if (OOSvers.length ) {
                    bodyText = "Please select the colour and size you'd like to be notified about:<br /><br /><select id='OOSversion' style='width:340px' class='myselects2'>";
                    OOSvers.each(function(ver) {
                        bodyText += "<option value='"+ver.cid+"'>Colour: <strong>" + ver.colour + "</strong>, Size: <strong>" + ver.size + "</strong>";
                    });

                    bodyText += '</select><div style="padding-left: 0px;">';
                    bodyText += '<label for="OOSemail" style="color:#000;float:left;font-family:Verdana, Arial, Helvetica, sans-serif;font-size:16px;font-weight:700;height:20px;margin-left:0;margin-right:0;padding-top:2px;width:inherit"  >';
                    bodyText += 'Enter your email address:</label>';
                    bodyText += "<br /><input title='Enter your email address' id='OOSemail' value='' name='email' type='text' class='myinput' tabindex='1' style='width:334px' />";
                    bodyText += '<div class="tcenter"><img src="/img/modal_subscribe.gif" id="OOSsubscribe" class="cur" /></div>';
                }
                else {
                    bodyText = "We're sorry, there are no 'out of stock' sizes of this product at the moment!<br /><br />You can just close this box and add to your basket.";
                    boxheight = 104;
                }

                this.modalBox({
                    height: boxheight,
                    width: 370,
                    title: "Out of stock? No problem...",
                    text: bodyText,
                    movable: true,
                    callback: function() {
                        new mooSelecta({
                            selector: "myselects2",
                            wrapperHeight: 194
                        });

                        toggleInputs("myinput", "myinputFocused");
                        var OOSsubscribe = $("OOSsubscribe");

                        if (OOSsubscribe) {
                            OOSsubscribe.addEvents({
                                click: function() {
                                    var em = $("OOSemail").get("value").clean();
                                    if (isValid(em)) {
                                        new Ajax("/accountAjax.php", {
                                            method: "get",
                                            onComplete: function() {
                                                $("modalBody").setStyles({
                                                    fontSize: "14px",
                                                    textAlign: "center"
                                                }).set("html", "<br /><br /><strong>Thank you for your interest, we appreciate it.</strong><br /><br /><br />You will receieve a notification email<br /> as soon as we stock this in.</center>");
                                                (function() {
                                                    if ($("modal"))
                                                        $("modal").fireEvent("click");
                                                }).delay(5000);
                                            }
                                        }).request("a=s2oos&email=" + em + "&skew="+$("OOSversion").get("value"));

                                    }
                                    else {
                                        // $("modalBox").setStyle("background", "#fff url(/img/login-review-box-error.gif) no-repeat");

                                        $("OOSemail").addClass("myinputFocusedError");

                                        $("OOSemail").tooltip("Invalid email,<br />check and try again.", {
                                            className: "what3",
                                            topOffset: 44,
                                            topStartOffset: 200,
                                            opacity: 1,
                                            eventEnd: "mouseenter",
                                            innerStyle: "padding: 5px;line-height: 1.3; font-weight: bold"
                                        }).addEvents({
                                            focus: function() {
                                                $("modalBox").setStyle("background", "#fff url(/img/top_grad_2.gif) repeat-x");
                                            }
                                        });

                                    }


                                }
                            }); // add Events
                        } // if
                    } // callback
                });


            }
        });
    }
}); // end Product



var angles = function() {
    var anglesObj = document.id("angles"), divAngles = anglesObj.getElements("div.angles"), zoomerKeys = [];

    divAngles.each(function(el) {
        var colour = el.get("data-colour");
        el.addEvents({
            mouseenter: function() {
                if (this.hasClass("myangleSelected")) {
                    this.store("Selected", true);
                    return false;
                }
                this.addClass("myangleOn").store("Selected", false);
            },
            mouseleave: function() {
                this.removeClass("myangleOn");
                if (this.retrieve("Selected"))
                    return false;

            },
            click: function() {
                if (this.retrieve("Selected"))
                    return false;

                if (document.id("zoomer"))
                    document.id("zoomer").destroy();

                // refactored to store zoomer
                var PI = $("productImage");

                if (PI.get("data-zoomer")) {
                    var old = $("angles").getElements("div.myangleSelected").filter(function(el) {
                        return el.retrieve("Selected");
                    });

                    anglesObj.getElement("div.myangleSelected").store("data-zoomer", PI.get("data-zoomer"));
                }

                divAngles.removeClass("myangleSelected").store("Selected", false);

                this.store("Selected", true).addClass("myangleSelected");

                var fn = this.getFirst().get("src");

                if (colour == "_") { // main
                    var mediumView = fn.replace("icon", "full");
                    var fullView = fn.replace("icon", "main");
                }
                else {
                    var mediumView = fn.replace("THUMB_", "");
                    var fullView = fn.replace("THUMB_", "FULL_");
                }

                if (this.get("data-zoomer"))
                    this.store("data-zoomer", fn.replace("THUMB_", "MAX_"));

                PI.set("id", "duff");
                var PIC = PI.clone().set({
                    "src": mediumView
                }).replaces(PI).set("id", "productImage").fade(0,1);

                if (this.get("data-zoomer")) {
                    PIC.store("data-zoomer", this.retrieve("data-zoomer")).zoomer();
                    // console.log("zoomer added");
                }


                document.id("PL").set("href", fullView);


            }
        }).addClass("cur");
    });

    // add zoomer?
    var selected = document.getElement("div.myangleSelected");
    document.id("productImage").set("data-zoomer", false).eliminate("data-zoomer");

    if (selected && (selected.retrieve("data-zoomer") || selected.get("data-zoomer")))
        document.id("productImage").zoomer();

};

var charts = {
    sizeChart: function(el, dbid) {
        // get the sizechart data on screen...
        if ($("mychart"))
            return false;

        var chartTitle = "";
        new Ajax("/accountAjax.php?a=getchart&id="+dbid, {
            method: "get",
            onComplete: function() {
                var MT = new Element("div", {id: "modalTitle"}).setStyles({display:"none"}).inject(document.body),
                temp = new Element("div").set("html", this.response.text).setStyles({
                    position: "absolute",
                    top: -400,
                    left: -400,
                    width: 540
                }).inject(document.body), tempHeight = temp.getCoordinates()['height'] + 28;

                temp.dispose();

                el.modalBox({
                    title: MT.innerHTML,
                    text: this.response.text,
                    shadow: !false,
                    width: 560,
                    height: tempHeight,
                    id: "mychart",
                    innerPadding: 0,
                    movable: true
                });

                MT.dispose();

            }
        }).request();
    }
}


Element.implement({
    facebookLike: function(url, options) {
        var options = $merge({
            show_faces: "false",
            layout: "standard",
            width: 90,
            action: "like",
            font: "lucida grande",
            colorscheme: "light",
            height: 21,
            href: url
        }, options);

        var src= "https://www.facebook.com/plugins/like.php?href={href}&layout={layout}&show_faces={show_faces}&width={width}&action={action}&font={font}&colorscheme={colorscheme}&height={height}".substitute(options);

        return this.adopt(new Element("iframe", {
            styles: {
                border: "medium none",
                overflow: "hidden",
                width: options.width,
                height: options.height
            },
            id: "FBFrame",
            frameborder: 0,
            allowTransparency: "true",
            scrolling: "no",
            src: src
        }));
    },
    zoomer: function() {
        var garbageCollect, zoomed = false;

        this.removeEvent("mousemove");

        if ($("zoomLarger")) {
            $("zoomLarger").destroy();
            // C.log("disposed larger");
        }
        if ($("zoomer")) {
            $("zoomer").destroy();
            //C.log("disposed");
        }

        var pbp = document.id("product_buyout_pane");
        pbp.setStyle("border", 0);

        var _this = this, coords = this.getCoordinates(), zoomer, zoomDimensions = {
            width: 127,
            height: 88,
            maxRight: coords.right - 127,
            maxBottom: coords.bottom - 88
        }, buyOut = pbp.getCoordinates();


        zoomLarger = new Element("div", {
            id: "zoomLarger",
            styles: {
                height: buyOut.height - 2,
                width: buyOut.width - 2,
                border: "1px solid #000",
                position: "absolute",
                display: "none",
                zIndex: 1000,
                marginTop: -1,
                marginLeft: -1
            }
        }).inject(pbp, "top");

        pbp.setStyle("border", "1px solid #ccc");

        var storageZoom = this.retrieve("data-zoomer");

        var largerImage = (storageZoom && storageZoom.contains("MAX"))
            ? this.retrieve("data-zoomer")
            : this.get("src").replace("full", "max");

        // console.log(largerImage);
        new Asset.image(largerImage, {

            onload: function() {
                var AR = 3.75;
                // console.info("loaded "
                zoomLarger.setStyle("background",  "#fff url(" +largerImage+ ") no-repeat");
                _this.addEvents({
                    mousemove: function(e) {
                        coords = _this.getCoordinates();
                        zoomDimensions = {
                            width: 127,
                            height: 88,
                            maxRight: coords.right - 127,
                            maxBottom: coords.bottom - 88
                        }
                        var e = new Event(e);
                        // where do we put it?
                        var adjY = window.getScrollTop() + e.client.y, adjX = window.getScrollLeft() + e.client.x;

                        //C.log(window.getScrollTop(), e.clientY, adjX, adjY);

                        newPos = {
                            left: (adjX - zoomDimensions.width / 2 > zoomDimensions.maxRight) ? zoomDimensions.maxRight : adjX - zoomDimensions.width / 2,
                            top: (adjY - zoomDimensions.height / 2 > zoomDimensions.maxBottom) ? zoomDimensions.maxBottom : adjY - zoomDimensions.height / 2
                        };


                        if (newPos.left < coords.left)
                            newPos.left = coords.left;

                        if (newPos.top < coords.top)
                            newPos.top = coords.top;

                        if ($("zoomer"))
                            zoomer = $("zoomer").setStyle("display", "block");
                        else
                            zoomer = new Element("div", {
                                id: "zoomer"
                            }).setStyles({
                                position: "absolute",
                                zIndex: 100000000+1,
                                width:zoomDimensions.width,
                                height:zoomDimensions.height,
                                // "background-image": "url(/img/polka.gif)",
                                background: "#ccc",
                                border: "1px solid #fff"
                            }).setStyle("opacity", .3).injectAfter(this).addEvents({
                                mousemove: function(e) {
                                    $clear(garbageCollect);
                                    var adjY = window.getScrollTop() + e.client.y, adjX = window.getScrollLeft() + e.client.x;

                                    newPos = {
                                        left: (adjX - zoomDimensions.width / 2 > zoomDimensions.maxRight) ? zoomDimensions.maxRight : adjX - zoomDimensions.width / 2,
                                        top: (adjY - zoomDimensions.height / 2 > zoomDimensions.maxBottom) ? zoomDimensions.maxBottom : adjY - zoomDimensions.height / 2
                                    };


                                    if (newPos.left < coords.left)
                                        newPos.left = coords.left;

                                    if (newPos.top < coords.top)
                                        newPos.top = coords.top;

                                    // fix via margins.
                                    var newMargins = {
                                        marginLeft: newPos.left,
                                        marginTop: newPos.top
                                    };

                                    this.setStyles(newPos);
                                    zoomed = true;

                                    // now larger one...
                                    zoomLarger.setStyles({
                                        backgroundPosition: "-" + (newPos.left-coords.left) * AR+"px -" + (newPos.top-coords.top) * AR + "px"
                                    });

                                },
                                mouseleave: function() {
                                    this.setStyle("display", "none");
                                    zoomLarger.setStyle("display", "none");
                                    zoomed = false;
                                }
                            });

                        zoomed = true;
                        zoomer.setStyles(newPos)

                        zoomLarger.setStyle("display", "block");

                    }, // mousemove
                    mouseleave: function() {
                        garbageCollect = (function() {
                            if (!zoomed) {
                                if (zoomer)
                                    zoomer.setStyle("display", "none");
                                zoomLarger.setStyle("display", "none");
                            }
                        }).delay(200); // 1 sec garbage collector.
                    }
                }); // events
            } // onload
        });


    }
});

var promoWidget = new Class({
    Implements: [Options, Events],
    stories: {},
    options: {
        selector: "div.whyItem",
        useAjax: true,
        baseURL: "accountAjax.php",
        baseOptions: "a=get_tip&id={id}",
        storage: "data-id",
        separatorClass: "dotted",
        overClass: "whyOver",
        storyId: "whyStory",
        storyClose: "whyStoryClose"
    },
    initialize: function(element, options) {
        this.element = document.id(element);
        if (!this.element)
            return;

        this.getElements();
        if (!this.elements.length)
            return;

        this.attachEvents();
        this.storyOpen = false;

    },
    getElements: function() {
        this.elements = this.element.getElements(this.options.selector);
        // console.log(this.element.getElements("img").get("src"));
    },
    attachEvents: function() {
        this.fxSort = new Fx.Sort(this.elements, {
            transition: Fx.Transitions.linear.easeInOut,
            link: "chain",
            duration: 500,
            mode: "vertical",
            onComplete: function() {
                this.fxSort.rearrangeDOM();
                this.getElements();

                this.elements.getLast().removeClass(this.options.separatorClass);
                this.showStory(this.elements[0]);
            }.bind(this)
        });

        this.elements.each(function(el) {
            el.addEvents({
                click: function() {
                    if (this.storyOpen)
                        return;
                    el.addClass(this.options.separatorClass);
                    this.fxSort.swap(el, this.element.getElement(this.options.selector));
                    //this.fxSort.rearrangeDOM();
                    this.getElements();

                }.bind(this),
                mouseenter: function() {
                    el.addClass(this.options.overClass);
                }.bind(this),
                mouseleave: function() {
                    el.removeClass(this.options.overClass);
                }.bind(this)
            });
        }, this);

    },
    showStory: function(el) {
        if (!this.story) {

            this.story = new Element("div", {
                id: this.options.storyId,
                styles: {
                    opacity: 0
                }
            });

            this.storyClose = new Element("div", {
                id: this.options.storyClose,
                events: {
                    mouseenter: function() {
                        this.fade(1).addClass("shadowy");
                    },
                    mouseleave: function() {
                        this.fade(.5).removeClass("shadowy");
                    },
                    click: function() {
                        this.fireEvent("mouseleave");
                        this.story.dispose();
                        this.storyOpen = false;
                    }.bind(this)
                },
                styles: {
                    opacity: .5
                }
            });
        }

        this.story.inject(this.element, "top").set({
            opacity: 0
        }).fade(0, .95);

        this.getStory(el);
    },
    getStory: function(el) {
        var key = el.get(this.options.storage);

        if (!this.stories[key]) {
            new Request({
                url: "/accountAjax.php",
                method: "get",
                onComplete: function(response) {
                    this.stories[key] = response;
                    this.outputTip(key);
                }.bind(this)
            }).send(this.options.baseOptions.substitute({id: key}));

        }
        this.outputTip(key);
    },
    outputTip: function(key) {
        this.story.set("html", this.stories[key]);
        this.storyClose.set("opacity", .5).removeClass("shadowy").inject(this.story, "top");
        this.storyOpen = true;
    }

});



// var load_method = (Browser.Engine.trident) ? "load" : 'domready';
(function() {
    String.implement({
        isURL: function() {
            return /^(https?):\/\/((?:[a-z0-9.-]|%[0-9A-F]{2}){3,})(?::(\d+))?((?:\/(?:[a-z0-9-._~!$&'()*+,;=:@]|%[0-9A-F]{2})*)*)(?:\?((?:[a-z0-9-._~!$&'()*+,;=:\/?@]|%[0-9A-F]{2})*))?(?:#((?:[a-z0-9-._~!$&'()*+,;=:\/?@]|%[0-9A-F]{2})*))?$/i.test(this);
        }
    });
})();

window.addEvent("domready", function() {

    // price match 15/03/2011 10:15:30
    (function() {
        var priceMatch = document.id("priceMatch");
        if (!priceMatch)
            return;
        priceMatch.addEvents({
            click: function(e) {
                e.stop();
                this.modalBox({
                    title: "Our WebTogs Price Promise Guarantee",
                    width: 660,
                    height: 560,
                    animate: false,
                    scroll: false,
                    text: "loading...",
                    callback: function() {
                        var mbody = document.id("modalBody");



                        new Request({
                            url: "accountAjax.php",
                            method: "get",
                            onComplete: function() {
                                mbody.set("html", this.response.text);
                                toggleInputs("myinputShort", "myinputShortFocused");
                                toggleInputs("myinput", "myinputFocused");

                                var showError = function(message) {
                                    this.tooltip(message, {
                                        className: "what3",
                                        topOffset: 44,
                                        topStartOffset: 200,
                                        opacity: 1,
                                        eventEnd: "mouseenter",
                                        innerStyle: "padding: 5px;line-height: 1.3; font-weight: bold"
                                    }).addClass("myinputFocusedError");
                                };

                                new mooPlaceholder().attachToElements();

                                var requireds = [$("customer_name"), $("customer_email"), $("other_URL"), $("quotedPrice")];

                                document.id("PMF").addEvents({
                                    submit: function(e) {
                                        e.stop();

                                        var errors = false;
                                        requireds.each(function(input) {
                                            var value = input.get("value").trim();
                                            if (value == input.get("placeholder"))
                                                value = "";

                                            if (!value.length && !errors) {
                                                errors = true;
                                                showError.call(input, ["Please fill in all relevant<br />fields and try again."]);
                                            }

                                        });

                                        if (errors)
                                            return;

                                        new Request({
                                            url: this.get("action"),
                                            method: "post",
                                            data: this,
                                            onComplete: function() {
                                                mbody.set("html", "<div class='tcenter' style='padding-top: 180px;'><strong>Thanks for your submission. </strong><br />We will check it out and get back to you as soon as possible.<br /><br /><img src='/img/products/Price-pop-up-close-button.jpg' class='cur closeThis' /></div>");

                                            }

                                        }).send();

                                    }

                                });

                            }
                        }).send("a=priceGuarantee&id="+priceMatch.get("data-id"));
                    }

                });
            }
        });

    })();

    // 23/02/2011 16:29:00 tips?
    (function() {
        var tiptip = document.id("tiptip");
        if (tiptip) {
            var sl = document.id("sizesLink"), whereTo = sl.getLast() || sl;
            new Element("a", {
                styles: {
                    marginLeft: sl == whereTo ? 0 : 10
                },
                href: "#tiptip",
                html: "<img src='/img/product/size-advice-button.gif' />"
            }).inject(whereTo);
        }
    })();


    var PH = $("product_heading_title");
    var reduceTitle = function() {
        var PHh1 = PH.getFirst(), fontSize = 18, currentSize = PH.getStyle("height").toInt();
        if (currentSize <= 23)
            return false;

        while (currentSize > 23) {
            fontSize--;
            PHh1.setStyle("font-size", fontSize + "px");
            currentSize = PH.getStyle("height").toInt();
            // C.log(PH.getStyle("height").toInt());
        }

        PH.setStyle("height", 23);

    }

    if (PH)
        reduceTitle();


    (function() {
        // recent products
        var recent = document.getElements("div.recentProducts");

        if (!recent.length)
            return;

        recent.each(function(el) {
            el.getFirst().addEvents({
                click: function(e) {
                    e.stop();
                    new Request({
                        url: "/accountAjax.php",
                        method: "get",
                        data: {
                            a: "removeProdFromSession",
                            id: el.get("data-id")
                        },
                        onComplete: function() {
                            el.set("tween", {
                                onComplete: function() {
                                    this.element.destroy();
                                    recent = document.getElements("div.recentProducts");

                                    if (!recent.length) {
                                        document.id("recentProducts").getPrevious().destroy();
                                        document.id("recentProducts").destroy();
                                    }
                                }
                            }).fade(0);
                        }
                    }).send();
                }
            });
        });
    })(); // recent products



    document.id("product_buyout_pane").addEvents({
        mouseenter: function() {
           this.setStyle("border", "1px solid #000");
        },
        mouseleave: function() {
           this.setStyle("border", "1px solid #ccc");
        }
    });

    var PI = document.id("productImage");

    if (PI.retrieve("data-zoomer")||PI.get("data-zoomer"))
        (function() {
            $("productImage").zoomer();
        }).delay(1000);


    // cdc
    var checkSum = $("priceSwap").get("value") + $("deliveryCountry").get("value");
    var cdcDelay = 0, csc = $("changeShippingSource").innerHTML;

    if (!$("cdc"))
        cdcDelay = 2000;

    $("changeShippingSource").dispose();

    (function() {
        $("cdc").addEvents({
            click: function(e) {
                new Event(e).stop();
                currencySwap.openSwapper(this);
            }
        }).addClass("curImage");
    }).delay(cdcDelay);

    // rest
    if ($("sizingchart"))
        $("sizingchart").addEvent("click", function() {
            charts.sizeChart(this, this.get("data-id"));
        });


    document.id("CS").addEvent("click", function() { continueShopping() }).addClass("curImage");



    // document.getElement("h1").dispose();

    Cookie.dispose("basketAB");


    document.id("add2basket").addEvents({
        click: function() {
            prd.toBasket(this);
        },
        mouseenter: function() {
            $clear(checker);
            var checker = (function() {
                prd.liveUpdate();
            }).delay(400);
        }
    });


    // widget for promo if available
    var pr = new promoWidget("whyWidgets");

    // get retweets for product page
    (function() {
        var tweetmeme = document.id("tweetmeme");
        var url = tweetmeme.get("rel").replace("dev", "www");

        tweetmeme.addEvents({
            click: function() {
                var count = this.getFirst().get("text").toInt();
                count++;
                this.getFirst().set("text", count);
            }
        });

        new Request.tweetmeme(url, {
            onSuccess: function(data) {
                var count = data && data.status != 'failure' && data.story ? data.story.url_count : 0;
                // count += 1;
                tweetmeme.set("html", "<div class='tcenter'>" + count + "</div>");
            }
        }).send();

        new Request.bitly(url, {
            onSuccess: function(data) {
                if (data && data.data && data.status_code == 200) {
                    var orig = data.data.long_url, hash = data.data.url, difference = orig.length - hash.length;

                    var url = (difference > 0) ? hash : url;
                    var tweet = "#outdoor #adventure " + document.title + " " + url + " - @webtogs";
                    tweetmeme.set({
                        href: "http://twitter.com/home/?status=" + escape(tweet),
                        target: "_blank"
                    });
                }
                else {
                    // try w/o bitly.
                    var tweet = "#outdoor #adventure " + document.title + " " + url + " - @webtogs";
                    tweetmeme.set({
                        href: "http://twitter.com/home/?status=" + escape(tweet),
                        target: "_blank"
                    });
                }
            }
        }).send();

    }).delay(100);


    // repostion features
    (function() {
        var feats = document.id("pdfeatures"), desc = document.id("pddescription"), tech = document.id("pdtech");
        var coords = {};
        if (!feats || !tech)
            return; // we don't show feats if empty.

        coords.PD = desc.getCoordinates();
        coords.FT = feats.getCoordinates();
        coords.TC = tech.getCoordinates();

        if (coords.PD.height.toInt() < coords.TC.height.toInt() + coords.FT.height.toInt())
            desc.adopt(feats);

    }).delay(100);

    // product reviews 07/04/2011 14:49:02
    (function() {
        document.getElements("a.placeReview").addEvents({
            click: function(e) {
                if (e && e.stop)
                    e.stop();
                if (!document.id("productRatingsJs")) {
                    new Asset.javascript("/js/productRatings.js", {
                        id: "productRatingsJs",
                        onload: function() {
                            attachRatingsBits.apply(e.target, [prd.get("id")]);
                        }
                    });
                }
                else {
                    attachRatingsBits.apply(e.target, [prd.get("id")]);
                }
            }
        }); // end addEvents

        // sorter
        var reviewsWrap = document.id("reviewsWrap");

        var getRidOfNoData = function() {
            if (document.getElement("div.NOmoreReviews")) {
                document.getElement("div.NOmoreReviews").set("tween", {
                    onComplete: function() {
                        //this.element.destroy();
                    },
                    duration: 6000
                }).fade(.2);
            }
        };

        getRidOfNoData();


        var fetchReviews = function(sort, lastReview, callback) {
            new Request({
                url: "/productReviews.php",
                method: "get",
                data: {
                    o: sort,
                    a: "xhr",
                    id: prd.options.id,
                    last: lastReview || ''
                },
                onComplete: function() {
                    if (lastReview)
                        reviewsWrap.set("html", reviewsWrap.get("html") + this.response.text);
                    else
                        reviewsWrap.set("html", this.response.text);

                    if (callback) {
                        callback.run();
                    }

                    getRidOfNoData();
                }
            }).send();
        };

        var sorter = document.id("reviewSortOrder");
        if (!Cookie.read("reviewsSortOrder"))
            Cookie.write("reviewsSortOrder", "SortDate;DESC", {
                path: "/"
            });

        if (sorter) {
            sorter.addEvents({
                change: function() {
                    var opt = this.get("value").clean();

                    if (opt.length) {
                        Cookie.write("reviewsSortOrder", opt, {
                            path: "/"
                        });
                        fetchReviews(opt);
                    }
                }
            });
        }

        if (reviewsWrap) {
            reviewsWrap.addEvents({
                "click:relay(div.moreReviews)": function(e, el) {
                    el.set("text", "GETTING MORE REVIEWS...");
                    fetchReviews(Cookie.read("reviewsSortOrder"), reviewsWrap.getElements("div.ratingWrap").getLast().get("data-id"), function() {
                        reviewsWrap.getElement("div.moreReviews").dispose();
                    });
                },
                "click:relay(img.reviewAction)": function(e, el) {
                    var p = el.getParent(), rid = p.get("data-id");
                    new Request({
                        url: "/accountAjax.php",
                        method: "get",
                        onComplete: function() {
                            p.empty();
                            p.getPrevious().set("html", "Thank you");
                        }
                    }).send("a=reviewHelpful&id="+rid+"&vote=" + ((el.hasClass("reviewHelpful")) ? "upvote" : "downvote"));
                }
            });

        }


    }).delay(10);

    // equal height for average bar columns
    (function() {
        var parentNode = document.getElement("div.whyAverage");
        if (!parentNode)
            return;

        var divs = parentNode.getElements("div.averageBobs"), highest = 0;

        divs.each(function(div) {
            var height =  div.getSize().y;
            if (height > highest)
                highest = height;
        });

        divs.setStyle("height", highest);
    }).delay(10);

    // exchange?
    if (window.location.href.contains("exchange=true") || Cookie.read("exchanging") == "yes") {
        // relevant element.
        var uid = window.location.href.split("ret=")[1] || Cookie.read("uid") || false;

        new Element("div", {
            styles: {
                border: "1px solid #555",
                position: "absolute",
                background: "#ffffdf",
                padding: 5,
                color: "#000",
                width: 958,
                zIndex: 10000000,
                opacity: 0
            },
            html: "You are currently browsing for an <strong class='blueColour'>exchange</strong>. Once you select your replacement item, this window will <a href='#' id='closeExchange'>close</a>"
        }).inject(document.id("main_wrap"), "top").fade(0, .9).dropShadow();

        document.id("closeExchange").addEvents({
            click: function() {
                Cookie.dispose("exchanging");
                if (window.opener && window.opener.document) {
                    window.close();
                }
                else {
                    this.getParent().smartDispose();
                    basketState = "basket";
                    $("add2basket").set("src", basketImages[basketState][0]);
                }
            }
        });
        basketState = "exchange";

        Cookie.write("exchanging", "yes", {
            path: "/"
        });

        Cookie.write("uid", uid, {
            path: "/"
        });

        $("add2basket").set("src", basketImages[basketState][0]);
    }
    else {
        Cookie.dispose("exchanging");
        Cookie.dispose("uid");
    }
});

