<!DOCTYPE html>
<html>
<head>
<script src="http://code.jquery.com/jquery-2.0.3.min.js"></script>
<link rel="stylesheet" href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.10.0/themes/ui-darkness/jquery-ui.css" />
<script src="//cdnjs.cloudflare.com/ajax/libs/jqueryui/1.10.0/jquery-ui.js"></script>
<script src="http://code.jquery.com/jquery-2.0.3.min.js"></script>
<link rel="stylesheet" href="demo.css" />
<script src="checkedUI.js"></script>
<script src="script.js"></script>
</head>
<body class="ui-widget">
<h1>Pretty demo </h1>
<div id="ThemeRoller"></div>
<p>
Just a quick demo of what checked-ui does, with a few common scenarios to make sure everything is hanging
together correctly.
</p>
<fieldset>
<legend>Checkbox Examples</legend>
<!-- tables .. urg ... didn't they die out last century ;-) -->
<table class="x-large">
<thead>
<tr>
<th>Scenario</th>
<th>prettyCheck</th>
</tr>
</thead>
<tbody>
<tr>
<td>
Initially check is <strong>off</strong>
</td>
<td>
<label for="chkUI1">Check 1</label>
<input type="checkbox" class="prettyCheck" id="chkUI1" />
</td>
</tr>
<tr>
<td>
Initially check is <strong>on</strong>
</td>
<td>
<label for="chkUI2">Check 2</label>
<input type="checkbox" class="prettyCheck" id="chkUI2" checked="checked" />
</td>
</tr>
<tr>
<td>
Initially check is <strong>on</strong> and <strong>disabled</strong>
</td>
<td>
<label for="chkUI3">Check 3</label>
<input type="checkbox" class="prettyCheck" id="chkUI3" checked="checked" disabled="disabled" />
</td>
</tr>
<tr>
<td>
Initially check is <strong>off</strong> and <strong>disabled</strong>
</td>
<td>
<label for="chkUI4">Check 4</label>
<input type="checkbox" class="prettyCheck" id="chkUI4" disabled="disabled" />
</td>
</tr>
</tbody>
</table>
</fieldset>
<fieldset>
<legend>Radiobutton Examples</legend>
<!-- tables .. urg ... didn't they die out last century ;-) -->
<table class="x-large">
<col class="large" />
<col class="small" />
<thead>
<tr>
<th>Scenario</th>
<th>Pretty Rad</th>
</tr>
</thead>
<tbody>
<tr>
<td>
Initially none active
</td>
<td>
<label for="radUI2_Yes">Yes</label>
<input class="prettyRad" type="radio" name="chkUI2" id="radUI2_Yes" value="Yes" />
<label for="radUI2_No">No</label>
<input class="prettyRad" type="radio" name="chkUI2" id="radUI2_No" value="No" />
</td>
</tr>
<tr>
<td>
Disabled
</td>
<td>
<label for="radUI3_Yes">Yes</label>
<input class="prettyRad" type="radio" name="chkUI3" id="radUI3_Yes" value="Yes" checked="checked" disabled="disabled" />
<label for="radUI3_No">No</label>
<input class="prettyRad" type="radio" name="chkUI3" id="radUI3_No" value="No" disabled="disabled" />
</td>
</tr>
<tr><td colspan="3"><hr /></td></tr>
<tr>
<td>
Not grouped (no <strong>name</strong> attribute)
</td>
<td>
<label for="radUI1_Yes">Yes</label>
<input class="prettyRad" type="radio" id="radUI1_Yes" value="Yes" />
<label for="radUI1_No">No</label>
<input class="prettyRad" type="radio" id="radUI1_No" value="No" />
</td>
</tr>
</tbody>
</table>
</fieldset>
</body>
</html>
$(document).ready(function() {
var debugMode = false;
$("input:checkbox.prettyCheck").checkedUI({
debug: debugMode
});
$("input:radio.prettyRad").checkedUI({
debug: debugMode
});
$('#ThemeRoller').themeswitcher();
});
body {
margin: 5%;
font-size: 80% !important;
}
fieldset {
margin-bottom: 1em;
}
h1 {
font-size: x-large;
}
ul {
list-style: none;
margin-left: -1em;
}
th {
text-align: left;
}
.x-large {
width: 100%;
}
.small {
width: 30%;
}
.large {
width: 40%;
}
(function ($) {
$.fn.checkedUI = function (settings) {
this.version = "1.0.0";
this.plugInName = "checkedUI";
/// <summary>
/// Set of overrides for configing how the plug-in works
/// </summary>
var config = {
// Possible variations
// onChkClass offChkClass
// "ui-icon-check" "ui-icon-close"
// "ui-icon-circle-check" "ui-icon-circle-close"
// "ui-icon-closethick"
// onRadClass offRadClass
// ui-icon-radio-on ui-icon-radio-off
// ui-icon-bullet
//
onChkClass: "ui-icon-check",
offChkClass: "ui-icon-closethick",
onRadClass: "ui-icon-bullet",
offRadClass: "ui-icon-radio-off"
}; // config
if (settings)
// add overrides from default settings
$.extend(config, settings);
/// <summary>
/// Builds up the HTML to surround the checkbox or radio button
/// </summary>
function getIconHtml(chk, opts) {
// is the checkbox currently ticked and/or disabled?
var isChecked = chk.is(':checked');
var isDisabled = chk.prop("disabled");
// locals for referencing the correct initial class state
var startIcon = (isChecked ? opts.onClass : opts.offClass);
var startState = "";
if (isDisabled) {
// disabled appearance takes precendence over checked
startState = "ui-state-disabled";
} else {
startState = (isChecked ? " ui-state-active " : "");
}
// build up the mark up for the pseudo icon
// ... basically we have a surrounding "inline-block" span around the icon span so we can have the background icon appear
var icoHtml = "<span class='ui-icon " + startIcon + "' />";
var wrapper =
"<span " +
"class='ui-state-default " + startState + " ui-corner-all ui-button' " +
"style='display: inline-block; margin-right: 5px;'>" +
icoHtml + "</span>";
return wrapper;
}; // getIconHtml
/// <summary>
/// Kind of what it says on the tin ... takes the status of the control and amends the styling
/// of the icon and container as appropriate
/// </summary>
function updateUI(chk, opts) {
var isChecked = chk.prop("checked");
var isDisabled = chk.prop("disabled");
opts._icon
.toggleClass(opts.onClass, isChecked)
.toggleClass(opts.offClass, !isChecked)
;
opts._box
.toggleClass("ui-state-active", (!isDisabled && isChecked))
.toggleClass("ui-state-disabled", isDisabled);
;
}; // updateUI
function hideElement(chk) {
if (chk.prop("disabled")) {
// For disabled elements, just hide the underlying control, as the
// z-index version doesn't look good. Besides for disabled elements
// you can't select it with the mouse OR keyboard anyway ...
chk.addClass("ui-helper-hidden");
} else {
// We don't want to physically hide the checkbox/rad as we'll lose keyboard
// access (you won't be able to hit "space" to toggle a checkbox for instance)
// so we just disguise it by placing it directly under our pretty span
chk
.css("position", "relative")
.css("left", "-25px")
.css("z-index", "-1000")
;
}
}; // hideElement
/// <summary>
/// Preps the checkbox/radio button as appropriate and wires up all events required to function
/// </summary>
function checkedUI(chk, opts) {
var isRadio = chk.is(":radio");
// wire up the correct icons to use
opts.onClass = (isRadio ? config.onRadClass : config.onChkClass);
opts.offClass = (isRadio ? config.offRadClass : config.offChkClass);
// Build up the HTML to mimic the control
var wrapper = getIconHtml(chk, opts);
// Put the HTML just before the actual checkbox/radio button
// ... doesn't have to be before, could be after it's not required I just like it checkbox being afterwards :)
chk.before(wrapper);
// get a reference back to the inline-block span which allows the background-image to be visible
opts._box = chk.prev();
// ... and a reference to the icon itself (i.e. the jQuery UI "ui-icon" span)
opts._icon = opts._box.find("span");
if (!config.debug) {
// hide the original checkbox (this will only exist behind the scenes)
// ... this is configurable, purely to make future development easier
hideElement(chk);
}
var changeSelector = chk;
if (isRadio) {
// The incoming control, "chk" only points to a single racio/checkbox. This is fine for checkboxes which
// run in isolation, but radio buttons can be grouped. So changing the value of one radio button, will
// actually un-select others in the group. But we won't get a "change" event for them becuase our "chk" filter
// is only looking at one of the radio buttons in the group.
// To fix this expand the "change" selector to include all radio buttons in the group, that way we'll get
// [radio button] notifications for both select and de-select scenarios.
// Not ideal to search teh full dom, but other than _guessing_ where they are in the hierarchy there's no a great
// deal we can do.
changeSelector = "input[name='" + chk.attr("name") + "']";
}
chk.add(changeSelector).change(function () {
updateUI(chk, opts);
});
// hover behaviour, note this is against the container element
opts._box.hover(
function () {
if (chk.prop("disabled"))
// shouldn't have any indication on disabled elements
return;
opts._box.removeClass("ui-state-active");
opts._box.addClass("ui-state-hover");
},
function () {
opts._box.removeClass("ui-state-hover");
updateUI(chk, opts);
}
);
// ... and wire up when the user clicks on the container
opts._box.click(
function () {
// change the appearance of the widget given the container has been clicked
updateUI(chk, opts);
// propagate the click through to the underlying checkbox
// ... the handles any other events that have latched onto the click event of the checkbox
// ... and honours them
chk.click();
}
);
}; // checkedUI
// iterate over in match in the selector
this.each(function (index) {
var options = {};
var me = $(this);
checkedUI(me, options);
});
// maintain chainability
return this;
};
})(jQuery);