/* ======== JQUEY CARET =========== */
(function($) {
$.fn.caret = function(pos) {
var target = this[0];
var isContentEditable = target.contentEditable === "true";
//get
if (arguments.length == 0) {
//HTML5
if (window.getSelection) {
//contenteditable
if (isContentEditable) {
target.focus();
var range1 = window.getSelection().getRangeAt(0),
range2 = range1.cloneRange();
range2.selectNodeContents(target);
range2.setEnd(range1.endContainer, range1.endOffset);
return range2.toString().length;
}
//textarea
return target.selectionStart;
}
//IE<9
if (document.selection) {
target.focus();
//contenteditable
if (isContentEditable) {
var range1 = document.selection.createRange(),
range2 = document.body.createTextRange();
range2.moveToElementText(target);
range2.setEndPoint("EndToEnd", range1);
return range2.text.length;
}
//textarea
var pos = 0,
range = target.createTextRange(),
range2 = document.selection.createRange().duplicate(),
bookmark = range2.getBookmark();
range.moveToBookmark(bookmark);
while (range.moveStart("character", -1) !== 0) pos++;
return pos;
}
//not supported
return 0;
}
//set
if (pos == -1) pos = this[isContentEditable ? "text" : "val"]().length;
//HTML5
if (window.getSelection) {
//contenteditable
if (isContentEditable) {
target.focus();
window.getSelection().collapse(target.firstChild, pos);
} else
//textarea
target.setSelectionRange(pos, pos);
} else if (document.body.createTextRange) {
//IE<9
var range = document.body.createTextRange();
range.moveToElementText(target);
range.moveStart("character", pos);
range.collapse(true);
range.select();
}
if (!isContentEditable) target.focus();
return pos;
};
})(jQuery);
/* ========= TEXTAREA HELPER =============== */
(function($) {
"use strict";
var caretClass = "textarea-helper-caret",
dataKey = "textarea-helper",
// Styles that could influence size of the mirrored element.
mirrorStyles = [
// Box Styles.
"box-sizing",
"height",
"width",
"padding-bottom",
"padding-left",
"padding-right",
"padding-top",
// Font stuff.
"font-family",
"font-size",
"font-style",
"font-variant",
"font-weight",
// Spacing etc.
"word-spacing",
"letter-spacing",
"line-height",
"text-decoration",
"text-indent",
"text-transform",
// The direction.
"direction"
];
var TextareaHelper = function(elem) {
if (elem.nodeName.toLowerCase() !== "textarea") return;
this.$text = $(elem);
this.$mirror = $("
")
.css({
position: "absolute",
overflow: "auto",
"white-space": "pre-wrap",
"word-wrap": "break-word",
top: 0,
left: -9999
})
.insertAfter(this.$text);
};
(function() {
this.update = function() {
// Copy styles.
var styles = {};
for (var i = 0, style; (style = mirrorStyles[i]); i++) {
styles[style] = this.$text.css(style);
}
this.$mirror.css(styles).empty();
// Update content and insert caret.
var caretPos = this.getOriginalCaretPos(),
str = this.$text.val(),
pre = document.createTextNode(str.substring(0, caretPos)),
post = document.createTextNode(str.substring(caretPos)),
$car = $("")
.addClass(caretClass)
.css("position", "absolute")
.html(" ");
this.$mirror.append(pre, $car, post).scrollTop(this.$text.scrollTop());
};
this.destroy = function() {
this.$mirror.remove();
this.$text.removeData(dataKey);
return null;
};
this.caretPos = function() {
this.update();
var $caret = this.$mirror.find("." + caretClass),
pos = $caret.position();
if (this.$text.css("direction") === "rtl") {
pos.right = this.$mirror.innerWidth() - pos.left - $caret.width();
pos.left = "auto";
}
return pos;
};
this.height = function() {
this.update();
this.$mirror.css("height", "");
return this.$mirror.height();
};
// XBrowser caret position
// Adapted from http://stackoverflow.com/questions/263743/how-to-get-caret-position-in-textarea
this.getOriginalCaretPos = function() {
var text = this.$text[0];
if (text.selectionStart) {
return text.selectionStart;
} else if (document.selection) {
text.focus();
var r = document.selection.createRange();
if (r == null) {
return 0;
}
var re = text.createTextRange(),
rc = re.duplicate();
re.moveToBookmark(r.getBookmark());
rc.setEndPoint("EndToStart", re);
return rc.text.length;
}
return 0;
};
}.call(TextareaHelper.prototype));
$.fn.textareaHelper = function(method) {
this.each(function() {
var $this = $(this),
instance = $this.data(dataKey);
if (!instance) {
instance = new TextareaHelper(this);
$this.data(dataKey, instance);
}
});
if (method) {
var instance = this.first().data(dataKey);
return instance[method]();
} else {
return this;
}
};
})(jQuery);
/* ========= JQURY ALERTS ================= */
(function($) {
$.jPopup = function(message, errorLevel, callback, options, buttons) {
var defaults = {
message: message,
errorLevel: errorLevel,
wrapperClass: "jpopup",
show: "drop",
minHeight: 5
};
options = $.extend(defaults, options);
var dialogCSS = "ui-state-error";
var iconCSS = " ui-icon-alert";
switch (options.errorLevel) {
case "highlight":
dialogCSS = " ui-state-highlight";
iconCSS = " ui-icon-notice";
break;
case "error":
dialogCSS = " ui-state-error";
iconCSS = " ui-icon-alert";
break;
default:
dialogCSS = "";
iconCSS = " ui-icon-info";
break;
}
var dialog = $(
'"
);
var dialogOptions = {
bgiframe: true,
dialogClass: options.wrapperClass + dialogCSS,
resizable: false,
minHeight: options.minHeight,
modal: true,
buttons: buttons,
close: function(event, ui) {
dialog.remove();
if (callback) callback(false);
}
};
options = $.extend(dialogOptions, options);
dialog.dialog(options);
};
$.jConfirm = function(message, errorLevel, callback, options) {
var buttons = {
Ok: function() {
$(this).dialog("close");
if (callback) {
callback(true);
}
},
Cancel: function() {
$(this).dialog("close");
if (callback) {
callback(false);
}
}
};
$.jPopup(message, errorLevel, callback, options, buttons);
};
$.jAlert = function(message, errorLevel, callback, options) {
var buttons = {
Ok: function() {
$(this).dialog("close");
if (callback) {
callback(true);
}
}
};
$.jPopup(message, errorLevel, callback, options, buttons);
};
})(jQuery);
/* === THEME SWITCHER TOOL ====== */
/* jQuery plugin themeswitcher
based on http://blog.rbe.homeip.net/posts/jquery-themeswitcher
---------------------------------------------------------------------*/
var baseUrl = baseUrl || "/";
if (!baseUrl.match(/\/$/)) {
baseUrl = baseUrl + "/";
}
$.fn.themeswitcher = function(settings) {
var options = jQuery.extend(
{
loadTheme: "cupertino",
initialText: "Switch Theme",
width: 180,
height: 400,
buttonPreText: "Theme: ",
closeOnSelect: true,
buttonHeight: 14,
cookieName: "jquery-ui-theme",
onOpen: function() {},
onClose: function() {},
onSelect: function() {},
useStandard: true,
cssPrefix: "//code.jquery.com/ui/1.12.1/themes/",
cssSuffix: "/jquery-ui.css",
imgPrefix: baseUrl + "images/Themeroller/theme_90_",
imgSuffix: ".png",
imageLocation: baseUrl + "images/Themeroller/",
themes: {},
useCookie: true
},
settings
);
if (options.useStandard)
$.extend(options.themes, {
base: { icon: options.imageLocation + "base.png" },
"black-tie": {},
blitzer: {},
cupertino: {},
"dark-hive": {},
"dot-luv": {},
eggplant: {},
"excite-bike": {},
flick: {},
"hot-sneaks": {},
humanity: {},
"le-frog": {},
"mint-choc": {},
overcast: {},
"pepper-grinder": {},
redmond: {},
smoothness: {},
"south-street": {},
start: {},
sunny: {},
"swanky-purse": {},
trontastic: {},
"ui-darkness": {},
"ui-lightness": {}
});
var theme_ul = "";
for (var i in options.themes) {
css = options.themes[i].css || options.cssPrefix + i + options.cssSuffix;
img =
options.themes[i].icon ||
options.imgPrefix + i.replace("-", "_") + options.imgSuffix;
theme_ul +=
"
" +
i +
"";
}
theme_ul = "";
//markup
var button = $(
'' +
options.initialText +
""
);
var switcherpane = $(
'"
)
.find("div")
.removeAttr("id");
//button events
button.click(function() {
if (switcherpane.is(":visible")) switcherpane.spHide();
else switcherpane.spShow();
return false;
});
//menu events (mouseout didn't work...)
switcherpane.hover(
function() {},
function() {
if (switcherpane.is(":visible")) {
$(this).spHide();
}
}
);
//show/hide panel functions
$.fn.spShow = function() {
$(this)
.css({
top: button.offset().top + options.buttonHeight + 6,
left: button.offset().left
})
.slideDown(50);
button.css(button_active);
options.onOpen();
};
$.fn.spHide = function() {
$(this).slideUp(50, function() {
options.onClose();
});
button.css(button_default);
};
/* Theme Loading
---------------------------------------------------------------------*/
switcherpane.find("a").click(function() {
updateCSS($(this).attr("href"));
var themeName = $(this)
.find("span")
.text();
button
.find(".jquery-ui-themeswitcher-title")
.text(options.buttonPreText + themeName);
if (options.useCookie)
$.cookie(options.cookieName, themeName, { path: "/" });
options.onSelect();
if (options.closeOnSelect && switcherpane.is(":visible")) {
switcherpane.spHide();
}
return false;
});
//function to rewrite stylesheet link.
// if there is not onewith an id='ui-theme', append to
function updateCSS(locStr) {
if ($("head link#ui-theme").length == 0)
$("head").append(
$('')
);
$("head link#ui-theme").attr("href", locStr);
}
/* Inline CSS
---------------------------------------------------------------------*/
var button_default = {
fontFamily: "Trebuchet MS, Verdana, sans-serif",
fontSize: "11px",
color: "#666",
background:
"#eee url(" + options.imageLocation + "buttonbg.png) 50% 50% repeat-x",
border: "1px solid #ccc",
"-moz-border-radius": "6px",
"-webkit-border-radius": "6px",
textDecoration: "none",
padding: "3px 3px 3px 8px",
width: options.width - 11, //minus must match left and right padding
display: "block",
height: options.buttonHeight,
outline: "0"
};
var button_hover = {
borderColor: "#bbb",
background: "#f0f0f0",
cursor: "pointer",
color: "#444"
};
var button_active = {
color: "#aaa",
background: "#000",
border: "1px solid #ccc",
borderBottom: 0,
"-moz-border-radius-bottomleft": 0,
"-webkit-border-bottom-left-radius": 0,
"-moz-border-radius-bottomright": 0,
"-webkit-border-bottom-right-radius": 0,
outline: "0"
};
//button css
button
.css(button_default)
.hover(
function() {
$(this).css(button_hover);
},
function() {
if (!switcherpane.is(":animated") && switcherpane.is(":hidden")) {
$(this).css(button_default);
}
}
)
.find(".jquery-ui-themeswitcher-icon")
.css({
float: "right",
width: "16px",
height: "16px",
background:
"url(" +
options.imageLocation +
"icon_color_arrow.gif) 50% 50% no-repeat"
});
//pane css
switcherpane
.css({
position: "absolute",
float: "left",
fontFamily: "Trebuchet MS, Verdana, sans-serif",
fontSize: "12px",
background: "#000",
color: "#fff",
padding: "8px 3px 3px",
border: "1px solid #ccc",
"-moz-border-radius-bottomleft": "6px",
"-webkit-border-bottom-left-radius": "6px",
"-moz-border-radius-bottomright": "6px",
"-webkit-border-bottom-right-radius": "6px",
borderTop: 0,
zIndex: 999999,
width: options.width - 6 //minus must match left and right padding
})
.find("ul")
.css({
listStyle: "none",
margin: "0",
padding: "0",
overflow: "auto",
height: options.height
})
.end()
.find("li")
.hover(
function() {
$(this).css({
borderColor: "#555",
background:
"url(" +
options.imageLocation +
"menuhoverbg.png) 50% 50% repeat-x",
cursor: "pointer"
});
},
function() {
$(this).css({
borderColor: "#111",
background: "#000",
cursor: "auto"
});
}
)
.css({
width: options.width - 30,
height: "",
padding: "2px",
margin: "1px",
border: "1px solid #111",
"-moz-border-radius": "4px",
clear: "left",
textAlign: "center",
float: "left"
})
.end()
.find("a")
.css({
color: "#aaa",
textDecoration: "none",
// float: 'left',
width: "100%",
outline: "0",
textAlign: "center"
})
.end()
.find("img")
.css({
// float: 'left',
border: "1px solid #333",
margin: "0 2px"
})
.end()
.find(".themeName")
.css({
float: "left",
margin: "3px 0",
display: "block",
width: "100%"
})
.end();
$(this).append(button);
$("body").append(switcherpane);
switcherpane.hide();
if (
options.useCookie &&
($.cookie(options.cookieName) || options.loadTheme)
) {
var themeName = $.cookie(options.cookieName) || options.loadTheme;
switcherpane.find("a:contains(" + themeName + ")").trigger("click");
}
return this;
};
/**
* Cookie plugin
*
* Copyright (c) 2006 Klaus Hartl (stilbuero.de)
* Dual licensed under the MIT and GPL licenses:
* http://www.opensource.org/licenses/mit-license.php
* http://www.gnu.org/licenses/gpl.html
*
*/
jQuery.cookie = function(name, value, options) {
if (typeof value != "undefined") {
// name and value given, set cookie
options = options || {};
options.expires = 365;
if (value === null) {
value = "";
options.expires = -1;
}
var expires = "";
if (
options.expires &&
(typeof options.expires == "number" || options.expires.toUTCString)
) {
var date;
if (typeof options.expires == "number") {
date = new Date();
date.setTime(date.getTime() + options.expires * 24 * 60 * 60 * 1000);
} else {
date = options.expires;
}
expires = "; expires=" + date.toUTCString(); // use expires attribute, max-age is not supported by IE
}
// CAUTION: Needed to parenthesize options.path and options.domain
// in the following expressions, otherwise they evaluate to undefined
// in the packed version for some reason...
var path = options.path ? "; path=" + options.path : "";
var domain = options.domain ? "; domain=" + options.domain : "";
var secure = options.secure ? "; secure" : "";
document.cookie = [
name,
"=",
encodeURIComponent(value),
expires,
path,
domain,
secure
].join("");
} else {
// only name given, get cookie
var cookieValue = null;
if (document.cookie && document.cookie != "") {
var cookies = document.cookie.split(";");
for (var i = 0; i < cookies.length; i++) {
var cookie = jQuery.trim(cookies[i]);
// Does this cookie string begin with the name we want?
if (cookie.substring(0, name.length + 1) == name + "=") {
cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
break;
}
}
}
return cookieValue;
}
};
/* ==== STICKEY TABLE HEADERS ======== */
(function($) {
$.StickyTableHeaders = function(el, options) {
// To avoid scope issues, use 'base' instead of 'this'
// to reference this class from internal events and functions.
var base = this;
// Access to jQuery and DOM versions of element
base.$el = $(el);
base.el = el;
// Add a reverse reference to the DOM object
base.$el.data("StickyTableHeaders", base);
base.init = function() {
base.options = $.extend({}, $.StickyTableHeaders.defaultOptions, options);
base.$el.each(function() {
var $this = $(this);
$this.wrap(
''
);
var originalHeaderRow = $("thead:first", this);
originalHeaderRow.before(originalHeaderRow.clone());
var clonedHeaderRow = $("thead:first", this);
clonedHeaderRow.addClass("tableFloatingHeader");
clonedHeaderRow.css("position", "fixed");
clonedHeaderRow.css("top", "0px");
clonedHeaderRow.css("left", $this.css("margin-left"));
clonedHeaderRow.css("display", "none");
originalHeaderRow.addClass("tableFloatingHeaderOriginal");
// enabling support for jquery.tablesorter plugin
$this.bind("sortEnd", function(e) {
base.updateCloneFromOriginal(originalHeaderRow, clonedHeaderRow);
});
});
base.updateTableHeaders();
$(window).scroll(base.updateTableHeaders);
$(window).resize(base.updateTableHeaders);
};
base.updateTableHeaders = function() {
base.$el.each(function() {
var $this = $(this);
var $window = $(window);
var fixedHeaderHeight = isNaN(base.options.fixedOffset)
? base.options.fixedOffset.height()
: base.options.fixedOffset;
var originalHeaderRow = $(".tableFloatingHeaderOriginal", this);
var floatingHeaderRow = $(".tableFloatingHeader", this);
var offset = $this.offset();
var scrollTop = $window.scrollTop() + fixedHeaderHeight;
var scrollLeft = $window.scrollLeft();
if (scrollTop > offset.top && scrollTop < offset.top + $this.height()) {
floatingHeaderRow.css("top", fixedHeaderHeight + "px");
floatingHeaderRow.css("margin-top", 0);
floatingHeaderRow.css("left", offset.left - scrollLeft + "px");
floatingHeaderRow.css("display", "block");
base.updateCloneFromOriginal(originalHeaderRow, floatingHeaderRow);
} else {
floatingHeaderRow.css("display", "none");
}
});
};
base.updateCloneFromOriginal = function(
originalHeaderRow,
floatingHeaderRow
) {
// Copy cell widths and classes from original header
$("th", floatingHeaderRow).each(function(index) {
$this = $(this);
var origCell = $("th", originalHeaderRow).eq(index);
$this.removeClass().addClass(origCell.attr("class"));
$this.css("width", origCell.width());
});
// Copy row width from whole table
floatingHeaderRow.css("width", originalHeaderRow.width());
};
// Run initializer
base.init();
};
$.StickyTableHeaders.defaultOptions = {
fixedOffset: 0
};
$.fn.stickyTableHeaders = function(options) {
return this.each(function() {
new $.StickyTableHeaders(this, options);
});
};
})(jQuery);
/************************************** jQuery Accordion Table ****************************************/
(function($) {
$.fn.accordionTable = function(options) {
return this.each(function() {
var settings = options; // no defaults
hideAllAccordionRows(this);
hideAllTableOpenIcons(this);
$(this)
.find("." + settings.accordionClosedImg)
.on("click", function(e) {
if (
settings.isRowLoaded(
$(e.target)
.closest("tr")
.next("tr")
)
)
$.ajax({
url: urlForAccordionRow(e),
data: dataAttributes(e),
complete: function(data) {
var accordion_row = toggleAccordionRow(e);
if (settings.formatResponseToHtml)
settings.formatResponseToHtml(data, accordion_row);
else accordion_row.find("td").html(data.responseText);
}
});
else toggleAccordionRow(e);
});
$(this)
.find("." + settings.accordionOpenImg)
.on("click", function(e) {
toggleAccordionRow(e);
});
function dataAttributes(e) {
if (settings.dataAttrs) return settings.dataAttrs(e);
else return null;
}
function urlForAccordionRow(e) {
if (settings.urlForAccordionRow) return settings.urlForAccordionRow(e);
else return "";
}
function toggleAccordionRow(e) {
var non_accordion_row = $(e.target).parents("tr"),
accordion_row = non_accordion_row.next("tr");
accordion_row.toggle();
non_accordion_row.find("." + settings.accordionClosedImg).toggle();
non_accordion_row.find("." + settings.accordionOpenImg).toggle();
return accordion_row;
}
function hideAllAccordionRows(table) {
$(table)
.find("tr." + settings.accordionRow)
.each(function(index) {
$(this).hide();
});
}
function hideAllTableOpenIcons(table) {
$(table)
.find("." + settings.accordionOpenImg)
.each(function(index) {
$(this).hide();
});
}
});
};
})(jQuery);
/*====== URL PARSING ========*/
/* https://github.com/websanova/url/tags */
window.url = (function() {
function isNumeric(arg) {
return !isNaN(parseFloat(arg)) && isFinite(arg);
}
return function(arg, url) {
var _ls = url || window.location.toString();
if (!arg) {
return _ls;
} else {
arg = arg.toString();
}
if (_ls.substring(0, 2) === "//") {
_ls = "http:" + _ls;
} else if (_ls.split("://").length === 1) {
_ls = "http://" + _ls;
}
url = _ls.split("/");
var _l = { auth: "" },
host = url[2].split("@");
if (host.length === 1) {
host = host[0].split(":");
} else {
_l.auth = host[0];
host = host[1].split(":");
}
_l.protocol = url[0];
_l.hostname = host[0];
_l.port =
host[1] ||
(_l.protocol.split(":")[0].toLowerCase() === "https" ? "443" : "80");
_l.pathname =
(url.length > 3 ? "/" : "") +
url
.slice(3, url.length)
.join("/")
.split("?")[0]
.split("#")[0];
var _p = _l.pathname;
if (_p.charAt(_p.length - 1) === "/") {
_p = _p.substring(0, _p.length - 1);
}
var _h = _l.hostname,
_hs = _h.split("."),
_ps = _p.split("/");
if (arg === "hostname") {
return _h;
} else if (arg === "domain") {
if (
/^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$/.test(
_h
)
) {
return _h;
}
return _hs.slice(-2).join(".");
} else if (arg === "sub") {
//else if (arg === 'tld') { return _hs.slice(-1).join('.'); }
return _hs.slice(0, _hs.length - 2).join(".");
} else if (arg === "port") {
return _l.port;
} else if (arg === "protocol") {
return _l.protocol.split(":")[0];
} else if (arg === "auth") {
return _l.auth;
} else if (arg === "user") {
return _l.auth.split(":")[0];
} else if (arg === "pass") {
return _l.auth.split(":")[1] || "";
} else if (arg === "path") {
return _l.pathname;
} else if (arg.charAt(0) === ".") {
arg = arg.substring(1);
if (isNumeric(arg)) {
arg = parseInt(arg, 10);
return _hs[arg < 0 ? _hs.length + arg : arg - 1] || "";
}
} else if (isNumeric(arg)) {
arg = parseInt(arg, 10);
return _ps[arg < 0 ? _ps.length + arg : arg] || "";
} else if (arg === "file") {
return _ps.slice(-1)[0];
} else if (arg === "filename") {
return _ps.slice(-1)[0].split(".")[0];
} else if (arg === "fileext") {
return _ps.slice(-1)[0].split(".")[1] || "";
} else if (arg.charAt(0) === "?" || arg.charAt(0) === "#") {
var params = _ls,
param = null;
if (arg.charAt(0) === "?") {
params = (params.split("?")[1] || "").split("#")[0];
} else if (arg.charAt(0) === "#") {
params = params.split("#")[1] || "";
}
if (!arg.charAt(1)) {
return params;
}
arg = arg.substring(1);
params = params.split("&");
for (var i = 0, ii = params.length; i < ii; i++) {
param = params[i].split("=");
if (param[0] === arg) {
return param[1] || "";
}
}
return null;
}
return "";
};
})();
if (typeof jQuery !== "undefined") {
jQuery.extend({
url: function(arg, url) {
return window.url(arg, url);
}
});
}
/* Highlighter */
/*
* jQuery Highlight plugin
*
* Based on highlight v3 by Johann Burkard
* http://johannburkard.de/blog/programming/javascript/highlight-javascript-text-higlighting-jquery-plugin.html
*
* Code a little bit refactored and cleaned (in my humble opinion).
* Most important changes:
* - has an option to highlight only entire words (wordsOnly - false by default),
* - has an option to be case sensitive (caseSensitive - false by default)
* - highlight element tag and class names can be specified in options
*
* Usage:
* // wrap every occurrance of text 'lorem' in content
* // with (default options)
* $('#content').highlight('lorem');
*
* // search for and highlight more terms at once
* // so you can save some time on traversing DOM
* $('#content').highlight(['lorem', 'ipsum']);
* $('#content').highlight('lorem ipsum');
*
* // search only for entire word 'lorem'
* $('#content').highlight('lorem', { wordsOnly: true });
*
* // don't ignore case during search of term 'lorem'
* $('#content').highlight('lorem', { caseSensitive: true });
*
* // wrap every occurrance of term 'ipsum' in content
* // with
* $('#content').highlight('ipsum', { element: 'em', className: 'important' });
*
* // remove default highlight
* $('#content').unhighlight();
*
* // remove custom highlight
* $('#content').unhighlight({ element: 'em', className: 'important' });
*
*
* Copyright (c) 2009 Bartek Szopka
*
* Licensed under MIT license.
*
*/
jQuery.extend({
highlight: function(node, re, nodeName, className) {
if (node.nodeType === 3) {
var match = node.data.match(re);
if (match) {
var highlight = document.createElement(nodeName || "span");
highlight.className = className || "highlight";
var wordNode = node.splitText(match.index);
wordNode.splitText(match[0].length);
var wordClone = wordNode.cloneNode(true);
highlight.appendChild(wordClone);
wordNode.parentNode.replaceChild(highlight, wordNode);
return 1; //skip added node in parent
}
} else if (
node.nodeType === 1 &&
node.childNodes && // only element nodes that have children
!/(script|style)/i.test(node.tagName) && // ignore script and style nodes
!(node.tagName === nodeName.toUpperCase() && node.className === className)
) {
// skip if already highlighted
for (var i = 0; i < node.childNodes.length; i++) {
i += jQuery.highlight(node.childNodes[i], re, nodeName, className);
}
}
return 0;
}
});
jQuery.fn.unhighlight = function(options) {
var settings = { className: "highlight", element: "span" };
jQuery.extend(settings, options);
return this.find(settings.element + "." + settings.className)
.each(function() {
var parent = this.parentNode;
parent.replaceChild(this.firstChild, this);
parent.normalize();
})
.end();
};
jQuery.fn.highlight = function(words, options) {
var settings = {
className: "highlight",
element: "span",
caseSensitive: false,
wordsOnly: false
};
jQuery.extend(settings, options);
if (words.constructor === String) {
words = [words];
}
words = jQuery.grep(words, function(word, i) {
return word != "";
});
words = jQuery.map(words, function(word, i) {
return word.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&");
});
if (words.length == 0) {
return this;
}
var flag = settings.caseSensitive ? "" : "i";
var pattern = "(" + words.join("|") + ")";
if (settings.wordsOnly) {
pattern = "\\b" + pattern + "\\b";
}
var re = new RegExp(pattern, flag);
return this.each(function() {
jQuery.highlight(this, re, settings.element, settings.className);
});
};