Created
September 26, 2013 15:24
-
-
Save jrochkind/6715756 to your computer and use it in GitHub Desktop.
JH custom JS for blacklight_advanced_search to have differnet method of auto-complete multi-select for voluminous facets
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* Custom JS for Advanced Search Form */ | |
jQuery(document).ready(function($) { | |
// A utility function we'll use to make a JQuery selector | |
// on a particular string 'id'. HTML id allows : or . chars, | |
// but need to be escaped in JQuery selectors. | |
// See http://docs.jquery.com/Frequently_Asked_Questions#How%5Fdo%5FI%5Fselect%5Fan%5Felement%5Fby%5Fan%5FID%5Fthat%5Fhas%5Fcharacters%5Fused%5Fin%5FCSS%5Fnotation.3F | |
function jq_id_select_escape(str_id) { | |
return str_id.replace(/(:|\.)/g,'\\$1'); | |
} | |
// Make the facet labels float left so the autocomplete will be next to it | |
$(".facet_item h3").css({ | |
"width": "30%", | |
"float": "left", | |
"clear": "left" | |
}); | |
$('.limit_column ul').each(function(){ | |
var ul = $(this); | |
// add an auto-completer with combo-box style toggle | |
var label = $(ul).prevAll("h3").text(); | |
$(ul).before("<input type='text' class='advanced_facet_autocomplete'/> <a title='Show all "+label+"' class='advanced_facet_toggler ui-button ui-widget ui-state-default ui-button-icon-only ui-corner-right ui-button-icon'><span class='ui-button-icon-primary ui-icon ui-icon-triangle-1-s'></span><span class='ui-button-text'></span></a>"); | |
//make the input an autocomplete that loads from ul | |
//when selected, checks relevant checkbox, and blanks | |
//out autocomplete textbox | |
$(ul).prevAll(".advanced_facet_autocomplete") | |
.keypress(function(e) { | |
//try to prevent enter in autocompletey field from submitting form. | |
if (e.which === 13) { | |
e.preventDefault(); | |
return false; | |
} | |
}) | |
.autocomplete({ | |
source: function(req, add) { | |
// For each checkbox, add an option to the autocomplete select. | |
add( | |
jQuery.map(ul.children('li'), function(i) { | |
var maybe_match = $.trim($(i).text()).toLowerCase(); | |
if ( ! $(i).find("input").attr("checked") && | |
maybe_match.indexOf(req.term.toLowerCase()) === 0) { | |
//we use original_value rather than 'value' | |
//so it won't mean anything to autocomplete, | |
//but we can keep it for later, in our select | |
//event. | |
return {label: $.trim($(i).text()), | |
value: $.trim($(i).find("label").text()), | |
original_value: $(i).find('input').attr('id') | |
}; | |
} | |
else { | |
return null; | |
} | |
} | |
) | |
); | |
}, | |
select: function(event, ui) { | |
//to be able to find the checkbox by id even if the id | |
// has period's in it, we need to escape em in the jquery selector. | |
ul.find("input#"+jq_id_select_escape(ui.item.original_value)).attr("checked", true).trigger("change"); | |
$(this).val(''); | |
return false; | |
}, | |
focus: function(event, ui) { | |
// Do NOT replace textbox contents with selection on | |
// focus -- otherwise confusing behavior if you close | |
// the autocomplete without an actual select, leaving | |
// the selected value in there. | |
event.preventDefault(); | |
}, | |
minLength: 0 | |
}) | |
.autocomplete("widget").css({ | |
'max-height': '18em', | |
'overflow-y': 'auto', | |
'overflow-x': 'hidden', | |
'padding-right': '20px' | |
}); | |
//make the combo-box thing turn the autocomplete on and off, copied | |
//from jquery-ui autocomplete combobox example. | |
$(ul).prevAll(".advanced_facet_toggler").click(function() { | |
var input = $(this).parent().find(".advanced_facet_autocomplete"); | |
if (input.autocomplete("widget").is(":visible")) { | |
input.autocomplete("close"); | |
return; | |
} | |
// bug workaround copied from autocomplete example | |
$( this ).blur(); | |
// pass empty string as value to search for, displaying all results | |
input.autocomplete( "search", "" ); | |
input.focus(); | |
}); | |
//move the container for displaying current constraints from | |
//the weird place it is to after the ul. | |
ul.closest(".facet_item").find(".adv_facet_selections").insertAfter(ul); | |
// hide the ul | |
ul.hide(); | |
}); | |
/* Stuff for handling the checkboxes */ | |
/* When you click a checkbox, update readout */ | |
/* Pass in a jquery obj holding the "selected facet element" spans, get back | |
a string for display representing currently checked things. */ | |
function convertCheckboxesToBubbles(div) { | |
var checkbox_elements = $(div).find("input:checkbox"); | |
var constraint_html = $('<span/>'); | |
var checked = 0; | |
checkbox_elements.each(function() { | |
if ($(this).is(":checked")) { | |
checked += 1; | |
var c = $("<span/></span>").addClass("appliedFilter constraint") | |
.append( $("<span/>").addClass("filterValue").html($(this).nextAll("label").text()) ) | |
.append( $("<a/>") | |
.addClass("btnRemove imgReplace") | |
.attr("title", "remove") | |
.attr("data-checkbox-id", $(this).attr('id')) | |
.click(function() { | |
var orig_id = $(this).attr("data-checkbox-id"); | |
$(div).find("input#" + jq_id_select_escape(orig_id)).removeAttr("checked").trigger("change"); | |
}) | |
) | |
.appendTo( constraint_html ); | |
} | |
}); | |
if (checked > 1) { | |
constraint_html.prepend("Any of: "); | |
} | |
return constraint_html; | |
} | |
//Pass in JQuery object of zero or more <div class="facet_item"> blocks, | |
//that contain an h3, some checkboxes, and a span.adv_facet_selections for | |
//display of current selections. Will update the span. | |
function updateSelectedDisplay(facet_item) { | |
var displaySpan = $(facet_item).find("span.adv_facet_selections"); | |
var displayHtml = convertCheckboxesToBubbles( facet_item ); | |
displaySpan.html( displayHtml ); | |
displaySpan.show(); | |
} | |
// on page load, set initial constraint bubbles properly | |
// based on initial checkbox state. | |
$(".facet_item").each(function() { | |
updateSelectedDisplay(this); | |
}); | |
// Everytime checkbox state changes, make sure | |
// we update constraint bubbles. We have our autocomplete | |
// making sure to change checkboxes on select, so that'll | |
// trigger this constraint display update too. | |
$(".facet_item input:checkbox").change( function() { | |
updateSelectedDisplay( $(this).closest(".facet_item")); | |
}); | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment