Last active
August 29, 2015 14:16
-
-
Save devdays/b98d8bca844c1fd241aa to your computer and use it in GitHub Desktop.
Sample jQuery UI Widget
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
<!DOCTYPE html> | |
<html> | |
<head> | |
<!-- | |
From http://ajpiano.com/widgetfactory/ | |
Copyright 2014 Bruce D Kyle | |
Licensed under the Apache License, Version 2.0 (the "License"); | |
you may not use this file except in compliance with the License. | |
You may obtain a copy of the License at | |
http://www.apache.org/licenses/LICENSE-2.0 | |
Unless required by applicable law or agreed to in writing, software | |
distributed under the License is distributed on an "AS IS" BASIS, | |
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
See the License for the specific language governing permissions and | |
limitations under the License. | |
Original presentation is copyrighted by Google 2010. | |
--> | |
<title>Filterable Widget</title> | |
<link href="Content/themes/base/core.css" rel="stylesheet" /> | |
<link href="Content/themes/base/theme.css" rel="stylesheet" /> | |
</head> | |
<body> | |
<button type="button" id="activation">Toggle Filterable</button> | |
<ul id="cheeses"> | |
<li data-price="17.99">Gruyere</li> | |
<li data-price="16.99">Comte</li> | |
<li data-price="4.99">Provolone</li> | |
<li data-price="8.99">Cheddar</li> | |
<li data-price="18.99">Parmigiano Reggiano</li> | |
<li data-price=".99">Government</li> | |
</ul> | |
<div id="register"> | |
One pound of each would cost $<span id="total"></span> | |
</div> | |
<script src="Scripts/jquery-2.1.3.js"></script> | |
<script src="Scripts/jquery-ui-1.11.3.js"></script> | |
<script src="Scripts/filterable/jquery-filterable-0.0.3.js"></script> | |
<script> | |
$(function() { | |
var total = $("#total"), | |
cheeses = $("#cheeses"), | |
register = $("#register"), | |
price = $("<span>"), | |
activation = $("#activation").button({icons:{primary:"ui-icon-search"}}); | |
activation.click(function() { | |
if (cheeses.is(":aj-filterable")) { | |
return cheeses.filterable("destroy"); | |
} | |
cheeses.filterable({ | |
className: "cheese", | |
create: function() { register.addClass("ui-widget-header cheese").show(); }, | |
filtered: function(e, ui) { | |
var t = 0; | |
ui.visible.each(function() { t = t + parseFloat($(this).data("price")); }); | |
console.log( t ); | |
total.text(t.toFixed(2)); | |
}, | |
setOption: function(e, ui) { | |
ui.option == "className" && register.toggleClass([ui.original, ui.current].join(" ")); | |
}, | |
hover: function(e, ui) { | |
if (e.originalEvent.type == "mouseenter") { | |
price.text(" - " + ui.hovered.data("price") + " per lb").appendTo(ui.hovered); | |
} else { | |
price.detach(); | |
} | |
} | |
}); | |
setTimeout(function() { cheeses.filterable("option", "className", "cheesePlease"); },3000); | |
}); | |
}); | |
</script> | |
</body> | |
</html> |
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
/* | |
From http://ajpiano.com/widgetfactory/ | |
Copyright 2014 Bruce D Kyle | |
Licensed under the Apache License, Version 2.0 (the "License"); | |
you may not use this file except in compliance with the License. | |
You may obtain a copy of the License at | |
http://www.apache.org/licenses/LICENSE-2.0 | |
Unless required by applicable law or agreed to in writing, software | |
distributed under the License is distributed on an "AS IS" BASIS, | |
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
See the License for the specific language governing permissions and | |
limitations under the License.. | |
*/ | |
(function ($) { | |
// The jQuery.aj namespace will automatically be created if it doesn't exist | |
$.widget("aj.filterable", { | |
// These options will be used as defaults | |
options: { | |
className: "" | |
}, | |
_create: function () { | |
// this.element -- a jQuery object of the element the widget was invoked on. | |
// this.options -- the merged options hash | |
console.log("_create" + this.options.className); | |
// Cache references to collections the widget needs to access regularly | |
this.filterElems = this.element.children() | |
.addClass("ui-widget-content " + this.options.className); | |
this.filterInput = $("<input type='text'>") | |
.insertBefore(this.element) | |
.wrap("<div class='ui-widget-header " + this.options.className + "'>"); | |
// bind events on elements: | |
this._on(this.filterElems, { | |
mouseenter: "_hover", | |
mouseleave: "_hover" | |
}); | |
// toggles ui-state-focus for you: | |
this._focusable(this.filterInput); | |
// _hoverable works for ui-state-hover, but we will do something slighty different in our hover | |
this._on(this.filterInput, { | |
"keyup": "filter" | |
}); | |
this.timeout = false; | |
}, | |
filter: function (event) { | |
// Debounce the keyup event with a timeout, using the specified delay | |
clearTimeout(this.timeout); | |
console.log("_create" + this.options.className); | |
// like setTimeout, only better! | |
this.timeout = this._delay(function () { | |
var re = new RegExp(this.filterInput.val(), "i"), | |
visible = this.filterElems.filter(function () { | |
var $t = $(this), matches = re.test($t.text()); | |
// Leverage the CSS Framework to handle visual state changes | |
$t.toggleClass("ui-helper-hidden", !matches); | |
return matches; | |
}); | |
// Trigger a callback so the user can respond to filtering being complete | |
// Supply an object of useful parameters with the second argument to _trigger | |
this._trigger("filtered", event, { | |
visible: visible | |
}); | |
}, this.options.delay); | |
}, | |
_hover: function (event) { | |
$(event.target).toggleClass("ui-state-active", event.type === "mouseenter"); | |
this._trigger("hover", event, { | |
hovered: $(event.target) | |
}); | |
}, | |
_setOption: function (key, value) { | |
var oldValue = this.options[key]; | |
console.log("_setOption: " + key + ": " + value); | |
// Check for a particular option being set | |
if (key === "className") { | |
// Gather all the elements we applied the className to | |
this.filterInput.parent().add(this.filterElems) | |
// Switch the new className in for the old | |
.toggleClass(oldValue + " " + value); | |
console.log("toggle class : " + oldValue + " " + value); | |
} | |
// Call the base _setOption method | |
this._super(key, value); | |
// The widget factory doesn't fire an callback for options changes by default | |
// In order to allow the user to respond, fire our own callback | |
this._trigger("setOption", null, { | |
option: key, | |
original: oldValue, | |
current: value | |
}); | |
}, | |
_destroy: function () { | |
// Use the destroy method to reverse everything your plugin has applied | |
this.filterInput.parent().remove(); | |
// Remove any classes, including CSS framework classes, that you applied | |
this.filterElems.removeClass("ui-widget-content ui-helper-hidden ui-state-active " + this.options.className); | |
return this._super(); | |
} | |
}); | |
})(jQuery); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment