<!--
/*
 * Converts a string to proper / title case
 * 
 * @param str is the string to be converted
 * @return string converted to title case 
 */
function toTitleCase(str) {
    return str.replace(/\w\S*/g, function(txt){return txt.charAt(0).toUpperCase() + txt.substr(1).toLowerCase();});
}

/*
 * Sets the active step to the value passed in the step parameter
 *
 * @param step is the numerical value of the step you want to set
 * @return nothing
 */
function set_active_step (step) {
  $(".step").removeClass("active");
  $("#steps ol li:nth-child("+step+")").addClass("active");
} // end set_active_step function


/*
 * Sets the text/html in an arbitrary step based on the values passed in 
 *
 * @param step is the numerical value of the step you want to set
 * @param txt the text you want to appear after the step
 * @return nothing
 */
function set_step_text (step, txt) {
  //$(".step").removeClass("active");
  $("#steps ol li:nth-child("+step+")").html("<span class='num'>"+step+"</span> "+txt);
  
} // end set_active_step function


/*
 * Simple function to handle error data that comes back from an AJAX script
 *
 * @param e is the error data
 * @return nothing
 */
function handle_error(e) {
    
    if(e == "reset") {
      if($("#messages").children().length) { // there's something to actually empty out
        $("#messages").empty().hide(); 
        //$(".working").removeClass("working");
        
      }
    } else {
      $("#messages").empty().append("<p class='"+e.val.type+"'>"+e.val.message+"</p>").slideDown();
      //$(".working").removeClass("working");
      $("#results").empty(); 
    }
    
} // end handle_error()



/*
 * Goes through the select/option dropdown elements and handles hiding & 
 * showing of them
 * 
 */
function clean_options() {                         
  
  set_triggers(); // this could probably be run in a more appropriate place (?)
  
  $("select").each(function() {
  
    var hashval   = $.bbq.getState($(this).attr("id")) || ''; // look for a hashval that coresponds to the current select box
    var selected  = +$(this).find(":selected").val()   || ''; // !make sure to use unary plus operator here or it will evaluate a "0" as a string
    var formitem  = $(this).parent().parent();
    
    // if there's a hashvalue that corresponds to a dropdown 
    // then the selected option should match the hash
    if (hashval && (selected == '' || !selected)) {   
      $(this).find("option").each(function() { 
        if($(this).val() == hashval) {
          $(this).attr('selected', 'selected');
        } 
      });        
    }

    // if there is NOT a hashvalue, and there's an unselected
    // dropdown, then hide it    
    else if(!selected && $(this).children().length < 2 /* && !window.location.hash */) {
      formitem.hide();
    }
    
    // if there's a hash value, and the selected option is equal
    // to that hashval, make sure it's visible
    else if(hashval && selected == hashval) {
      formitem.show(); 
    } 

  });
} // end clean_options()



/*
 * Make sure the form elements have the appropriate event triggers
 * 
 * @return   nothing, but probably should return some data indicating what 
 *           triggers were set.
 */
function set_triggers() {

  // "by model" search
  $('#make').change(function() {    
    if($(this).siblings("strong").hasClass("working") == false) { 
      $(this).siblings("strong").addClass("working");
    }
    $.bbq.pushState("#make="+$(this).val(), 2);
  });
  $('#model').change(function() {    
    if($(this).siblings("strong").hasClass("working") == false) {   $(this).siblings("strong").addClass("working"); }
    $.bbq.pushState("model="+$(this).val(), 0); 
  });    
  
  // "by dimension" search
  $('#width').change(function() {    
    if($(this).siblings("strong").hasClass("working") == false) {   $(this).siblings("strong").addClass("working"); }
    $.bbq.pushState("#width="+$(this).val(), 2);
  });
  $('#length').change(function() {    
    if($(this).siblings("strong").hasClass("working") == false) {   $(this).siblings("strong").addClass("working"); }
    $.bbq.pushState("length="+$(this).val(), 0); 
  });
  $('#height').change(function() {
    if($(this).siblings("strong").hasClass("working") == false) {   $(this).siblings("strong").addClass("working"); }
    $.bbq.pushState("height="+$(this).val(), 0); 
  });
  
} // end set_triggers()



