function mlcSearchError(location, errMsg){
	jQuery(document).ready(function(){
		jQuery("html").append("<!-- mlc_ajax_error: " + location + " - " + errMsg + "-->");

        jQuery("#searchprogress").css("background","");
        jQuery("#navcontainer").html("");
        jQuery("#resultcontainer").html("An error has occurred. Please try again later.");
	});
	return false;
}

function mlcSearch(p) {
    this.path = p;
    this.query = "";
    this.resultscount = 0;
    this.pagenum = 1;
    this.pagesize = 0;
    this.pagecount = 0;
    this.results = "";
    this.didyoumean = [];
    this.featured = "";
    this.nav = "";
    this.navitem = "";
    this.navigators = "";
    this.defaultnavigator = "";
	this.lastEvent = null;

    this.executeSiteSearch = function() {

        // capture the params from the address
        if (jQuery.address.parameter("q"))
            this.query = unescape(jQuery.address.parameter("q"));
            jQuery("#q").val(this.query);

        if (jQuery.address.parameter("p"))
            this.pagenum = unescape(jQuery.address.parameter("p"));

        if (jQuery.address.parameter("n"))
            this.nav = unescape(jQuery.address.parameter("n"));

        if (jQuery.address.parameter("ni"))
            this.navitem = unescape(jQuery.address.parameter("ni"));

        if (this.query && jQuery("#resultcontainer").length) {

            var jsonHref = "/vgn-webapi/services/search/mlc/" + this.path
                    + "?query=" + this.query + "&pagenum=" + this.pagenum
                    + "&nav=" + this.nav + "&navitem=" + this.navitem
                    + "&mode=sitesearch&callback=?";

		    // set the progress indicator and grey out the results
            jQuery("#searchprogress").css("background", "url(\"/vgn-ext-templating/mlc/images/jquery/ui-anim_basic_16x16.gif\")");
		    jQuery("#searchcontainer").fadeTo(50, "0.5");

            jQuery.jsonp({
                url: jsonHref,
                timeout: 30000,
                error: function(xOptions, textStatus) {
                    return mlcSearchError("search", textStatus);
                },
                success: function(data) {
                    //alert("data = " + JSON.stringify(data));
                    if(data.error) {return mlcSearchError("search", data.error)}

                    search.resultscount = parseInt(data.resultscount);
                    search.pagenum = parseInt(data.pagenum);
                    search.pagesize = parseInt(data.pagesize);
                    search.pagecount = Math.ceil(search.resultscount/search.pagesize);
                    search.results = data.results;
                    search.didyoumean = data.didyoumean;
                    search.featured = data.featured;
                    search.navigators = data.navigators;
                    search.defaultnavigator = data.defaultnavigator;

                    // only need to render the navigator html on page 1 or if we came in from a bookmark etc
                    if (search.pagenum == 1 || !jQuery("#navcontainer").html()) renderNavigator();                    

                    // render the page of results
                    renderResults();
			
			        // turn off the progress indicator and show results
                    jQuery("#searchprogress").css("background","");
			        jQuery("#searchcontainer").fadeTo(50, "1");
                    jQuery("#advancedsearchsub").blur();
                }
            });

        } else {
            jQuery(document).ready(function(){
                jQuery("#resultcontainer").html("Please enter your search terms..");
            });
        }
    }

}

