/* Copyright 2009 Palm, Inc.  All rights reserved. */
/*global Mojo, Class, $L, Template, WordAssistant, ExcelAssistant, PowerPointAssistant */
/*jslint rhino:true, undef:true */

var OutlineAssistant = Class.create({

    initialize: function( documentAssistant, outlineArray ) {

        this.outline_typetext = undefined;
        this.check_page = 1;
        this.listArray = [];

        this.documentAssistant = documentAssistant;
        this.outlineFromServer = outlineArray;
   
        // false indicates that we are NOT calling as a result of wanting to filter
        this.listArray = this.buildOutline( this.outlineFromServer, false);
    },

    setup: function() {
        //Mojo.Log.info("OutlineAssistant: setup");
        this.isFirst = true;

        // Set up the view buttons (header)
        var viewMenuModel = { visible: true, items: [ { template: 'outline/outline_header' } ] };			            
        this.controller.setupWidget(Mojo.Menu.viewMenu,
                                    {menuClass:'no-fade'},
                                    viewMenuModel);

        // Setting up scroll widget for notes dialog
        this.scrollModel = { scrollbars: false, mode: 'vertical' };

        this.controller.setupWidget('outlineScroll', {}, this.scrollModel);

        // Setting up the list widget for the outline
        this.outlineModel = { items:this.listArray };
        
        this.controller.setupWidget('OutlineList',
                                    {
                                      itemTemplate:'outline/listitem',
                                      listTemplate:'outline/listcontainer'
                                    },
                                    this.outlineModel);

        this.controller.get('OutlineList').observe(Mojo.Event.tap,
                this.listTapHandler.bindAsEventListener(this));

        // Setup the Filter Field
        var attr = { filterFieldName: 'name' };
        this.controller.setupWidget('filterField', attr, this.model = { disabled: false });
        Mojo.Event.listen( this.controller.get('filterField'), Mojo.Event.filter, this.filterHandler.bind(this) );

        this.controller.setupWidget(Mojo.Menu.appMenu,
                                    { omitDefaultItems: true },
                                    this.appMenuModel);

        this.controller.listen( this.controller.sceneElement, Mojo.Event.keydown,
                this.handleKeyDown.bindAsEventListener(this) );

    },

    handleKeyDown: function(event) {
    },

    handleCommand: function(event) {

        if (event.type == Mojo.Event.commandEnable) {
            if (event.command == Mojo.Menu.helpCmd) {
                event.stopPropagation();
            }
        }

        if (event.type == Mojo.Event.command) {
			try {
				if (event.command == Mojo.Menu.helpCmd) {

					this.controller.serviceRequest('palm://com.palm.applicationManager', {
						method: 'open',
						parameters: {
							id: 'com.palm.app.help',
							params: {
								target: "http://help.palm.com/pdf_view/index.html"
							}
						} 
					});
				}
			}
			catch (e) {
				Mojo.Log.logException(e);
			}
        }
    },

    /*
     * After getting the outline from the server this function is called.
     * The contents of the outline are contained in outlineArray 
     */
    buildOutline: function( outlineArray, filterFromKeyPress )
    {
        var bookmarkItems = [];

        // Clear the timeout and filter the entry
        if ( filterFromKeyPress ) {
            this.flagOutline( outlineArray );
        }

        // Check/uncheck the bookmark menu item
        this.documentAssistant.updateBookmarksMenuItem(outlineArray.length !== 0);

        if (outlineArray.length === 0) 
        {
            bookmarkItems.push( 
                { 
                  width: 24,
                  maxWidth: 210,
                  data: $L("( No outline data found )"), 
                  listitem: 1 
                }
            );

            return bookmarkItems;
        }

		var outlineCount = 0;
        for (var i = 0; i < outlineArray.length; i++) 
        {
            if (outlineArray[i].show) {

				outlineCount++;

                // Set our max-width
                var width = outlineArray[i].depth * 24 - 6;
                var max_width = 240 - width;

                bookmarkItems.push( 
                    { 
                      expanded: outlineArray[i].haschild ? "expanded" : "closed",
                      maxWidth: max_width,
                      width: width,
                      data: outlineArray[i].text, 
                      listitem: outlineArray[i].pagenumber 
                    }
                );

            }

			if (filterFromKeyPress) {
				this.controller.get('filterField').mojo.setCount( outlineCount );
			}
        }

        return bookmarkItems;
    },

    flagOutline: function ( outlineArray )
    {
        var user_text = this.outline_typetext.toUpperCase();
        var parent_depth = 0;
        var child_depth = 0;
        var i;

        // Find matches and flip show switch
        for (i = outlineArray.length - 1; i >= 0; i--)
        {
            if (outlineArray[i].text.toUpperCase().indexOf(user_text) != -1)
            {
                outlineArray[i].show = true;
                parent_depth = outlineArray[i].depth;
            }
            else
            {
                if (outlineArray[i].depth < parent_depth)
                {
                    outlineArray[i].show = true;
                    parent_depth--;
                }
                else
                {
                    outlineArray[i].show = false;
                }
            }
        }

        // Traverse the array one more time to update haschild data
        for (i = outlineArray.length - 1; i >= 0; i--)
        {
            if (outlineArray[i].show)
            {
                parent_depth = outlineArray[i].depth;

                if (outlineArray[i].haschild) {

                    if (child_depth < parent_depth) {
                        outlineArray[i].haschild = false;
                    }

                    child_depth = parent_depth;
                }
            }
            else
            {
                outlineArray[i].haschild = false;
            }
        }

    },


    listTapHandler: function(event) {
        //Mojo.Log.info("OutlineAssistant: listTapHandler");

        // Figure out which page they want to jump to
        var new_page = this.controller.get(event.target).readAttribute('x-app-page');

        this.documentAssistant.JumpToPage(new_page);

        this.controller.stageController.popScene();
    },

                    /*
    resetCheckmark: function ()
    {
        var row_id;
        var img_row_id;
        var row_element;
        var the_cells;
        var check_found = false;
        var close_page = this.check_page;
        var closed_element = '';
        var open_element = '';
        var i = 0;
        var check_row = 0;
        var check_rowid = ['img_row1'];

        // Clear the old check marks
        for (i = 0; i < this.check_rowid.length; i++) {
            this.controller.get(this.check_rowid[i]).src = '';
        }

        // Truncate the array
        this.check_rowid = this.check_rowid.splice(0, 0);

        // Must be coming from a followlink
        if (this.check_row !== 0) {
            img_row_id = 'img_row'+this.check_row;
            this.controller.get(img_row_id).src = 'images/checkmark.png';

            check_found = true;
        }
        else {
            for (i = 1; i <= this.outline_cnt; i++) {
                row_id = 'row'+i;

                row_element = this.controller.get(row_id);
                the_cells = row_element.cells;

                //Mojo.Log.info("row_id = %d", row_id);
                //Mojo.Log.info("nodeValue = '%s'",the_cells[1].firstChild.nodeValue);

                if (the_cells[1].firstChild.nodeValue == this.check_page) {
                    img_row_id = 'img_row'+i;
                    this.controller.get(img_row_id).src = 'images/checkmark.png';
                    check_found = true;
                    break;
                }
            }
        }

        // Couldn't find the page lets just find the closest page number
        while (!check_found) {
            close_page--;

            //for (i = 1; i <= this.outline_cnt && close_page > 0; i++)

            for (i = this.outline_cnt; i >= 1 && close_page > 0; i--) {
                row_id = 'row'+i;

                row_element = this.controller.get(row_id);
                the_cells = row_element.cells;

                //Mojo.Log.info("row_id = %d", row_id);
                //Mojo.Log.info("nodeValue = '%s'",the_cells[1].firstChild.nodeValue);
                //Mojo.Log.info("close_page = %d", close_page);

                if (the_cells[1].firstChild.nodeValue == close_page)
                {
                    img_row_id = 'img_row'+i;
                    this.controller.get(img_row_id).src = 'images/checkmark.png';
                    check_found = true;
                    break;
                }
            }
        }

        // Could not find a page... Just default to page 1
        if (!check_found)
        {
            img_row_id = 'img_row1';
            this.controller.get(img_row_id).src = 'images/checkmark.png';
            check_found = true;
        }

        this.check_rowid.push(img_row_id);

        // Always open the parents if the current page is a child and place the
        // gray check mark on each parent
        var loop_counter = 1;
        var loop_depth = undefined;
        var items_visible = 0;
        var openParents = [];

        var array_index = this.check_rowid[0].substring(7);

        //Mojo.Log.info("array_index = '%s'", array_index);

        this.documentAssistant.outlineCopy = this.documentAssistant.arrayCopy(this.documentAssistant.outlineArray);

        for (i = array_index - 1; i >= 0; i--) {
            //Mojo.Log.info("i = %d", i);
            //Mojo.Log.info("depth = %d", this.documentAssistant.outlineCopy[i].depth);
            //Mojo.Log.info("haschild = %d", this.documentAssistant.outlineCopy[i].haschild);

            // We are at the parent level
            if (this.documentAssistant.outlineCopy[i].depth == 1 &&
                (!this.documentAssistant.outlineCopy[i].haschild || loop_counter == 1)) {
                break;
            }

            if (this.documentAssistant.outlineCopy[i].haschild) {
                if (loop_counter > 1) {
                    if (this.documentAssistant.outlineCopy[i].depth < loop_depth ||
                        loop_depth === undefined) {
                        // Record the open parent
                        openParents.push(i);

                        // Recode the current loop depth
                        loop_depth = this.documentAssistant.outlineCopy[i].depth;

                        // Open this node
                        closed_element = 'closed'+(i+1);
                        open_element = 'open'+(i+1);

                        if (this.controller.get(closed_element)) {
                            this.controller.get(closed_element).style.display = 'none';
                        }

                        if (this.controller.get(open_element)) {
                            this.controller.get(open_element).style.display = '';
                        }

                        if (this.controller.get(closed_element) && this.controller.get(open_element)) {
                            Effect.SlideDown('list'+(i+1), { duration: 0 });
                        }

                        // Parent nodes get the gray check mark
                        img_row_id = 'img_row'+(i+1);
                        this.controller.get(img_row_id).src = 'images/checkmark-gray.png';
                        this.check_rowid.push(img_row_id);
                    }
                }
                else
                {
                    loop_depth = this.documentAssistant.outlineCopy[i].depth;
                }
            }

            loop_counter++;
        }

        // Figure out the nodes that are visible
        var array_depth = this.documentAssistant.outlineCopy[array_index - 1].depth;
        var follow_parent = false;
        var follow_child = false;
        var follow_depth = 1;
        var j = 0;

        openParents = openParents.reverse();

        //this.documentAssistant.printOutline(this.documentAssistant.outlineCopy);

        //Mojo.Log.info("array_index = %d", array_index);
        //Mojo.Log.info("array_depth = %d", array_depth);

        //for (i = 0; i < openParents.length; i++)
            ////Mojo.Log.info("openParents[%d] = %d", i, openParents[i]);

        // Depth is 1 so just count all of the depth 1 items
        if (array_depth == 1) {

            for (i = 0; i < this.documentAssistant.outlineCopy.length && i < array_index; i++) {

                if (this.documentAssistant.outlineCopy[i].depth == array_depth) {
                    items_visible++;
                }
            }
        }
        // Depth is greater than 1
        else {

            for (i = 0; i < this.documentAssistant.outlineCopy.length && i < array_index; i++) {

                //Mojo.Log.info("Working on i value = %d", i);
                //Mojo.Log.info("   follow_parent = %d", follow_parent);
                //Mojo.Log.info("   follow_child = %d", follow_child);
                //Mojo.Log.info("   follow_depth = %d", follow_depth);

                if (this.documentAssistant.outlineCopy[i].depth == 1) {

                    items_visible++;
                    //Mojo.Log.info("    items_visible(1) = %d", items_visible);

                    if (this.documentAssistant.outlineCopy[i].haschild) {

                        // first clear the flag
                        follow_parent = false;
                        follow_child = false;

                        // Check to see if this parent is in our list
                        for (j = 0; j < openParents.length && j < array_index; j++) {

                            // We found an open parent
                            if (openParents[j] == i) {

                                follow_parent = true;
                                follow_child = true;
                                follow_depth = this.documentAssistant.outlineCopy[i].depth + 1;

                                break;
                            }
                        }
                    }
                }
                else if (this.documentAssistant.outlineCopy[i].depth <= array_depth) {

                    if (follow_parent) {

                        if (this.documentAssistant.outlineCopy[i].haschild) {

                            if (follow_child ||
                                this.documentAssistant.outlineCopy[i].depth == follow_depth) {

                                follow_child = false;

                                // Check to see if this node is in our list
                                for (j = 0; j < openParents.length &&
                                            j < array_index; j++) {

                                    // We found an open parent
                                    if (openParents[j] == i) {

                                        follow_child = true;
                                        follow_depth = this.documentAssistant.outlineCopy[i].depth + 1;

                                        break;
                                    }
                                }

                                items_visible++;
                                //Mojo.Log.info("items_visible(2) = %d", items_visible);
                            }
                        }
                        else {

                            if (follow_child ||
                                this.documentAssistant.outlineCopy[i].depth == follow_depth) {

                                items_visible++;
                                //Mojo.Log.info("items_visible(3) = %d", items_visible);
                            }
                        }
                    }
                }
            }
        }

        //Mojo.Log.info("items_visible = %d", items_visible);

        // Auto scroll to the element
        if (array_index > 5) {

            var y_scroll = (parseInt(items_visible, 10) - 2) * -65;

            this.controller.get('outlineScroll').mojo.scrollTo(0, y_scroll, true);
        }
    },
    */

    activate: function() {
        //Mojo.Log.info("OutlineAssistant: activate\n");

        this.check_page = this.documentAssistant.currentpage;
    },

    filterHandler: function(event) {
        //Mojo.Log.info("OutlineAssistant: filterHandler");
        //Mojo.Log.info("text: '%s'", event.filterString);

        if (event.filterString.length > 0)
        {
            this.controller.setMenuVisible(Mojo.Menu.viewMenu, false);
        }
        else
        {
            this.controller.setMenuVisible(Mojo.Menu.viewMenu, true);
        }

        this.outline_typetext = event.filterString;
        this.outlineModel.items = this.buildOutline( this.outlineFromServer, true);
        this.controller.modelChanged(this.outlineModel);
    },

    ready: function() 
    {
        //this.resetCheckmark();
    },

    cleanup: function() {
        //Mojo.Log.info("OutlineAssistant: cleanup");
    },

    deactivate: function() {
    },

    appMenuModel: { label: $L('PDF View'),
		items: [
			{ label:$L('Help'), command:Mojo.Menu.helpCmd, checkEnabled:true }
		] 
	}
});