var frameNames = new Array()
        frameNames[23] = {'name': "Round Tube", 'anchor': 'standard'};
        frameNames[31] = {'name': "Square Tube", 'anchor': 'square'};
        frameNames[32] = {'name': "Stainless Round Tube", 'anchor': 'standard'};
        frameNames[47] = {'name': "Super Sport", 'anchor': 'sport'};
        frameNames[44] = {'name': "Buggy-style Square Tube", 'anchor': 'buggy'};
/*
 * Converts result-data from JSON into HTML 
 *
 * @param type is the type of result-data (bimini, boat cover, etc.)
 * @param data JSON product data
 * @return HTML string representing the JSON data
 */
function get_results(type, select, data) {

  
  var results = "";
  var url;
  
  if(type == "bimini") {
    if(select == "model") {
      //alert(data["results"][0].val.brand);
      var is_carver = data["brand"] == 'carver';
      //var is_westland = data["results"][0].val.brand == 'westland';
    
      // start assembling the HTML for a results table with link(s) to the fabirc / frame page
      results   = "<strong>Select your boat below</strong>";
      
      // table headers
      if(is_carver) { // carver
        results   += "<table><tr><th>Frame</th><th></th></tr>"
      } else {
        results   += "<table><tr><th>Model</th><th>Year</th><th></th></tr>"
      }
      
      for(i=0; i < data["results"].length; i++)  { 
      
        if(is_carver) { // carver
          //Assemble the URL. Redirect to square frame page if necessary
          if(data["results"][i].val.productTypeID == 31) url = base_path+'covers/bimini/carver-squaredetail.php';
          else url = base_path+'covers/bimini/carver-biminidetail.php';
          url += '?manufacturerID='+data["results"][i].val.manufacturerID+'&modelID='+data["results"][i].val.modelID+'&orderNo='+data["results"][i].val.bimini_partnum;
          results += '<tr><td>'+frameNames[data["results"][i].val.productTypeID]['name']+' <a href="glossary.php#'+frameNames[data["results"][i].val.productTypeID]['anchor']+'">(?)</a></td></td><td><a class="link-button right" title="Choose this product and proceed to select fabric and frame type" href="'+url+'">Select Frame</a></td></tr>';          
        }
        else { // westland 
          // sample westland url = /covers/bimini/part-number/3681
          results += '<tr><td>'+data["results"][i].name+'</td><td>'+data["results"][i].val.year+'</td><td><a class="link-button right" title="Choose this product and proceed to select a material and color" href="'+base_path+'covers/bimini/part-number/'+data["results"][i].val.bimini_partnum+'">Select this Model</a></td></tr>';
        }
      }
      results         += "</table>";
    }

    else if(select == "dimensions"){
      
      // start assembling the HTML for a results table with link(s) to the fabirc / frame page
      results   = "<strong>Select a height and frame type below</strong><table><tr><th>Height</th><th>Frame</th><th></th></tr>"
      for(var i in data['results']) { 
        
	var nugget = data['results'][i];

        //Assemble the URL. Redirect to square frame page if necessary
        if(nugget.productTypeID == 31) url = base_path+'covers/bimini/carver-squaredetail.php';
        else url = base_path+'covers/bimini/carver-biminidetail.php';
        url += '?productTypeID='+nugget.productTypeID+'&bows='+nugget.bows+'&widths='+nugget.widths+'&height='+nugget.height+'&length='+nugget.length+'&orderNo='+nugget.orderNo;

      // remember to set the anchor tag HTML to the correct IDs
        frame_name = 'Standard';
        frame_anchor = 'standard';
        if(frameNames[nugget.productTypeID] != undefined) {
          frame_name = frameNames[nugget.productTypeID]['name'];
          frame_anchor = frameNames[nugget.productTypeID]['anchor']
        }
        results += '<tr><td>'+nugget.height+'"</td><td>'+frame_name+' <a href="glossary.php#'+frame_anchor+'">(?)</a></td></td><td><a class="link-button right" title="Choose this product and proceed to select fabric and frame type" href="'+url+'">Select Frame</a></td></tr>';
      }
      results         += "</table>";
    }
  }
  else if(type == "covers") {

    results   = "<strong>Select your boat below</strong>"

    if ( data["brand"] == 'westland' ) {
      // start assembling the HTML for a results table with link(s) to the material
      results   += "<table><tr><th>Model (Year)</th><th></th></tr>"

      for(i=0; i < data["results"].length; i++)  {
        // remember to set the anchor tag HTML to the correct IDs
        results += '<tr><td>'+data["results"][i].name+'</td><td><form method="POST" action="'+base_path+'covers/boat/boatdetail.php"><input type="hidden" name="REFNUM" value="'+data["results"][i].val.refno+'" /><input class="link-button right" type="submit" value="Select This Model" /></form></td></tr>';
      }
    }
    else {
 	    // start assembling the HTML for a results table with link(s) to the material
      results   += "<table><tr><th>Model</th><th>Year</th><th></th></tr>"
      for(i=0; i < data["results"].length; i++)  {
        // remember to set the anchor tag HTML to the correct IDs
        results += '<tr><td>'+data["results"][i].name+'</td><td>'+data["results"][i].val.year+'</td><td><a class="link-button right" title="Choose this product and proceed to select a material and color" href="'+base_path+'covers/boat/carver/'+$("#make").val()+'/'+data["results"][i].val.id+'">Select this Model</a></td></tr>';
      }
    }

    results         += "</table>";

  }

  return results;

} // end get_results()


/*
 * Processes an AJAX requests by sending variables to a script and accepting
 * JSON.   The JSON can come back in a couple flavors -- as options, results,
 * or an error message.  The options are used to populate select menu drop-
 * downs and results are sent to another function to be output (usually as a
 * table of data.
 *
 * @param ajax_script  the name of the script that will receive the query and 
 *                     that returns the set of results or errors
 * @param var_string   data formatted as a URL query string that is sent to the ajax script
 * @param e            the element that returned data is to be inserted into
 * @return             0 or 1 indicating success of execution
 */
function process_ajax(ajax_script, var_string, e, callback) {
  
  var form_item =  e.parent().parent();
  
  $.ajax({
    type: "POST",
    async: false,
    url: base_path+"ajax/"+ajax_script,
    dataType: 'json',
    data: var_string,
    timeout: (99000),
    success: function(data) {
    
      // catch no-data, null, and network errors
      if(!data || data == "Internal Server Error" || data == '' || data == null) { 
        $("messages").empty().append("<p class='error'>Whoa, sorry.  Something went really haywire while communicating with the server.  Please try again, and if this message keeps popping up, let us know.</p>");
      }
      
      // otherwise, we can assume some real data is returned as JSON
      else {

        //if("results" in data) console.log("results");
        //if("options" in data) console.log("options");
        //if("message" in data) console.log("message");
        
        handle_error("reset");  // if there was already an error, this will reset and hide the container
        
        // it's also possible that error messages are being returned in the 
        // same name/val format if that's what we got back, then display them 
        // to the screen
        if("message" in data) { // data[var_name][0].name == "message") { 
            handle_error(data["message"][0]);
            return 0;
        } 

        // if a mfg and model have been supplied, and the AJAX request returns results
        else if ("results" in data) {
            var results = get_results(data['type'], data['select'], data);
            // empty the old results and then append the new results and expose the container
            if($("#results").children().length) { // if there's already a result set, animate it
             $("#results").slideUp(300).delay(500).empty().append(results).slideDown(300).children().show();
            } else {
             $("#results").empty().append(results).children().show();
            }
           
            
            //$("#results").empty().append(results).children().show();
           
           // make the table rows clickable and hovery
            $("#results a").each(function(){
              var loc = $(this).attr("href");
              $(this).parent().parent().click(function() {
                window.location = loc; 
              }).hover( // this is because IE doesn't recognize hover state for table rows
                function () {
                  $(this).find("td").addClass("hover");
                },
                function () {
                  $(this).find("td").removeClass("hover");
                }
              );
            });
            callback(e);

        } // end if (results)
        
        // if var_name is something else, then we're still configuring the search and populating drop-down select boxes
        else {

            // empty the current dropdown box in preparation for the new data
            e.empty().append('<option value="">Make a selection</option>');
            var new_options = "";
            
            // loop through the data and assemble the HTML necesssary for the options
            for(i=0; i < data["options"].length; i++) {
              var hashval = $.bbq.getState(e.attr("id"));
              var selected = (data["options"][i].val == hashval) ? 'selected="selected"' : "";
              new_options += '<option '+selected+' value="'+data["options"][i].val+'">'+data["options"][i].name+'</option>';
            }
            
            // append those options to the select box element passed into the function
            e.append(new_options); 
            
            // unhide the element containing the newly assembled select box
            form_item.show().children().slideDown("slow");
            callback(e);
            return 1; // very very important!
        } // end else (populating select boxes)
      } // end else (data returned successfully)
    }, // end success
    error:function (xhr, ajaxOptions, thrownError) {
      handle_error("There was an error of type: " + thrownError + ".  We're not proud of this, but, please report this to someone so we can fix it ASAP.  Thanks.");
      //$(".working").removeClass("working");
      return 0;
    },
    complete:function(jqXHR, textStatus) {
      
      if(textStatus == "timeout") {
        handle_error("It looks like the request timed out (took longer than it was supposed to).  This can happen sometimes.  Please try again, and if the problem continues, let us know.");
        return 0;
      }
      
      return 1;
      
    }
  });
  
  //return 1;
} // end process_ajax()