function prepareSearch(path) {

    // this global will be updated and used by all search functions
    search = new mlcSearch(path)

    // setup the click event for the search submission
    jQuery("#advancedsearchsub").button().click(function() {
        // do the search and render results
        jQuery("#search2").submit();
    });

    jQuery("#q").autocomplete({
        source: "/vgn-webapi/services/search/mlc/" + path + "?mode=autocomplete&callback=?",
        minLength: 3,
        delay: 500,
        select: function(event, ui) {
            event.preventDefault();

            // set the value in the field - if we just call submit here and a selection is made with the mouse,
            // the form submits before the field is updated, so we update and then submit here.
            jQuery("#q").val(ui.item.value);
            jQuery("#search2").submit();
        }
    });

    // execute ajax search rather than normal submit
    jQuery("#search2").submit(function(event) {
        event.preventDefault();
        // capture the current query value from the form
        search.query = jQuery("#q").val();
        search.pagenum = 1;
        search.nav = "";
        search.navitem = "";

		// set the address hash for backbutton support
        jQuery.address.parameter("q", escape(search.query));
        jQuery.address.parameter("p", escape(search.pagenum));
        jQuery.address.parameter("n", escape(search.nav));
        jQuery.address.parameter("ni", escape(search.navitem));

        // this triggers the address.change function which executes the search
        jQuery.address.update();

    });

    // setup the pagination links
    jQuery(".gopage").live("click", function(event) {
        event.preventDefault();
        search.pagenum = jQuery(this).attr("page");
		
		jQuery.address.parameter("p", escape(search.pagenum));
        jQuery.address.parameter("n", escape(search.nav));
        jQuery.address.parameter("ni", escape(search.navitem));

        // this triggers the address.change function which executes the search
        jQuery.address.update();

    })

    // setup the navigator links
    jQuery(".gonav").live("click", function(event) {
        event.preventDefault();
        search.pagenum = 1;

        // special case for when 'All Results' is clicked
        if (jQuery(this).hasClass("gonavall")) {
            search.nav = "all";
            search.navitem = "";

        } else {

            var nav;
            if (jQuery(this).attr("nav")) {
                nav = jQuery(this).attr("nav");
            } else {
                nav = "";
            }
            search.nav = unescape(nav);

            var navitem;
            if (jQuery(this).attr("navitem")) {
                navitem = jQuery(this).attr("navitem");
            } else {
                navitem = "";
            }
            search.navitem = unescape(navitem);
        }

		jQuery.address.parameter("p", 1);
        jQuery.address.parameter("n", escape(search.nav));
        jQuery.address.parameter("ni", escape(search.navitem));

        // this triggers the address.change function which executes the search
        jQuery.address.update();

    })

    // setup the did you mean link
    jQuery("#didyoumean, .popularsearches").live("click", function(event) {
        event.preventDefault();
        var newsearch = jQuery(this).html()
        jQuery("#q").val(newsearch);
        jQuery("#search2").submit();
    })

    // when the page loads, grab the # attributes and execute a search
    jQuery.address.init(function(event) {
        search.executeSiteSearch();
	
	}).change(function(event) {
        // for some reason internal change is firing twice in some cases..
		// do the search and render only if the event parameters have changed since last event.
		var match = false;		
		try {
			match = (unescape(search.lastEvent.queryString) == unescape(event.queryString));
			//alert("event " + event.queryString);
			//alert("lastevent " + search.lastEvent.queryString);
		} catch (e){}

		//alert(match);

		if (search.lastEvent == null || !match) {
			search.lastEvent = event;
			search.executeSiteSearch();
		}	

    // turning off autoupdate as we quite often update multiple values, and will call address.update at each point
    }).autoUpdate(false);

}

// this function is separate to renderNavigator as it may be called independently in the future
function updateNavigator() {

    // collapse all navs (each top level .gonav anchor has sibling ul containing subnav.)
    jQuery("a.gonav + ul").hide();

    // turn off all highlights
    jQuery(".gonav").removeClass("active");

    // expand current nav
    jQuery(".gonav[nav='" +search.nav+ "'] + ul").show();

    // highlight the current nav or navitem
    if ((!search.nav && !search.navitem) || search.nav == 'all') {
        jQuery(".gonavall").addClass("active");

    } else if (!search.navitem) {
        jQuery(".gonav[nav='" + search.nav + "'][navlevel='1']").addClass("active");

    } else{
        jQuery(".gonav[nav='" + search.nav + "'][navitem='" + search.navitem + "']").addClass("active");
    }
}

function sortNavigators(a,b){
     return a.displayname > b.displayname ? 1 : -1;
}

function sortNavitems(a,b){
     return a.name > b.name ? 1 : -1;
}

function renderNavigator() {
    var navHtml = "";

    navHtml += "<h3>Refine results</h3>";

	if (search.navigators.length > 1) {
    	navHtml += "<ul class=\"navigator1\"><li><a class=\"page gonav gonavall\">All Results</a></li>";
	}

    // sort the navigators
    search.navigators = jQuery(search.navigators).sort(sortNavigators);

    jQuery.each(search.navigators, function(i, navigator) {
        navHtml += "<li><a nav=\"" + navigator.name + "\" class=\"page gonav\" navlevel=\"1\">" + navigator.displayname + "</a> (" + navigator.count + ")";

        if (navigator.items.length) {
            navHtml += "<ul class=\"navigator2\">";

            // sort the navitems
            navigator.items = jQuery(navigator.items).sort(sortNavitems);

            jQuery.each(navigator.items, function(j, item) {
                 navHtml += "<li><a nav=\"" + navigator.name + "\" navitem=\"" + item.name + "\" class=\"page gonav\">" +
                         item.name + "</a> (" + item.count + ")" + "</li>";
            });
            navHtml += "</ul>";
        }

         navHtml += "</li>";
    });

    navHtml += "</ul>"

    jQuery(document).ready(function(){
        jQuery("#navcontainer").html(navHtml);
        // setup the default navigator if it exists.
        if (!search.nav) {
                search.nav = search.defaultnavigator; 
        }

	    //update navigator highlight/expansions
        updateNavigator();

        // render the popular searches - note that fullChannelPath is set as a global by the searchResults.jsp
        jQuery("#navcontainer").append("<div id=\"popularsearchestitle\"><h3>Popular searches</h3><div id=\"popularsearches\"></div></div>");
        mlcRenderArticleBody(fullChannelPath, 'Popular searches', "popularsearches", false);
    });
}


