﻿/*  ROTATOR PLUGIN By COLIN WISEMAN */
(function ($) {

    // this is a complicated beastie as it encompasses more than just rotation of pages now
    // due to style considerations - some of the rotation elements have a "content" block
    // that will slide the "block".  because we need to remember the current page, this was
    // the most logical way to build it.

    var pathname = window.location.pathname;

    var Rotator = function (element) {
        var elem = $(element);
        var id = "";

        var obj = this;

        var nexts = $(elem).find(".next"); // each rotator has a next button
        var prevs = $(elem).find(".previous"); // each rotator has a back button
        var rms = $(elem).find("a[rel]"); // some of the rotators have a "content" page that will allow the user to slide to a specific block.
        var pageLinks = elem.find(".pager ul li");

        // the current chapter is the vertical scroll of the page
        // if the current chapter is the same as the chapter of the link that has been clicked,
        // then the rotator will scroll the web page to the correct chapter
        var currentChapter = "";
        var currentPage = 0; //  the current page is the horizontal scroll of the rotator

        var siblingBlocks = null;
        var current = 0;
        var holder = null;
        var moving = false;

        // a public method that returns the current "chapter" that the web page is on
        this.setChapter = function (chapter) {
            currentChapter = chapter;
        }

        // a public method that returns wether or not this instance of the rotator is currently moving
        this.isMoving = function () {
            return moving;
        }

        // a public method that basically handles all the movement
        this.scrollTo = function (chapter, page) {
            moving = true;

            if (isTablet()) {
                // scroll to the chapter if it is only a new chapter...don't scroll if there is a page number/name involved
                // this takes into account sub navigation
                if (currentChapter != chapter && ((page + "") == "" || (page + "") == "0")) {
                    $.scrollTo(chapter + "-page", "500");
                }

                // now scroll if the page exists
                if ((page + "") != "")
                    scrollToPage(page);
            }
            else {

                if (currentChapter != chapter) {
                    $.scrollTo(chapter + "-page", "500", function () {
                        scrollToPage(page);
                    });
                }
                else {
                    scrollToPage(page)
                }

            }

            currentChapter = chapter;

            var path = "/virtual" + pathname + chapter + "/" + page;
            _gaq.push(['_trackPageview', path]);
        }

        function indexMove(obj, index) {
            if (!moving) // if it is moving, we won't want to set a page, otherwise things might go gooey!
            {
                $(obj).click(function (e) {
                    var aBetterEventObject = $.Event(e);
                    // Now you can do what you want: (Cross-browser)
                    aBetterEventObject.preventDefault();

                    var rel = 0;

                    // if the obj that has been passed in, has a "rel" property on it, this "rel" property will be
                    // what we want to see in the URL
                    if ($(obj).attr("rel") != undefined && $(obj).attr("rel") != "") {
                        index = $(obj).attr("rel");
                    }
                    else {

                        // the object that has been passed in, doesn't have a "rel" property
                        // so from the index passed in, check if the block we are to be
                        // rotated to has a label to use instead of an number.
                        if ($((siblingBlocks)[index]).attr("rel") != undefined) {
                            index = $((siblingBlocks)[index]).attr("rel");
                        }
                    }

                    if (index == 0)
                        location.hash = id;
                    else
                        location.hash = id + "/" + index;

                });
            }
        }

        function scrollToPage(page) // not a public method
        {
            var moveBy = 0;
            $(siblingBlocks).each(function (index, obj) {
                if ($(this).attr("rel") == page) {
                    page = index;
                }
            });

            if (page > currentPage) {
                for (ii = currentPage; ii < page; ii++) {
                    // moveBy += parseInt($(siblingBlocks[ii]).css("width"));
                    moveBy += parseInt($(siblingBlocks[ii]).css("width")) +
                                        parseInt($(siblingBlocks[ii]).css("margin-right")) +
                                        parseInt($(siblingBlocks[ii]).css("margin-left")) +
                                        parseInt($(siblingBlocks[ii]).css("padding-right")) +
                                        parseInt($(siblingBlocks[ii]).css("padding-left"));
                }

                siblingBlocks.each(function (index, obj) {
                    var currentLeft = parseInt($(this).css("left"));
                    // subtract the moveBy as we are moving to the right
                    var newLeft = currentLeft - moveBy;
                    $(this).animate({ left: newLeft + "px" }, "1000", function () { moving = false; });
                });
            }
            else {
                for (ii = page; ii < currentPage; ii++) {
                    // moveBy += parseInt($(siblingBlocks[ii]).css("width"));                    
                    moveBy += parseInt($(siblingBlocks[ii]).css("width")) +
                                        parseInt($(siblingBlocks[ii]).css("margin-right")) +
                                        parseInt($(siblingBlocks[ii]).css("margin-left")) +
                                        parseInt($(siblingBlocks[ii]).css("padding-right")) +
                                        parseInt($(siblingBlocks[ii]).css("padding-left"));

                }

                siblingBlocks.each(function (index, obj) {
                    var currentLeft = parseInt($(this).css("left"));

                    // add the moveBy as we are moving to the left
                    var newLeft = currentLeft + moveBy;
                    $(this).animate({ left: newLeft + "px" }, "1000", function () { moving = false; });
                });
            }

            currentPage = parseInt(page);

            if (pageLinks != null) {
                pageLinks.removeClass("selected");
                $(pageLinks[currentPage]).addClass("selected");
            }

        }

        this.init = function (settings) {
            // each rotator has a block holder, think of the block holder as a "window", where the blocks slide past, making them visible.

            try {
                id = $(element).parents(".page").attr("id").replace("-page", "");
            }
            catch (ex) {

            }

            pager = settings['pager'];

            holder = $(elem).children("." + settings['window-class'])[0];
            if (holder != null) {
                // now get all the blocks that are related - siblings :D
                // we will now move the blocks to the correct position, so that the developer doesn't
                // need to work all that out!       
                siblingBlocks = $(holder).children("." + settings['item-class']);
                $(siblingBlocks).each(function (index, obj) {
                    $(this).css("left", current);
                    $(this).css("top", 0);

                    // the next block's position will be the current position + the width of the one we just placed
                    current += parseInt($(this).css("width")) +
                                        parseInt($(this).css("margin-right")) +
                                        parseInt($(this).css("margin-left")) +
                                        parseInt($(this).css("padding-right")) +
                                        parseInt($(this).css("padding-left"));

                    // current += parseInt($(this).css("width")); // the next block's position will be the current position + the width of the one we just placed

                    index++;
                });

                $(holder).find("a.previous,a.next").each(function (index, obj) {
                    // we generally use # as the href on a tags that we want to "work", but don't want to go anywhere.  This helps with styling.
                    // but this messes around with movement on the page.
                    // remove the # tag at this point so that the styles are applied, but the hash tag doesn't work.
                    $(this).attr("href", "");
                });

                $(nexts).click(function (e) {

                    var aBetterEventObject = $.Event(e);
                    // Now you can do what you want: (Cross-browser)
                    aBetterEventObject.preventDefault(); // stop any clicks from redirecting the site without our say so.

                    if (!moving) // if it is moving, we won't want to set a page, otherwise things might go gooey!
                    {
                        var nextIndex = currentPage + 1;
                        if (nextIndex < siblingBlocks.length) {
                            var name = $($(siblingBlocks)[nextIndex]).attr("rel");
                            if (name != "" && name != undefined)
                                location.hash = id + "/" + name;
                            else
                                location.hash = id + "/" + nextIndex;
                        }
                        else
                            location.hash = id;
                    }

                });

                $(prevs).click(function (e) {

                    var aBetterEventObject = $.Event(e);
                    // Now you can do what you want: (Cross-browser)
                    aBetterEventObject.preventDefault(); // stop any clicks from redirecting the site without our say so.

                    if (!moving) // if it is moving, we won't want to set a page, otherwise things might go gooey!
                    {
                        var previousIndex = currentPage - 1;
                        if (previousIndex >= 0) {
                            if (previousIndex == 0)
                                location.hash = id;
                            else {

                                var name = $($(siblingBlocks)[previousIndex]).attr("rel");
                                if (name != "" && name != undefined)
                                    location.hash = id + "/" + name;
                                else
                                    location.hash = id + "/" + previousIndex;
                            }
                        }
                        else {
                            // previous index < 0
                            previousIndex = ($(siblingBlocks).length - 1);
                            var name = $($(siblingBlocks)[previousIndex]).attr("rel");
                            if (name != "" && name != undefined)
                                location.hash = id + "/" + name;
                            else
                                location.hash = id + "/" + previousIndex;
                        }
                    }

                });

                $(rms).each(function (index, obj) {
                    indexMove(this, index);
                });

                $(pageLinks).each(function (index, obj) {
                    indexMove(this, index);
                });

                var pager = elem.find(".pager");

                if (pager.length) {
                    var ul = $(pager[0]).find("ul");
                    if (ul.length) {
                        var lis = $(ul[0]).find("li");
                        var length = 0;

                        $(lis).each(function (index, obj) {
                            // the $(elem).outerWidth() doesn't seem to work on dynamic elements
                            length += parseInt($(obj).css("width")) +
                                        parseInt($(obj).css("margin-right")) +
                                        parseInt($(obj).css("margin-left")) +
                                        parseInt($(obj).css("padding-right")) +
                                        parseInt($(obj).css("padding-left"));
                        });


                        $(ul[0]).css("width", length + "px");
                    }
                }
            }
        };
    }



    $.fn.rotator = function (options) {
        var settings = {
            'window-class': 'block-holder',
            'item-class': 'block'
        };

        return this.each(function () {
            if (options) {
                $.extend(settings, options);
            }

            var element = $(this);

            // Return early if this element already has a plugin instance
            if (element.data('rotator')) {
                element.data('rotator', null);
            }

            var rotator = new Rotator(this);
            rotator.init(settings);

            // Store plugin object in this element's data
            element.data('rotator', rotator);

        });
    };

})(jQuery);