$(document).ready(function(){
  
  //var console = window['console'];

  // this is for proper functioning of the dropdown menus in IE7
  $('li.head').hover(
			function() { $('ul', this).css({display: 'block', position: 'absolute', left: '0px', backgroundColor: 'red'}); },
			function() { $('ul', this).css('display', 'none'); }
    );
  
  
  
  // -------------------------------------------------------------
  // Selection Process for Boats and Bimini's
  // -------------------------------------------------------------
  if($('.boat-covers').length > 0 || $('.bimini-tops').length) { // don't want this block processed on every page
    
    $("#submit").hide();    // we could just get rid of the submit button.  But we might one day want to have an actual form submit fallback.
    clean_options();
          
    var brand = "";
    if(window.location.search.indexOf("westland") > 0) { brand = "westland" }
    if(window.location.search.indexOf("carver") > 0) { brand = "carver" }
    
    var type = $('.bimini-tops').length ? "bimini" : "covers"; //(window.location.pathname.indexOf("bimini") > 0) ? "bimini" : "covers"; // works for now
    // type = (window.location.pathname.indexOf("covers") && window.location.pathname.indexOf("boat")) ? "covers" : '';    
    var search_type = (window.location.pathname.indexOf("dimension") > 0) ? "dimension" : "model"; // works for now
    // search_type = (window.location.pathname.indexOf("model")) ? "model" : "dimension";    

    if(brand) {
      $("label").removeClass("selected");
      $("."+brand+" label").toggleClass("selected");
      set_active_step(2);
      set_step_text(1, toTitleCase(brand));
      $('form h3, .form-container h2').scrollToViewPort(800);
    }
    
    var hashes = new Array();
    hashes["make"] = $.bbq.getState("make") || '';
    hashes["model"] = $.bbq.getState("model") || '';
    hashes["width"] = $.bbq.getState("width") || '';
    hashes["length"] = $.bbq.getState("length") || '';
    hashes["height"] = $.bbq.getState("height") || '';    

    // bind an event to the hashchange so that when the 
    // hash values are updated, other events can be triggered
    $(window).bind( 'hashchange', function(e) {
    
      var results = $("#results");
      $('#messages').insertAfter(results);
      
      clean_options();

      hashes["make"]    = $.bbq.getState("make")   || '';
      hashes["model"]   = $.bbq.getState("model")  || '';
      hashes["width"]   = $.bbq.getState("width")  || '';
      hashes["length"]  = $.bbq.getState("length") || '';
      hashes["height"]  = $.bbq.getState("height") || '';


      // use the brand name and type of search to determine the most 
      // appropriate ajax script.  If we wanted to slam all the AJAX
      // handling into one big script, we could do away with this
      var ajax_script = brand+"-"+type+".php"; 
      
      // handle the "by dimension" search sequence of options
      // since each step has a requisite preliminary step,
      // the sequece is fully nested
      if(search_type == "dimension") {
      
        if(hashes['width']) {
        
          var next_step_element = $("#length");
          var var_string = "width="+hashes["width"];
       
          process_ajax(ajax_script, var_string, next_step_element, function(e) {
            
            set_active_step(3);
            set_step_text(2, "W = "+$("#width :selected").text());
            clean_options();
            e.show();
            $(".working").removeClass("working");
            
          });
          
            // there's a width and a length in the hash
            if(hashes['length']) {
            
              var next_step_element = $("#height");
              var var_string = "width="+hashes['width']+"&length="+hashes['length'];
              
              process_ajax(ajax_script, var_string, next_step_element, function(e){
              
                set_active_step(4);
                set_step_text(3, "L = "+$("#length :selected").text());
                clean_options();
                e.show();
                $(".working").removeClass("working");
                
                // if there's a width, length, and height
                if(hashes['height']) {
                  set_step_text(4, "H = "+$("#height :selected").text());
                  $('#submit').show().children().show();
                } // end if height 
              
              
              }); // end processing of length
            } // end if length
        } // end if width
      } // end dimensional search cascade
      
      
      // handle the "by model" search sequence
      else if(search_type == "model") {
       

       
        // the make has been specified
        if(hashes['make']) {
          
          var nse = $("#model"); // next step element
          var var_string = "make="+hashes["make"];
          
          
          process_ajax(ajax_script, var_string, nse, function(e) {
           
            set_active_step(3);
            clean_options();
            e.show();
            $(".working").removeClass("working");
            
          });  
          
          
          // nested so such that this implies both make and model are known
          if(hashes['model']) { 
            var nse = $("");
            var var_string = "make="+hashes['make']+"&model="+hashes['model'];
            
            
            process_ajax(ajax_script, var_string, nse, function(e) { 
              set_active_step(4);
              clean_options();
              e.show();
              $(".working").removeClass("working");
              
              // if there's a width, length, and height
              if(hashes['year']) {
                $('#submit').show().children().show();
              } // end if height 
            
            });
           
          } // end if model          
        } // end if make
      } // end dimensional search cascade
      
      clean_options();

    });
   
   
    $("#brands label").click(function() { // a brand is clicked on
        var brand = $(this).text().toLowerCase();
        window.location.href = "?brand=" + brand; // we don't want to bbq this
    }); // end click on brand

  } // end if this is a boat cover page
  
  
  // ---------------------------------------------------------------
  // Carver material and cover pages 
  // ---------------------------------------------------------------
  if($('#fabric-fit-colors').length > 0) { 
    
   
    var two_str = $("#steps ol li:nth-child(2)").text();
    two_str = two_str.substring(2, two_str.length);
    var three_str = $("#steps ol li:nth-child(3)").text();
    three_str = three_str.substring(2, three_str.length);
    
    set_step_text(2, toTitleCase(two_str));
    set_step_text(3, toTitleCase(three_str));
    
    $("#fabric-fit-colors input[type=submit]").hide();
    $("#fabric-fit-colors .color").each(function() {
      if($(this).find("select").length < 1) {
        $(this).siblings("input[type=submit]").show();
      }
    });
   
      function handle_colors(e) {
      
        var selected = e.find(":selected");
        var target = e.parents(".color");
        var swatch_val = selected.val();
        var color_val = selected.attr("title"); 

        if(swatch_val) {
          target.parents("form").children("input[type=submit]").show();
        } else {
          target.parents("form").children("input[type=submit]").hide();
        }
        target.children(".swatch").css("backgroundColor", color_val); 
      }
      
      
      
      $("#fabric-fit-colors .swatch").click(function(){
        var target = $(this).parent();
        var swatch_menu =  $("<div class='swatch-options'></div>");
        target.find("select option").each(function(){
          var option = $(this);
          var swatch = $("<span class='swatch' style='background: "+$(this).attr("title")+"'></span>").click(function() {
            option.attr("selected", "selected");
            $(".swatch-options").remove();
            handle_colors(option.parent());
          });
          swatch_menu.append(swatch);
          target.append(swatch_menu);
        });
      });
      
      $("#fabric-fit-colors select").change(function() {
        handle_colors($(this));
      });
      
      
      
      
      
    
    }
    
    
    
    
    $("#fabric-fit-colors tbody th").each(function(){ 
      var text = $(this).find("small").text();
      $(this).qtip({
       content: text,
       show: 'mouseover',
       hide: 'mouseout',
       position: {
        target: $(this)
       },
       style: { 
          width: 400,
          padding: 5,
          border: {
             width: 7,
             radius: 5
          },
          name: 'green' // Inherit the rest of the attributes from the preset dark style
       }
      });
    });
    
    $("#fabric-fit-colors tr td").each(function(){
      //var row_index   = $(this).parent().index()+1;
      var row_targets  = $(this).siblings("td");//$("#fabric-fit-colors tbody tr:nth-child("+row_index+") td");
      var col_index   = $(this).index()+1;
      var col_targets  = $("#fabric-fit-colors tbody tr td:nth-child("+col_index+"), #fabric-fit-colors thead tr th:nth-child("+col_index+")");
      
      $(this).hover(
        function(){ 
          col_targets.addClass("subtle-highlight");
          row_targets.addClass("subtle-highlight");
        }, 
        function() { 
          col_targets.removeClass("subtle-highlight");
          row_targets.removeClass("subtle-highlight");
        }
      );
      
    
    });
  
  /* 
   * Other actions
   */

/* STYLE FINDER STUFF ====================================================== */

  var styles    = $(".boat-matrix");
  var features  = $(".boat-matrix-features");
  styles.find(".boat").hide();
  
  features.find("select").change(function() {

      var feature_name = $(this).val();
        if(feature_name) {
          $(this).find("option[value='']").text('None');
          $(".boat-matrix-features").scrollToViewPort(1400);//, {easing:'swing'});
        }
        
      $.bbq.pushState("#feature="+feature_name);
    

      
  });
  $(".boat-matrix-categories ul li a").each(function() {
    
    var class_name = $(this).attr("class");
    var human_name = $(this).html();
    var styles_subset = styles.find("."+class_name);
    
    
     
    
    $("<div class='boats-row'></div>").append("<h4 id='"+class_name+"'>"+human_name+"</h4>").append(styles_subset.show()).appendTo(".boat-matrix");

  });

  if($(".boat-matrix-categories").length) {
  
    $(window).bind( 'hashchange', function(e) {
    
    
      // reset the highlights and the hides
      $(".highlight").removeClass("highlight");
      $(".boats-row").show();
      $(".boat-matrix .boat").css("opacity", "1");
     

      var feature = $.bbq.getState("feature") || '';
      if(feature) {
        
        $(".boat-matrix .boat").each(function() {
          if($(this).hasClass(feature)) {
            $(this).addClass("highlight");
          } else if(!$(this).hasClass(feature)) {
            $(this).css("opacity", "0.3");
          }
        });
        $(".boats-row").each(function(){
          if(!$(this).find(".highlight").length) {
            $(this).hide();
          }
        });
      } // end if feature is selected
      else {
        $(window.location.hash).scrollToViewPort(1400);
      }
    });
  
  }
  

/* END STYLE FINDER STUFF ================================================== */   
  
  $(window).trigger( 'hashchange' ); // !important: makes the bbq work
 
  
}); // end document(ready);
 
//-->