function renderResults() {

    var resultHtml = "";
    var pagingHtml = "";
    var didyoumeanHtml = "";
    var featuredHtml = "";

    var activeNavHtml = jQuery(".gonav.active").parentsUntil("ul.navigator1").last().find("a[navlevel=1]").html();
	var activeNavItemHtml = jQuery(".gonav.active[navitem]").html();
    
    didyoumeanHtml += "<div id=\"didyoumeantext\">You searched for <strong>" + search.query + "</strong>";
    if (activeNavHtml != null && activeNavHtml.length > 0) {
        didyoumeanHtml += " in area '" + activeNavHtml;
		if (activeNavItemHtml != null) {
			didyoumeanHtml += " &gt; " + activeNavItemHtml;
		}
		didyoumeanHtml += "'";
    }
	didyoumeanHtml += ".";

    if (search.didyoumean!=undefined && search.didyoumean.length > 0) {
        didyoumeanHtml += " Did you mean \"<a id=\"didyoumean\">" + search.didyoumean[0] + "</a>\"?</div>";
    }
    didyoumeanHtml += "</div>";

    if (search.featured && search.pagenum == 1)
        featuredHtml = "<div id=\"searchfeatured\">" + search.featured + "</div>";

    // if no results..
    if (!search.results.length > 0 || search.query=="noresult") {
        resultHtml += "<p>Your request returned no results. Please change your filter criteria and try again.</p>";

    // otherwise render the results
    } else {

        // work out the range or results we are displaying
        var start = search.pagenum == 1 ? 1 : (search.pagesize * (search.pagenum -1)) + 1;
        var end = search.pagenum != search.pagecount && (start + search.pagesize < search.resultscount)
                ? (start + search.pagesize - 1)
                : start + (search.pagesize - 1 - (search.pagesize - (search.resultscount % search.pagesize)));

        // work out the page ranges available for navigation
        var pagingWindowSize = 10;
        var pageStart = search.pagenum < (pagingWindowSize + 1) ? 1 : search.pagenum - (search.pagenum % pagingWindowSize) + 1;
        var pageEnd = pageStart + (pagingWindowSize-1);

        // adjust for when last page in each range is current
        if (search.pagenum > pagingWindowSize && search.pagenum % pagingWindowSize == 0) {
            pageStart = pageStart-pagingWindowSize;
            pageEnd = pageEnd-pagingWindowSize;
        }

        // adjust the last page end
        pageEnd = pageEnd > search.pagecount ? search.pagecount : pageEnd;

        // build the paging html
        pagingHtml += "<div class=\"resultpaging\">";
        pagingHtml += "<p>Showing " + start + " - " + end + " of " + search.resultscount + " results</p>";
        pagingHtml += "<ul class=\"navh\">";

        // previous link
        if (search.pagenum > 1 && search.pagecount > 1) {
            pagingHtml += "<li>";
            pagingHtml += "<a page=\""+ (search.pagenum - 1) + "\" class=\"gopage\"> &lt;&nbsp;Prev</a> ";
            pagingHtml += "</li>";
        }

        // paging links
        for (j=pageStart;j<=pageEnd;j++) {
            pagingHtml += "<li>";
            var pageClass = j == search.pagenum ? "page on" : "page";
            pagingHtml += "<a page=\""+ j + "\" class=\""+ pageClass + " gopage\"> " + j + "</a> ";
            pagingHtml += "</li>";
        }

        // more link
        if (pageEnd < search.pagecount) {
            pagingHtml += "<li>";
            pagingHtml += "<a page=\""+ (pageEnd + 1) + "\" class=\"gopage\"> More </a> ";
            pagingHtml += "</li>";
        }

        // next link
        if (search.pagenum < search.pagecount) {
            pagingHtml += "<li>";
            pagingHtml += "<a page=\""+ (search.pagenum + 1) + "\" class=\"gopage\"> Next&nbsp;&gt;</a> ";
            pagingHtml += "</li>";
        }
        pagingHtml += "</ul></div>"

        // build the results
        resultHtml += "<ol start=\"" + start + "\" class=\"searchresults\">";

        jQuery.each(search.results, function(i, result) {
			
			// format the url for display
            var url = result.url.replace(/^.*:\/\/[^\/]*/g, "").replace(/\/mlc\/im_considering_mlc|\/mlc\/im_with_mlc|\/wps\/wcm/, "");

            resultHtml += "<li>";
            resultHtml += "<a href=\"" + result.url + "\">";
            resultHtml += result.title;
            resultHtml += "</a>";
            resultHtml += "<br/>" + result.body + "<br/>";
            resultHtml += "<a class=\"page\" href=\"" + result.url + "\">" + url + "</a>";
            resultHtml += "</li>";

        });

        resultHtml += "</ol>";
    }

    resultHtml += "</div>";

    jQuery(document).ready(function(){
        jQuery("#resultcontainer").html(didyoumeanHtml + pagingHtml + featuredHtml + resultHtml + pagingHtml);
    });

}





