From a78a80e2dffd1b33a8f2024fcf83e6bfc254c1fe Mon Sep 17 00:00:00 2001 From: Julian Prieber <60265788+JulianPrieber@users.noreply.github.com> Date: Mon, 9 May 2022 16:45:27 +0200 Subject: [PATCH] Fixed Button Editor not working on Touch devices Fixed button editor not working on Touch enabled devices such as smartphones. --- studio/button-editor/css/colorpicker.css | 164 + studio/button-editor/css/layout.css | 218 ++ studio/button-editor/images/blank.gif | Bin 0 -> 49 bytes studio/button-editor/js/colorpicker.js | 1005 ++--- studio/button-editor/js/eye.js | 28 + studio/button-editor/js/jquery.js | 4365 ++++++++++++++++++++++ studio/button-editor/js/layout.js | 67 + studio/button-editor/js/utils.js | 246 ++ 8 files changed, 5617 insertions(+), 476 deletions(-) create mode 100644 studio/button-editor/css/colorpicker.css create mode 100644 studio/button-editor/css/layout.css create mode 100644 studio/button-editor/images/blank.gif create mode 100644 studio/button-editor/js/eye.js create mode 100644 studio/button-editor/js/jquery.js create mode 100644 studio/button-editor/js/layout.js create mode 100644 studio/button-editor/js/utils.js diff --git a/studio/button-editor/css/colorpicker.css b/studio/button-editor/css/colorpicker.css new file mode 100644 index 0000000..da594b5 --- /dev/null +++ b/studio/button-editor/css/colorpicker.css @@ -0,0 +1,164 @@ +.colorpicker * { + -webkit-tap-highlight-color: rgba(0, 0, 0, 0); +} +.colorpicker { + width: 356px; + height: 176px; + overflow: hidden; + position: absolute; + background: url(../images/colorpicker_background.png); + font-family: Arial, Helvetica, sans-serif; + display: none; +} +.colorpicker_color { + width: 150px; + height: 150px; + left: 14px; + top: 13px; + position: absolute; + background: #f00; + overflow: hidden; + cursor: crosshair; +} +.colorpicker_color div { + position: absolute; + top: 0; + left: 0; + width: 150px; + height: 150px; + background: url(../images/colorpicker_overlay.png); +} +.colorpicker_color div div { + position: absolute; + top: 0; + left: 0; + width: 11px; + height: 11px; + overflow: hidden; + background: url(../images/colorpicker_select.gif); + margin: -5px 0 0 -5px; +} +.colorpicker_hue { + position: absolute; + top: 13px; + left: 171px; + width: 35px; + height: 150px; + cursor: n-resize; +} +.colorpicker_hue div { + position: absolute; + width: 35px; + height: 9px; + overflow: hidden; + background: url(../images/colorpicker_indic.gif) left top; + margin: -4px 0 0 0; + left: 0px; +} +.colorpicker_new_color { + position: absolute; + width: 60px; + height: 30px; + left: 213px; + top: 13px; + background: #f00; +} +.colorpicker_current_color { + position: absolute; + width: 60px; + height: 30px; + left: 283px; + top: 13px; + background: #f00; +} +.colorpicker input { + background-color: transparent; + border: 1px solid transparent; + position: absolute; + font-size: 10px; + font-family: Arial, Helvetica, sans-serif; + color: #898989; + top: 4px; + right: 11px; + text-align: right; + margin: 0; + padding: 0; + height: 11px; +} +.colorpicker_hex { + position: absolute; + width: 72px; + height: 22px; + background: url(../images/colorpicker_hex.png) top; + left: 212px; + top: 142px; +} +.colorpicker_hex input { + right: 6px; +} +.colorpicker_field { + height: 22px; + width: 62px; + background-position: top; + position: absolute; +} +.colorpicker_field span { + position: absolute; + width: 12px; + height: 22px; + overflow: hidden; + top: 0; + right: 0; + cursor: n-resize; +} +.colorpicker_rgb_r { + background-image: url(../images/colorpicker_rgb_r.png); + top: 52px; + left: 212px; +} +.colorpicker_rgb_g { + background-image: url(../images/colorpicker_rgb_g.png); + top: 82px; + left: 212px; +} +.colorpicker_rgb_b { + background-image: url(../images/colorpicker_rgb_b.png); + top: 112px; + left: 212px; +} +.colorpicker_hsb_h { + background-image: url(../images/colorpicker_hsb_h.png); + top: 52px; + left: 282px; +} +.colorpicker_hsb_s { + background-image: url(../images/colorpicker_hsb_s.png); + top: 82px; + left: 282px; +} +.colorpicker_hsb_b { + background-image: url(../images/colorpicker_hsb_b.png); + top: 112px; + left: 282px; +} +.colorpicker_submit { + position: absolute; + width: 22px; + height: 22px; + background: url(../images/colorpicker_submit.png) top; + left: 322px; + top: 142px; + overflow: hidden; +} +.colorpicker_focus { + background-position: center; +} +.colorpicker_hex.colorpicker_focus { + background-position: bottom; +} +.colorpicker_submit.colorpicker_focus { + background-position: bottom; +} +.colorpicker_slider { + background-position: bottom; +} diff --git a/studio/button-editor/css/layout.css b/studio/button-editor/css/layout.css new file mode 100644 index 0000000..cc5da1d --- /dev/null +++ b/studio/button-editor/css/layout.css @@ -0,0 +1,218 @@ +body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,form,fieldset,input,textarea,p,blockquote,th,td { + margin:0; + padding:0; +} +table { + border-collapse:collapse; + border-spacing:0; +} +fieldset,img { + border:0; +} +address,caption,cite,code,dfn,em,strong,th,var { + font-style:normal; + font-weight:normal; +} +ol,ul { + list-style:none; +} +caption,th { + text-align:left; +} +h1,h2,h3,h4,h5,h6 { + font-size:100%; + font-weight:normal; +} +q:before,q:after { + content:''; +} +abbr,acronym { border:0; +} +html, body { + background-color: #fff; + font-family: Arial, Helvetica, sans-serif; + font-size: 12px; + line-height: 18px; + color: #52697E; +} +body { + text-align: center; + overflow: auto; +} +.wrapper { + width: 700px; + margin: 0 auto; + text-align: left; +} +h1 { + font-size: 21px; + height: 47px; + line-height: 47px; + text-transform: uppercase; +} +.navigationTabs { + height: 23px; + line-height: 23px; + border-bottom: 1px solid #ccc; +} +.navigationTabs li { + float: left; + height: 23px; + line-height: 23px; + padding-right: 3px; +} +.navigationTabs li a{ + float: left; + dispaly: block; + height: 23px; + line-height: 23px; + padding: 0 10px; + overflow: hidden; + color: #52697E; + background-color: #eee; + position: relative; + text-decoration: none; +} +.navigationTabs li a:hover { + background-color: #f0f0f0; +} +.navigationTabs li a.active { + background-color: #fff; + border: 1px solid #ccc; + border-bottom: 0px solid; +} +.tabsContent { + border: 1px solid #ccc; + border-top: 0px solid; + width: 698px; + overflow: hidden; +} +.tab { + padding: 16px; + display: none; +} +.tab h2 { + font-weight: bold; + font-size: 16px; +} +.tab h3 { + font-weight: bold; + font-size: 14px; + margin-top: 20px; +} +.tab p { + margin-top: 16px; + clear: both; +} +.tab ul { + margin-top: 16px; + list-style: disc; +} +.tab li { + margin: 10px 0 0 35px; +} +.tab a { + color: #8FB0CF; +} +.tab strong { + font-weight: bold; +} +.tab pre { + font-size: 11px; + margin-top: 20px; + width: 668px; + overflow: auto; + clear: both; +} +.tab table { + width: 100%; +} +.tab table td { + padding: 6px 10px 6px 0; + vertical-align: top; +} +.tab dt { + margin-top: 16px; +} + +#colorSelector { + position: relative; + width: 36px; + height: 36px; + background: url(../images/select.png); +} +#colorSelector div { + position: absolute; + top: 3px; + left: 3px; + width: 30px; + height: 30px; + background: url(../images/select.png) center; +} +#colorSelector2 { + position: absolute; + top: 0; + left: 0; + width: 36px; + height: 36px; + background: url(../images/select2.png); +} +#colorSelector2 div { + position: absolute; + top: 4px; + left: 4px; + width: 28px; + height: 28px; + background: url(../images/select2.png) center; +} +#colorpickerHolder2 { + top: 32px; + left: 0; + width: 356px; + height: 0; + overflow: hidden; + position: absolute; +} +#colorpickerHolder2 .colorpicker { + background-image: url(../images/custom_background.png); + position: absolute; + bottom: 0; + left: 0; +} +#colorpickerHolder2 .colorpicker_hue div { + background-image: url(../images/custom_indic.gif); +} +#colorpickerHolder2 .colorpicker_hex { + background-image: url(../images/custom_hex.png); +} +#colorpickerHolder2 .colorpicker_rgb_r { + background-image: url(../images/custom_rgb_r.png); +} +#colorpickerHolder2 .colorpicker_rgb_g { + background-image: url(../images/custom_rgb_g.png); +} +#colorpickerHolder2 .colorpicker_rgb_b { + background-image: url(../images/custom_rgb_b.png); +} +#colorpickerHolder2 .colorpicker_hsb_s { + background-image: url(../images/custom_hsb_s.png); + display: none; +} +#colorpickerHolder2 .colorpicker_hsb_h { + background-image: url(../images/custom_hsb_h.png); + display: none; +} +#colorpickerHolder2 .colorpicker_hsb_b { + background-image: url(../images/custom_hsb_b.png); + display: none; +} +#colorpickerHolder2 .colorpicker_submit { + background-image: url(../images/custom_submit.png); +} +#colorpickerHolder2 .colorpicker input { + color: #778398; +} +#customWidget { + position: relative; + height: 36px; +} diff --git a/studio/button-editor/images/blank.gif b/studio/button-editor/images/blank.gif new file mode 100644 index 0000000000000000000000000000000000000000..75b945d2553848b8b6f41fe5e24599c0687b8472 GIT binary patch literal 49 zcmZ?wbhEHbWMp7unE0RJ|Ns9C3=9Vj8~~DvKUo+V7?>DzfNY>Fh|Ltj$Y2csQN9XW literal 0 HcmV?d00001 diff --git a/studio/button-editor/js/colorpicker.js b/studio/button-editor/js/colorpicker.js index 628e05c..505a642 100644 --- a/studio/button-editor/js/colorpicker.js +++ b/studio/button-editor/js/colorpicker.js @@ -1,476 +1,529 @@ -(function ($) { - var ColorPicker = function () { - var - ids = {}, - inAction, - charMin = 65, - visible, - tpl = '
', - defaults = { - eventName: 'click', - onShow: function () {}, - onBeforeShow: function(){}, - onHide: function () {}, - onChange: function () {}, - onSubmit: function () {}, - color: 'ff0000', - livePreview: true, - flat: false - }, - fillRGBFields = function (hsb, cal) { - var rgb = HSBToRGB(hsb); - $(cal).data('colorpicker').fields - .eq(1).val(rgb.r).end() - .eq(2).val(rgb.g).end() - .eq(3).val(rgb.b).end(); - }, - fillHSBFields = function (hsb, cal) { - $(cal).data('colorpicker').fields - .eq(4).val(hsb.h).end() - .eq(5).val(hsb.s).end() - .eq(6).val(hsb.b).end(); - }, - fillHexFields = function (hsb, cal) { - $(cal).data('colorpicker').fields - .eq(0).val(HSBToHex(hsb)).end(); - }, - setSelector = function (hsb, cal) { - $(cal).data('colorpicker').selector.css('backgroundColor', '#' + HSBToHex({h: hsb.h, s: 100, b: 100})); - $(cal).data('colorpicker').selectorIndic.css({ - left: parseInt(150 * hsb.s/100, 10), - top: parseInt(150 * (100-hsb.b)/100, 10) - }); - }, - setHue = function (hsb, cal) { - $(cal).data('colorpicker').hue.css('top', parseInt(150 - 150 * hsb.h/360, 10)); - }, - setCurrentColor = function (hsb, cal) { - $(cal).data('colorpicker').currentColor.css('backgroundColor', '#' + HSBToHex(hsb)); - }, - setNewColor = function (hsb, cal) { - $(cal).data('colorpicker').newColor.css('backgroundColor', '#' + HSBToHex(hsb)); - }, - keyDown = function (ev) { - var pressedKey = ev.charCode || ev.keyCode || -1; - if ((pressedKey > charMin && pressedKey <= 90) || pressedKey == 32) { - return false; - } - var cal = $(this).parent().parent(); - if (cal.data('colorpicker').livePreview === true) { - change.apply(this); - } - }, - change = function (ev) { - var cal = $(this).parent().parent(), col; - if (this.parentNode.className.indexOf('_hex') > 0) { - cal.data('colorpicker').color = col = HexToHSB(fixHex(this.value)); - } else if (this.parentNode.className.indexOf('_hsb') > 0) { - cal.data('colorpicker').color = col = fixHSB({ - h: parseInt(cal.data('colorpicker').fields.eq(4).val(), 10), - s: parseInt(cal.data('colorpicker').fields.eq(5).val(), 10), - b: parseInt(cal.data('colorpicker').fields.eq(6).val(), 10) - }); - } else { - cal.data('colorpicker').color = col = RGBToHSB(fixRGB({ - r: parseInt(cal.data('colorpicker').fields.eq(1).val(), 10), - g: parseInt(cal.data('colorpicker').fields.eq(2).val(), 10), - b: parseInt(cal.data('colorpicker').fields.eq(3).val(), 10) - })); - } - if (ev) { - fillRGBFields(col, cal.get(0)); - fillHexFields(col, cal.get(0)); - fillHSBFields(col, cal.get(0)); - } - setSelector(col, cal.get(0)); - setHue(col, cal.get(0)); - setNewColor(col, cal.get(0)); - cal.data('colorpicker').onChange.apply(cal, [col, HSBToHex(col), HSBToRGB(col)]); - }, - blur = function (ev) { - var cal = $(this).parent().parent(); - cal.data('colorpicker').fields.parent().removeClass('colorpicker_focus'); - }, - focus = function () { - charMin = this.parentNode.className.indexOf('_hex') > 0 ? 70 : 65; - $(this).parent().parent().data('colorpicker').fields.parent().removeClass('colorpicker_focus'); - $(this).parent().addClass('colorpicker_focus'); - }, - downIncrement = function (ev) { - var field = $(this).parent().find('input').focus(); - var current = { - el: $(this).parent().addClass('colorpicker_slider'), - max: this.parentNode.className.indexOf('_hsb_h') > 0 ? 360 : (this.parentNode.className.indexOf('_hsb') > 0 ? 100 : 255), - y: ev.pageY, - field: field, - val: parseInt(field.val(), 10), - preview: $(this).parent().parent().data('colorpicker').livePreview - }; - $(document).bind('mouseup', current, upIncrement); - $(document).bind('mousemove', current, moveIncrement); - }, - moveIncrement = function (ev) { - ev.data.field.val(Math.max(0, Math.min(ev.data.max, parseInt(ev.data.val + ev.pageY - ev.data.y, 10)))); - if (ev.data.preview) { - change.apply(ev.data.field.get(0), [true]); - } - return false; - }, - upIncrement = function (ev) { - change.apply(ev.data.field.get(0), [true]); - ev.data.el.removeClass('colorpicker_slider').find('input').focus(); - $(document).unbind('mouseup', upIncrement); - $(document).unbind('mousemove', moveIncrement); - return false; - }, - downHue = function (ev) { - var current = { - cal: $(this).parent(), - y: $(this).offset().top - }; - current.preview = current.cal.data('colorpicker').livePreview; - $(document).bind('mouseup', current, upHue); - $(document).bind('mousemove', current, moveHue); - }, - moveHue = function (ev) { - change.apply( - ev.data.cal.data('colorpicker') - .fields - .eq(4) - .val(parseInt(360*(150 - Math.max(0,Math.min(150,(ev.pageY - ev.data.y))))/150, 10)) - .get(0), - [ev.data.preview] - ); - return false; - }, - upHue = function (ev) { - fillRGBFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); - fillHexFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); - $(document).unbind('mouseup', upHue); - $(document).unbind('mousemove', moveHue); - return false; - }, - downSelector = function (ev) { - var current = { - cal: $(this).parent(), - pos: $(this).offset() - }; - current.preview = current.cal.data('colorpicker').livePreview; - $(document).bind('mouseup', current, upSelector); - $(document).bind('mousemove', current, moveSelector); - }, - moveSelector = function (ev) { - change.apply( - ev.data.cal.data('colorpicker') - .fields - .eq(6) - .val(parseInt(100*(150 - Math.max(0,Math.min(150,(ev.pageY - ev.data.pos.top))))/150, 10)) - .end() - .eq(5) - .val(parseInt(100*(Math.max(0,Math.min(150,(ev.pageX - ev.data.pos.left))))/150, 10)) - .get(0), - [ev.data.preview] - ); - return false; - }, - upSelector = function (ev) { - fillRGBFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); - fillHexFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); - $(document).unbind('mouseup', upSelector); - $(document).unbind('mousemove', moveSelector); - return false; - }, - enterSubmit = function (ev) { - $(this).addClass('colorpicker_focus'); - }, - leaveSubmit = function (ev) { - $(this).removeClass('colorpicker_focus'); - }, - clickSubmit = function (ev) { - var cal = $(this).parent(); - var col = cal.data('colorpicker').color; - cal.data('colorpicker').origColor = col; - setCurrentColor(col, cal.get(0)); - cal.data('colorpicker').onSubmit(col, HSBToHex(col), HSBToRGB(col), cal.data('colorpicker').el); - }, - show = function (ev) { - var cal = $('#' + $(this).data('colorpickerId')); - cal.data('colorpicker').onBeforeShow.apply(this, [cal.get(0)]); - var pos = $(this).offset(); - var viewPort = getViewport(); - var top = pos.top + this.offsetHeight; - var left = pos.left; - if (top + 176 > viewPort.t + viewPort.h) { - top -= this.offsetHeight + 176; - } - if (left + 356 > viewPort.l + viewPort.w) { - left -= 356; - } - cal.css({left: left + 'px', top: top + 'px'}); - if (cal.data('colorpicker').onShow.apply(this, [cal.get(0)]) != false) { - cal.show(); - } - $(document).bind('mousedown', {cal: cal}, hide); - return false; - }, - hide = function (ev) { - if (!isChildOf(ev.data.cal.get(0), ev.target, ev.data.cal.get(0))) { - if (ev.data.cal.data('colorpicker').onHide.apply(this, [ev.data.cal.get(0)]) != false) { - ev.data.cal.hide(); - } - $(document).unbind('mousedown', hide); - } - }, - isChildOf = function(parentEl, el, container) { - if (parentEl == el) { - return true; - } - if (parentEl.contains) { - return parentEl.contains(el); - } - if ( parentEl.compareDocumentPosition ) { - return !!(parentEl.compareDocumentPosition(el) & 16); - } - var prEl = el.parentNode; - while(prEl && prEl != container) { - if (prEl == parentEl) - return true; - prEl = prEl.parentNode; - } - return false; - }, - getViewport = function () { - var m = document.compatMode == 'CSS1Compat'; - return { - l : window.pageXOffset || (m ? document.documentElement.scrollLeft : document.body.scrollLeft), - t : window.pageYOffset || (m ? document.documentElement.scrollTop : document.body.scrollTop), - w : window.innerWidth || (m ? document.documentElement.clientWidth : document.body.clientWidth), - h : window.innerHeight || (m ? document.documentElement.clientHeight : document.body.clientHeight) - }; - }, - fixHSB = function (hsb) { - return { - h: Math.min(360, Math.max(0, hsb.h)), - s: Math.min(100, Math.max(0, hsb.s)), - b: Math.min(100, Math.max(0, hsb.b)) - }; - }, - fixRGB = function (rgb) { - return { - r: Math.min(255, Math.max(0, rgb.r)), - g: Math.min(255, Math.max(0, rgb.g)), - b: Math.min(255, Math.max(0, rgb.b)) - }; - }, - fixHex = function (hex) { - var len = 6 - hex.length; - if (len > 0) { - var o = []; - for (var i=0; i -1) ? hex.substring(1) : hex), 16); - return {r: hex >> 16, g: (hex & 0x00FF00) >> 8, b: (hex & 0x0000FF)}; - }, - HexToHSB = function (hex) { - return RGBToHSB(HexToRGB(hex)); - }, - RGBToHSB = function (rgb) { - var hsb = { - h: 0, - s: 0, - b: 0 - }; - var min = Math.min(rgb.r, rgb.g, rgb.b); - var max = Math.max(rgb.r, rgb.g, rgb.b); - var delta = max - min; - hsb.b = max; - if (max != 0) { - - } - hsb.s = max != 0 ? 255 * delta / max : 0; - if (hsb.s != 0) { - if (rgb.r == max) { - hsb.h = (rgb.g - rgb.b) / delta; - } else if (rgb.g == max) { - hsb.h = 2 + (rgb.b - rgb.r) / delta; - } else { - hsb.h = 4 + (rgb.r - rgb.g) / delta; - } - } else { - hsb.h = -1; - } - hsb.h *= 60; - if (hsb.h < 0) { - hsb.h += 360; - } - hsb.s *= 100/255; - hsb.b *= 100/255; - return hsb; - }, - HSBToRGB = function (hsb) { - var rgb = {}; - var h = Math.round(hsb.h); - var s = Math.round(hsb.s*255/100); - var v = Math.round(hsb.b*255/100); - if(s == 0) { - rgb.r = rgb.g = rgb.b = v; - } else { - var t1 = v; - var t2 = (255-s)*v/255; - var t3 = (t1-t2)*(h%60)/60; - if(h==360) h = 0; - if(h<60) {rgb.r=t1; rgb.b=t2; rgb.g=t2+t3} - else if(h<120) {rgb.g=t1; rgb.b=t2; rgb.r=t1-t3} - else if(h<180) {rgb.g=t1; rgb.r=t2; rgb.b=t2+t3} - else if(h<240) {rgb.b=t1; rgb.r=t2; rgb.g=t1-t3} - else if(h<300) {rgb.b=t1; rgb.g=t2; rgb.r=t2+t3} - else if(h<360) {rgb.r=t1; rgb.g=t2; rgb.b=t1-t3} - else {rgb.r=0; rgb.g=0; rgb.b=0} - } - return {r:Math.round(rgb.r), g:Math.round(rgb.g), b:Math.round(rgb.b)}; - }, - RGBToHex = function (rgb) { - var hex = [ - rgb.r.toString(16), - rgb.g.toString(16), - rgb.b.toString(16) - ]; - $.each(hex, function (nr, val) { - if (val.length == 1) { - hex[nr] = '0' + val; - } - }); - return hex.join(''); - }, - HSBToHex = function (hsb) { - return RGBToHex(HSBToRGB(hsb)); - }, - restoreOriginal = function () { - var cal = $(this).parent(); - var col = cal.data('colorpicker').origColor; - cal.data('colorpicker').color = col; - fillRGBFields(col, cal.get(0)); - fillHexFields(col, cal.get(0)); - fillHSBFields(col, cal.get(0)); - setSelector(col, cal.get(0)); - setHue(col, cal.get(0)); - setNewColor(col, cal.get(0)); - }; - return { - init: function (opt) { - opt = $.extend({}, defaults, opt||{}); - if (typeof opt.color == 'string') { - opt.color = HexToHSB(opt.color); - } else if (opt.color.r != undefined && opt.color.g != undefined && opt.color.b != undefined) { - opt.color = RGBToHSB(opt.color); - } else if (opt.color.h != undefined && opt.color.s != undefined && opt.color.b != undefined) { - opt.color = fixHSB(opt.color); - } else { - return this; - } - return this.each(function () { - if (!$(this).data('colorpickerId')) { - var options = $.extend({}, opt); - options.origColor = opt.color; - var id = 'collorpicker_' + parseInt(Math.random() * 1000); - $(this).data('colorpickerId', id); - var cal = $(tpl).attr('id', id); - if (options.flat) { - cal.appendTo(this).show(); - } else { - cal.appendTo(document.body); - } - options.fields = cal - .find('input') - .bind('keyup', keyDown) - .bind('change', change) - .bind('blur', blur) - .bind('focus', focus); - cal - .find('span').bind('mousedown', downIncrement).end() - .find('>div.colorpicker_current_color').bind('click', restoreOriginal); - options.selector = cal.find('div.colorpicker_color').bind('mousedown', downSelector); - options.selectorIndic = options.selector.find('div div'); - options.el = this; - options.hue = cal.find('div.colorpicker_hue div'); - cal.find('div.colorpicker_hue').bind('mousedown', downHue); - options.newColor = cal.find('div.colorpicker_new_color'); - options.currentColor = cal.find('div.colorpicker_current_color'); - cal.data('colorpicker', options); - cal.find('div.colorpicker_submit') - .bind('mouseenter', enterSubmit) - .bind('mouseleave', leaveSubmit) - .bind('click', clickSubmit); - fillRGBFields(options.color, cal.get(0)); - fillHSBFields(options.color, cal.get(0)); - fillHexFields(options.color, cal.get(0)); - setHue(options.color, cal.get(0)); - setSelector(options.color, cal.get(0)); - setCurrentColor(options.color, cal.get(0)); - setNewColor(options.color, cal.get(0)); - if (options.flat) { - cal.css({ - position: 'relative', - display: 'block' - }); - } else { - $(this).bind(options.eventName, show); - } - } - }); - }, - showPicker: function() { - return this.each( function () { - if ($(this).data('colorpickerId')) { - show.apply(this); - } - }); - }, - hidePicker: function() { - return this.each( function () { - if ($(this).data('colorpickerId')) { - $('#' + $(this).data('colorpickerId')).hide(); - } - }); - }, - setColor: function(col) { - if (typeof col == 'string') { - col = HexToHSB(col); - } else if (col.r != undefined && col.g != undefined && col.b != undefined) { - col = RGBToHSB(col); - } else if (col.h != undefined && col.s != undefined && col.b != undefined) { - col = fixHSB(col); - } else { - return this; - } - return this.each(function(){ - if ($(this).data('colorpickerId')) { - var cal = $('#' + $(this).data('colorpickerId')); - cal.data('colorpicker').color = col; - cal.data('colorpicker').origColor = col; - fillRGBFields(col, cal.get(0)); - fillHSBFields(col, cal.get(0)); - fillHexFields(col, cal.get(0)); - setHue(col, cal.get(0)); - setSelector(col, cal.get(0)); - setCurrentColor(col, cal.get(0)); - setNewColor(col, cal.get(0)); - } - }); - } - }; - }(); - $.fn.extend({ - ColorPicker: ColorPicker.init, - ColorPickerHide: ColorPicker.hidePicker, - ColorPickerShow: ColorPicker.showPicker, - ColorPickerSetColor: ColorPicker.setColor - }); -})(jQuery) \ No newline at end of file + (function($) { + var ColorPicker = function() { + var ids = {}, + inAction, + charMin = 65, + visible, + tpl = '
', + defaults = { + eventName: 'click', + onShow: function() {}, + onBeforeShow: function() {}, + onHide: function() {}, + onChange: function() {}, + onSubmit: function() {}, + color: 'ff0000', + livePreview: true, + flat: false + }, + fillRGBFields = function(hsb, cal) { + var rgb = HSBToRGB(hsb); + $(cal).data('colorpicker').fields.eq(1).val(rgb.r).end().eq(2).val(rgb.g).end().eq(3).val(rgb.b).end(); + }, + fillHSBFields = function(hsb, cal) { + $(cal).data('colorpicker').fields.eq(4).val(hsb.h).end().eq(5).val(hsb.s).end().eq(6).val(hsb.b).end(); + }, + fillHexFields = function(hsb, cal) { + $(cal).data('colorpicker').fields.eq(0).val(HSBToHex(hsb)).end(); + }, + setSelector = function(hsb, cal) { + $(cal).data('colorpicker').selector.css('backgroundColor', '#' + HSBToHex({ + h: hsb.h, + s: 100, + b: 100 + })); + $(cal).data('colorpicker').selectorIndic.css({ + left: parseInt(150 * hsb.s / 100, 10), + top: parseInt(150 * (100 - hsb.b) / 100, 10) + }); + }, + setHue = function(hsb, cal) { + $(cal).data('colorpicker').hue.css('top', parseInt(150 - 150 * hsb.h / 360, 10)); + }, + setCurrentColor = function(hsb, cal) { + $(cal).data('colorpicker').currentColor.css('backgroundColor', '#' + HSBToHex(hsb)); + }, + setNewColor = function(hsb, cal) { + $(cal).data('colorpicker').newColor.css('backgroundColor', '#' + HSBToHex(hsb)); + }, + keyDown = function(ev) { + var pressedKey = ev.charCode || ev.keyCode || -1; + if ((pressedKey > charMin && pressedKey <= 90) || pressedKey == 32) { + return false; + } + var cal = $(this).parent().parent(); + if (cal.data('colorpicker').livePreview === true) { + change.apply(this); + } + }, + change = function(ev) { + var cal = $(this).parent().parent(), + col; + if (this.parentNode.className.indexOf('_hex') > 0) { + cal.data('colorpicker').color = col = HexToHSB(fixHex(this.value)); + } else if (this.parentNode.className.indexOf('_hsb') > 0) { + cal.data('colorpicker').color = col = fixHSB({ + h: parseInt(cal.data('colorpicker').fields.eq(4).val(), 10), + s: parseInt(cal.data('colorpicker').fields.eq(5).val(), 10), + b: parseInt(cal.data('colorpicker').fields.eq(6).val(), 10) + }); + } else { + cal.data('colorpicker').color = col = RGBToHSB(fixRGB({ + r: parseInt(cal.data('colorpicker').fields.eq(1).val(), 10), + g: parseInt(cal.data('colorpicker').fields.eq(2).val(), 10), + b: parseInt(cal.data('colorpicker').fields.eq(3).val(), 10) + })); + } + if (ev) { + fillRGBFields(col, cal.get(0)); + fillHexFields(col, cal.get(0)); + fillHSBFields(col, cal.get(0)); + } + setSelector(col, cal.get(0)); + setHue(col, cal.get(0)); + setNewColor(col, cal.get(0)); + cal.data('colorpicker').onChange.apply(cal, [col, HSBToHex(col), HSBToRGB(col)]); + }, + blur = function(ev) { + var cal = $(this).parent().parent(); + cal.data('colorpicker').fields.parent().removeClass('colorpicker_focus'); + }, + focus = function() { + charMin = this.parentNode.className.indexOf('_hex') > 0 ? 70: 65; + $(this).parent().parent().data('colorpicker').fields.parent().removeClass('colorpicker_focus'); + $(this).parent().addClass('colorpicker_focus'); + }, + downIncrement = function(ev) { + var field = $(this).parent().find('input').focus(); + var current = { + el: $(this).parent().addClass('colorpicker_slider'), + max: this.parentNode.className.indexOf('_hsb_h') > 0 ? 360: (this.parentNode.className.indexOf('_hsb') > 0 ? 100: 255), + y: ev.pageY, + field: field, + val: parseInt(field.val(), 10), + preview: $(this).parent().parent().data('colorpicker').livePreview + }; + $(document).bind('mouseup', current, upIncrement); + $(document).bind('mousemove', current, moveIncrement); + }, + moveIncrement = function(ev) { + ev.data.field.val(Math.max(0, Math.min(ev.data.max, parseInt(ev.data.val + ev.pageY - ev.data.y, 10)))); + if (ev.data.preview) { + change.apply(ev.data.field.get(0), [true]); + } + return false; + }, + upIncrement = function(ev) { + change.apply(ev.data.field.get(0), [true]); + ev.data.el.removeClass('colorpicker_slider').find('input').focus(); + $(document).unbind('mouseup', upIncrement); + $(document).unbind('mousemove', moveIncrement); + return false; + }, + downHue = function(ev) { + // prevent android from highlighting the hue selector on click + ev.preventDefault(); + + var moveEvent = ev; + if (typeof(event) !== "undefined" && event.touches) { + moveEvent = event.touches[0]; + } + + var current = { + cal: $(this).parent(), + y: $(this).offset().top + }; + current.preview = current.cal.data('colorpicker').livePreview; + $(document).bind('mouseup touchend', current, upHue); + $(document).bind('mousemove touchmove', current, moveHue); + + changeHue(moveEvent, current, current.preview); + return false; + }, + changeHue = function(ev, data, preview) { + change.apply(data.cal.data('colorpicker').fields.eq(4).val(parseInt(360 * (150 - Math.max(0, Math.min(150, ev.pageY - data.y))) / 150, 10)).get(0), [preview]); + }, + moveHue = function(ev) { + var moveEvent = ev; + + // mobile touch event! + if (typeof(event) !== "undefined" && event.touches) { + moveEvent = event.touches[0]; + } + changeHue(moveEvent, ev.data, ev.data.preview); + return false; + }, + upHue = function(ev) { + fillRGBFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); + fillHexFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); + $(document).unbind('mouseup touchend', upHue); + $(document).unbind('mousemove touchmove', moveHue); + return false; + }, + downSelector = function(ev) { + // prevent android from highlighting the selector on click + ev.preventDefault(); + var current = { + cal: $(this).parent(), + pos: $(this).offset() + }; + current.preview = current.cal.data('colorpicker').livePreview; + $(document).bind('mouseup touchend', current, upSelector); + $(document).bind('mousemove touchmove', current, moveSelector); + + $(".colorpicker_color", current.cal).one('click', current, moveSelector); + ev.data = current; + moveSelector(ev); + }, + moveSelector = function(ev) { + var moveEvent = ev; + + // mobile touch event! + if (typeof(event) !== "undefined" && event.touches) { + moveEvent = event.touches[0]; + } + + change.apply(ev.data.cal.data('colorpicker').fields.eq(6).val(parseInt(100 * (150 - Math.max(0, Math.min(150, (moveEvent.pageY - ev.data.pos.top)))) / 150, 10)).end().eq(5).val(parseInt(100 * (Math.max(0, Math.min(150, (moveEvent.pageX - ev.data.pos.left)))) / 150, 10)).get(0), [ev.data.preview]); + return false; + }, + upSelector = function(ev) { + fillRGBFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); + fillHexFields(ev.data.cal.data('colorpicker').color, ev.data.cal.get(0)); + $(document).unbind('mouseup touchend', upSelector); + $(document).unbind('mousemove touchmove', moveSelector); + return false; + }, + enterSubmit = function(ev) { + $(this).addClass('colorpicker_focus'); + }, + leaveSubmit = function(ev) { + $(this).removeClass('colorpicker_focus'); + }, + clickSubmit = function(ev) { + var cal = $(this).parent(); + var col = cal.data('colorpicker').color; + cal.data('colorpicker').origColor = col; + setCurrentColor(col, cal.get(0)); + cal.data('colorpicker').onSubmit(col, HSBToHex(col), HSBToRGB(col), cal.data('colorpicker').el); + }, + toggle = function(ev) { + var $body = $('body'), + current = $body.data('colorpickerId'), + me = $(this).data('colorpickerId'); + if ( current && current === me ) { + $(document).trigger('mousedown'); + $body.data('colorpickerId', null ); + } else { + show.call(this, ev); + $body.data('colorpickerId', me ); + } + }, + show = function(ev) { + var cal = $('#' + $(this).data('colorpickerId')); + cal.data('colorpicker').onBeforeShow.apply(this, [cal.get(0)]); + var pos = $(this).offset(); + var viewPort = getViewport(); + var top = pos.top + this.offsetHeight; + var left = pos.left; + if (top + 176 > viewPort.t + viewPort.h) { + top -= this.offsetHeight + 176; + } + if (left + 356 > viewPort.l + viewPort.w) { + left = Math.max(0, left - 356); + } + cal.css({ + left: left + 'px', + top: top + 'px' + }); + if (cal.data('colorpicker').onShow.apply(this, [cal.get(0)]) != false) { + cal.show(); + } + $(document).bind('mousedown', { + cal: cal + }, hide); + return false; + }, + hide = function(ev) { + if (!isChildOf(ev.data.cal.get(0), ev.target, ev.data.cal.get(0))) { + if (ev.data.cal.data('colorpicker').onHide.apply(this, [ev.data.cal.get(0)]) != false) { + ev.data.cal.hide(); + } + if (!isChildOf($(ev.data.cal[0]).data("colorpicker")["el"], ev.target)) { + $('body').data('colorpickerId', null); + } + $(document).unbind('mousedown', hide); + } + }, + isChildOf = function(parentEl, el, container) { + if (parentEl == el) { + return true; + } + if (parentEl.contains) { + return parentEl.contains(el); + } + if (parentEl.compareDocumentPosition) { + return !! (parentEl.compareDocumentPosition(el) & 16); + } + var prEl = el.parentNode; + while (prEl && prEl != container) { + if (prEl == parentEl) + return true; + prEl = prEl.parentNode; + } + return false; + }, + getViewport = function() { + var m = document.compatMode == 'CSS1Compat'; + return { + l: window.pageXOffset || (m ? document.documentElement.scrollLeft: document.body.scrollLeft), + t: window.pageYOffset || (m ? document.documentElement.scrollTop: document.body.scrollTop), + w: window.innerWidth || (m ? document.documentElement.clientWidth: document.body.clientWidth), + h: window.innerHeight || (m ? document.documentElement.clientHeight: document.body.clientHeight) + }; + }, + fixHSB = function(hsb) { + return { + h: Math.round( Math.min(360, Math.max(0, hsb.h)) ), + s: Math.round( Math.min(100, Math.max(0, hsb.s)) ), + b: Math.round( Math.min(100, Math.max(0, hsb.b)) ) + }; + }, + fixRGB = function(rgb) { + return { + r: Math.min(255, Math.max(0, rgb.r)), + g: Math.min(255, Math.max(0, rgb.g)), + b: Math.min(255, Math.max(0, rgb.b)) + }; + }, + fixHex = function(hex) { + var len = 6 - hex.length; + if (len > 0) { + var o = []; + for (var i = 0; i < len; i++) { + o.push('0'); + } + o.push(hex); + hex = o.join(''); + } + return hex; + }, + HexToRGB = function(hex) { + var hex = parseInt(((hex.indexOf('#') > -1) ? hex.substring(1) : hex), 16); + return { + r: hex >> 16, + g: (hex & 0x00FF00) >> 8, + b: (hex & 0x0000FF) + }; + }, + HexToHSB = function(hex) { + return RGBToHSB(HexToRGB(hex)); + }, + RGBToHSB = function(rgb) { + var hsb = { + h: 0, + s: 0, + b: 0 + }; + var min = Math.min(rgb.r, rgb.g, rgb.b); + var max = Math.max(rgb.r, rgb.g, rgb.b); + var delta = max - min; + hsb.b = max; + if (max != 0) { +} + hsb.s = max != 0 ? 255 * delta / max: 0; + if (hsb.s != 0) { + if (rgb.r == max) { + hsb.h = (rgb.g - rgb.b) / delta; + } else if (rgb.g == max) { + hsb.h = 2 + (rgb.b - rgb.r) / delta; + } else { + hsb.h = 4 + (rgb.r - rgb.g) / delta; + } + } else { + hsb.h = -1; + } + hsb.h *= 60; + if (hsb.h < 0) { + hsb.h += 360; + } + hsb.s *= 100 / 255; + hsb.b *= 100 / 255; + + hsb.h = Math.round ( hsb.h ); + hsb.s = Math.round ( hsb.s ); + hsb.b = Math.round ( hsb.b ); + return hsb; + }, + HSBToRGB = function(hsb) { + var rgb = {}; + var h = Math.round(hsb.h); + var s = Math.round(hsb.s * 255 / 100); + var v = Math.round(hsb.b * 255 / 100); + if (s == 0) { + rgb.r = rgb.g = rgb.b = v; + } else { + var t1 = v; + var t2 = (255 - s) * v / 255; + var t3 = (t1 - t2) * (h % 60) / 60; + if (h == 360) + h = 0; + if (h < 60) { + rgb.r = t1; + rgb.b = t2; + rgb.g = t2 + t3 + } else if (h < 120) { + rgb.g = t1; + rgb.b = t2; + rgb.r = t1 - t3 + } else if (h < 180) { + rgb.g = t1; + rgb.r = t2; + rgb.b = t2 + t3 + } else if (h < 240) { + rgb.b = t1; + rgb.r = t2; + rgb.g = t1 - t3 + } else if (h < 300) { + rgb.b = t1; + rgb.g = t2; + rgb.r = t2 + t3 + } else if (h < 360) { + rgb.r = t1; + rgb.g = t2; + rgb.b = t1 - t3 + } else { + rgb.r = 0; + rgb.g = 0; + rgb.b = 0 + } + } + return { + r: Math.round(rgb.r), + g: Math.round(rgb.g), + b: Math.round(rgb.b) + }; + }, + RGBToHex = function(rgb) { + var hex = [rgb.r.toString(16), rgb.g.toString(16), rgb.b.toString(16)]; + $.each(hex, function(nr, val) { + if (val.length == 1) { + hex[nr] = '0' + val; + } + }); + return hex.join(''); + }, + HSBToHex = function(hsb) { + return RGBToHex(HSBToRGB(hsb)); + }, + restoreOriginal = function() { + var cal = $(this).parent(); + var col = cal.data('colorpicker').origColor; + cal.data('colorpicker').color = col; + fillRGBFields(col, cal.get(0)); + fillHexFields(col, cal.get(0)); + fillHSBFields(col, cal.get(0)); + setSelector(col, cal.get(0)); + setHue(col, cal.get(0)); + setNewColor(col, cal.get(0)); + }; + return { + init: function(opt) { + opt = $.extend({}, defaults, opt || {}); + if (typeof opt.color == 'string') { + opt.color = HexToHSB(opt.color); + } else if (opt.color.r != undefined && opt.color.g != undefined && opt.color.b != undefined) { + opt.color = RGBToHSB(opt.color); + } else if (opt.color.h != undefined && opt.color.s != undefined && opt.color.b != undefined) { + opt.color = fixHSB(opt.color); + } else { + return this; + } + return this.each(function() { + if (!$(this).data('colorpickerId')) { + var options = $.extend({}, opt); + options.origColor = opt.color; + var id = 'colorpicker_' + ($(this).attr('id') || parseInt(Math.random() * 1000)); + $(this).data('colorpickerId', id); + var cal = $(tpl).attr('id', id); + if (options.flat) { + cal.appendTo(this).show(); + } else { + cal.appendTo(document.body); + } + options.fields = cal.find('input').bind('keyup', keyDown).bind('change', change).bind('blur', blur).bind('focus', focus); + cal.find('span').bind('mousedown touchstart', downIncrement).end().find('>div.colorpicker_current_color').bind('click', restoreOriginal); + options.selector = cal.find('div.colorpicker_color').bind('touchstart mousedown', downSelector); + options.selectorIndic = options.selector.find('div div'); + options.el = this; + options.hue = cal.find('div.colorpicker_hue div'); + cal.find('div.colorpicker_hue').bind('mousedown touchstart', downHue); + options.newColor = cal.find('div.colorpicker_new_color'); + options.currentColor = cal.find('div.colorpicker_current_color'); + cal.data('colorpicker', options); + cal.find('div.colorpicker_submit').bind('mouseenter touchstart', enterSubmit).bind('mouseleave touchend', leaveSubmit).bind('click', clickSubmit); + fillRGBFields(options.color, cal.get(0)); + fillHSBFields(options.color, cal.get(0)); + fillHexFields(options.color, cal.get(0)); + setHue(options.color, cal.get(0)); + setSelector(options.color, cal.get(0)); + setCurrentColor(options.color, cal.get(0)); + setNewColor(options.color, cal.get(0)); + if (options.flat) { + cal.css({ + position: 'relative', + display: 'block' + }); + } else { + $(this).bind(options.eventName, toggle); + } + } + }); + }, + showPicker: function() { + return this.each(function() { + if ($(this).data('colorpickerId')) { + show.apply(this); + } + }); + }, + hidePicker: function() { + return this.each(function() { + if ($(this).data('colorpickerId')) { + $('#' + $(this).data('colorpickerId')).hide(); + } + }); + }, + setColor: function(col) { + if (typeof col == 'string') { + col = HexToHSB(col); + } else if (col.r != undefined && col.g != undefined && col.b != undefined) { + col = RGBToHSB(col); + } else if (col.h != undefined && col.s != undefined && col.b != undefined) { + col = fixHSB(col); + } else { + return this; + } + return this.each(function() { + if ($(this).data('colorpickerId')) { + var cal = $('#' + $(this).data('colorpickerId')); + cal.data('colorpicker').color = col; + cal.data('colorpicker').origColor = col; + fillRGBFields(col, cal.get(0)); + fillHSBFields(col, cal.get(0)); + fillHexFields(col, cal.get(0)); + setHue(col, cal.get(0)); + setSelector(col, cal.get(0)); + setCurrentColor(col, cal.get(0)); + setNewColor(col, cal.get(0)); + } + }); + } + }; + } (); + $.fn.extend({ + ColorPicker: ColorPicker.init, + ColorPickerHide: ColorPicker.hidePicker, + ColorPickerShow: ColorPicker.showPicker, + ColorPickerSetColor: ColorPicker.setColor + }); +})(jQuery) diff --git a/studio/button-editor/js/eye.js b/studio/button-editor/js/eye.js new file mode 100644 index 0000000..2556ec5 --- /dev/null +++ b/studio/button-editor/js/eye.js @@ -0,0 +1,28 @@ +(function($){ + var EYE = window.EYE = function() { + var _registered = { + init: [] + }; + return { + init: function() { + $.each(_registered.init, function(nr, fn){ + fn.call(); + }); + }, + extend: function(prop) { + for (var i in prop) { + if (prop[i] != undefined) { + this[i] = prop[i]; + } + } + }, + register: function(fn, type) { + if (!_registered[type]) { + _registered[type] = []; + } + _registered[type].push(fn); + } + }; + }(); + $(EYE.init); +})(jQuery); diff --git a/studio/button-editor/js/jquery.js b/studio/button-editor/js/jquery.js new file mode 100644 index 0000000..009265c --- /dev/null +++ b/studio/button-editor/js/jquery.js @@ -0,0 +1,4365 @@ +(function(){ + +var + // Will speed up references to window, and allows munging its name. + window = this, + // Will speed up references to undefined, and allows munging its name. + undefined, + // Map over jQuery in case of overwrite + _jQuery = window.jQuery, + // Map over the $ in case of overwrite + _$ = window.$, + + jQuery = window.jQuery = window.$ = function( selector, context ) { + // The jQuery object is actually just the init constructor 'enhanced' + return new jQuery.fn.init( selector, context ); + }, + + // A simple way to check for HTML strings or ID strings + // (both of which we optimize for) + quickExpr = /^[^<]*(<(.|\s)+>)[^>]*$|^#([\w-]+)$/, + // Is it a simple selector + isSimple = /^.[^:#\[\.,]*$/; + +jQuery.fn = jQuery.prototype = { + init: function( selector, context ) { + // Make sure that a selection was provided + selector = selector || document; + + // Handle $(DOMElement) + if ( selector.nodeType ) { + this[0] = selector; + this.length = 1; + this.context = selector; + return this; + } + // Handle HTML strings + if ( typeof selector === "string" ) { + // Are we dealing with HTML string or an ID? + var match = quickExpr.exec( selector ); + + // Verify a match, and that no context was specified for #id + if ( match && (match[1] || !context) ) { + + // HANDLE: $(html) -> $(array) + if ( match[1] ) + selector = jQuery.clean( [ match[1] ], context ); + + // HANDLE: $("#id") + else { + var elem = document.getElementById( match[3] ); + + // Handle the case where IE and Opera return items + // by name instead of ID + if ( elem && elem.id != match[3] ) + return jQuery().find( selector ); + + // Otherwise, we inject the element directly into the jQuery object + var ret = jQuery( elem || [] ); + ret.context = document; + ret.selector = selector; + return ret; + } + + // HANDLE: $(expr, [context]) + // (which is just equivalent to: $(content).find(expr) + } else + return jQuery( context ).find( selector ); + + // HANDLE: $(function) + // Shortcut for document ready + } else if ( jQuery.isFunction( selector ) ) + return jQuery( document ).ready( selector ); + + // Make sure that old selector state is passed along + if ( selector.selector && selector.context ) { + this.selector = selector.selector; + this.context = selector.context; + } + + return this.setArray(jQuery.isArray( selector ) ? + selector : + jQuery.makeArray(selector)); + }, + + // Start with an empty selector + selector: "", + + // The current version of jQuery being used + jquery: "1.3.2", + + // The number of elements contained in the matched element set + size: function() { + return this.length; + }, + + // Get the Nth element in the matched element set OR + // Get the whole matched element set as a clean array + get: function( num ) { + return num === undefined ? + + // Return a 'clean' array + Array.prototype.slice.call( this ) : + + // Return just the object + this[ num ]; + }, + + // Take an array of elements and push it onto the stack + // (returning the new matched element set) + pushStack: function( elems, name, selector ) { + // Build a new jQuery matched element set + var ret = jQuery( elems ); + + // Add the old object onto the stack (as a reference) + ret.prevObject = this; + + ret.context = this.context; + + if ( name === "find" ) + ret.selector = this.selector + (this.selector ? " " : "") + selector; + else if ( name ) + ret.selector = this.selector + "." + name + "(" + selector + ")"; + + // Return the newly-formed element set + return ret; + }, + + // Force the current matched set of elements to become + // the specified array of elements (destroying the stack in the process) + // You should use pushStack() in order to do this, but maintain the stack + setArray: function( elems ) { + // Resetting the length to 0, then using the native Array push + // is a super-fast way to populate an object with array-like properties + this.length = 0; + Array.prototype.push.apply( this, elems ); + + return this; + }, + + // Execute a callback for every element in the matched set. + // (You can seed the arguments with an array of args, but this is + // only used internally.) + each: function( callback, args ) { + return jQuery.each( this, callback, args ); + }, + + // Determine the position of an element within + // the matched set of elements + index: function( elem ) { + // Locate the position of the desired element + return jQuery.inArray( + // If it receives a jQuery object, the first element is used + elem && elem.jquery ? elem[0] : elem + , this ); + }, + + attr: function( name, value, type ) { + var options = name; + + // Look for the case where we're accessing a style value + if ( typeof name === "string" ) + if ( value === undefined ) + return this[0] && jQuery[ type || "attr" ]( this[0], name ); + + else { + options = {}; + options[ name ] = value; + } + + // Check to see if we're setting style values + return this.each(function(i){ + // Set all the styles + for ( name in options ) + jQuery.attr( + type ? + this.style : + this, + name, jQuery.prop( this, options[ name ], type, i, name ) + ); + }); + }, + + css: function( key, value ) { + // ignore negative width and height values + if ( (key == 'width' || key == 'height') && parseFloat(value) < 0 ) + value = undefined; + return this.attr( key, value, "curCSS" ); + }, + + text: function( text ) { + if ( typeof text !== "object" && text != null ) + return this.empty().append( (this[0] && this[0].ownerDocument || document).createTextNode( text ) ); + + var ret = ""; + + jQuery.each( text || this, function(){ + jQuery.each( this.childNodes, function(){ + if ( this.nodeType != 8 ) + ret += this.nodeType != 1 ? + this.nodeValue : + jQuery.fn.text( [ this ] ); + }); + }); + + return ret; + }, + + wrapAll: function( html ) { + if ( this[0] ) { + // The elements to wrap the target around + var wrap = jQuery( html, this[0].ownerDocument ).clone(); + + if ( this[0].parentNode ) + wrap.insertBefore( this[0] ); + + wrap.map(function(){ + var elem = this; + + while ( elem.firstChild ) + elem = elem.firstChild; + + return elem; + }).append(this); + } + + return this; + }, + + wrapInner: function( html ) { + return this.each(function(){ + jQuery( this ).contents().wrapAll( html ); + }); + }, + + wrap: function( html ) { + return this.each(function(){ + jQuery( this ).wrapAll( html ); + }); + }, + + append: function() { + return this.domManip(arguments, true, function(elem){ + if (this.nodeType == 1) + this.appendChild( elem ); + }); + }, + + prepend: function() { + return this.domManip(arguments, true, function(elem){ + if (this.nodeType == 1) + this.insertBefore( elem, this.firstChild ); + }); + }, + + before: function() { + return this.domManip(arguments, false, function(elem){ + this.parentNode.insertBefore( elem, this ); + }); + }, + + after: function() { + return this.domManip(arguments, false, function(elem){ + this.parentNode.insertBefore( elem, this.nextSibling ); + }); + }, + + end: function() { + return this.prevObject || jQuery( [] ); + }, + + // For internal use only. + // Behaves like an Array's method, not like a jQuery method. + push: [].push, + sort: [].sort, + splice: [].splice, + + find: function( selector ) { + if ( this.length === 1 ) { + var ret = this.pushStack( [], "find", selector ); + ret.length = 0; + jQuery.find( selector, this[0], ret ); + return ret; + } else { + return this.pushStack( jQuery.unique(jQuery.map(this, function(elem){ + return jQuery.find( selector, elem ); + })), "find", selector ); + } + }, + + clone: function( events ) { + // Do the clone + var ret = this.map(function(){ + if ( !jQuery.support.noCloneEvent && !jQuery.isXMLDoc(this) ) { + // IE copies events bound via attachEvent when + // using cloneNode. Calling detachEvent on the + // clone will also remove the events from the orignal + // In order to get around this, we use innerHTML. + // Unfortunately, this means some modifications to + // attributes in IE that are actually only stored + // as properties will not be copied (such as the + // the name attribute on an input). + var html = this.outerHTML; + if ( !html ) { + var div = this.ownerDocument.createElement("div"); + div.appendChild( this.cloneNode(true) ); + html = div.innerHTML; + } + + return jQuery.clean([html.replace(/ jQuery\d+="(?:\d+|null)"/g, "").replace(/^\s*/, "")])[0]; + } else + return this.cloneNode(true); + }); + + // Copy the events from the original to the clone + if ( events === true ) { + var orig = this.find("*").andSelf(), i = 0; + + ret.find("*").andSelf().each(function(){ + if ( this.nodeName !== orig[i].nodeName ) + return; + + var events = jQuery.data( orig[i], "events" ); + + for ( var type in events ) { + for ( var handler in events[ type ] ) { + jQuery.event.add( this, type, events[ type ][ handler ], events[ type ][ handler ].data ); + } + } + + i++; + }); + } + + // Return the cloned set + return ret; + }, + + filter: function( selector ) { + return this.pushStack( + jQuery.isFunction( selector ) && + jQuery.grep(this, function(elem, i){ + return selector.call( elem, i ); + }) || + + jQuery.multiFilter( selector, jQuery.grep(this, function(elem){ + return elem.nodeType === 1; + }) ), "filter", selector ); + }, + + closest: function( selector ) { + var pos = jQuery.expr.match.POS.test( selector ) ? jQuery(selector) : null, + closer = 0; + + return this.map(function(){ + var cur = this; + while ( cur && cur.ownerDocument ) { + if ( pos ? pos.index(cur) > -1 : jQuery(cur).is(selector) ) { + jQuery.data(cur, "closest", closer); + return cur; + } + cur = cur.parentNode; + closer++; + } + }); + }, + + not: function( selector ) { + if ( typeof selector === "string" ) + // test special case where just one selector is passed in + if ( isSimple.test( selector ) ) + return this.pushStack( jQuery.multiFilter( selector, this, true ), "not", selector ); + else + selector = jQuery.multiFilter( selector, this ); + + var isArrayLike = selector.length && selector[selector.length - 1] !== undefined && !selector.nodeType; + return this.filter(function() { + return isArrayLike ? jQuery.inArray( this, selector ) < 0 : this != selector; + }); + }, + + add: function( selector ) { + return this.pushStack( jQuery.unique( jQuery.merge( + this.get(), + typeof selector === "string" ? + jQuery( selector ) : + jQuery.makeArray( selector ) + ))); + }, + + is: function( selector ) { + return !!selector && jQuery.multiFilter( selector, this ).length > 0; + }, + + hasClass: function( selector ) { + return !!selector && this.is( "." + selector ); + }, + + val: function( value ) { + if ( value === undefined ) { + var elem = this[0]; + + if ( elem ) { + if( jQuery.nodeName( elem, 'option' ) ) + return (elem.attributes.value || {}).specified ? elem.value : elem.text; + + // We need to handle select boxes special + if ( jQuery.nodeName( elem, "select" ) ) { + var index = elem.selectedIndex, + values = [], + options = elem.options, + one = elem.type == "select-one"; + + // Nothing was selected + if ( index < 0 ) + return null; + + // Loop through all the selected options + for ( var i = one ? index : 0, max = one ? index + 1 : options.length; i < max; i++ ) { + var option = options[ i ]; + + if ( option.selected ) { + // Get the specifc value for the option + value = jQuery(option).val(); + + // We don't need an array for one selects + if ( one ) + return value; + + // Multi-Selects return an array + values.push( value ); + } + } + + return values; + } + + // Everything else, we just grab the value + return (elem.value || "").replace(/\r/g, ""); + + } + + return undefined; + } + + if ( typeof value === "number" ) + value += ''; + + return this.each(function(){ + if ( this.nodeType != 1 ) + return; + + if ( jQuery.isArray(value) && /radio|checkbox/.test( this.type ) ) + this.checked = (jQuery.inArray(this.value, value) >= 0 || + jQuery.inArray(this.name, value) >= 0); + + else if ( jQuery.nodeName( this, "select" ) ) { + var values = jQuery.makeArray(value); + + jQuery( "option", this ).each(function(){ + this.selected = (jQuery.inArray( this.value, values ) >= 0 || + jQuery.inArray( this.text, values ) >= 0); + }); + + if ( !values.length ) + this.selectedIndex = -1; + + } else + this.value = value; + }); + }, + + html: function( value ) { + return value === undefined ? + (this[0] ? + this[0].innerHTML.replace(/ jQuery\d+="(?:\d+|null)"/g, "") : + null) : + this.empty().append( value ); + }, + + replaceWith: function( value ) { + return this.after( value ).remove(); + }, + + eq: function( i ) { + return this.slice( i, +i + 1 ); + }, + + slice: function() { + return this.pushStack( Array.prototype.slice.apply( this, arguments ), + "slice", Array.prototype.slice.call(arguments).join(",") ); + }, + + map: function( callback ) { + return this.pushStack( jQuery.map(this, function(elem, i){ + return callback.call( elem, i, elem ); + })); + }, + + andSelf: function() { + return this.add( this.prevObject ); + }, + + domManip: function( args, table, callback ) { + if ( this[0] ) { + var fragment = (this[0].ownerDocument || this[0]).createDocumentFragment(), + scripts = jQuery.clean( args, (this[0].ownerDocument || this[0]), fragment ), + first = fragment.firstChild; + + if ( first ) + for ( var i = 0, l = this.length; i < l; i++ ) + callback.call( root(this[i], first), this.length > 1 || i > 0 ? + fragment.cloneNode(true) : fragment ); + + if ( scripts ) + jQuery.each( scripts, evalScript ); + } + + return this; + + function root( elem, cur ) { + return table && jQuery.nodeName(elem, "table") && jQuery.nodeName(cur, "tr") ? + (elem.getElementsByTagName("tbody")[0] || + elem.appendChild(elem.ownerDocument.createElement("tbody"))) : + elem; + } + } +}; + +// Give the init function the jQuery prototype for later instantiation +jQuery.fn.init.prototype = jQuery.fn; + +function evalScript( i, elem ) { + if ( elem.src ) + jQuery.ajax({ + url: elem.src, + async: false, + dataType: "script" + }); + + else + jQuery.globalEval( elem.text || elem.textContent || elem.innerHTML || "" ); + + if ( elem.parentNode ) + elem.parentNode.removeChild( elem ); +} + +function now(){ + return +new Date; +} + +jQuery.extend = jQuery.fn.extend = function() { + // copy reference to target object + var target = arguments[0] || {}, i = 1, length = arguments.length, deep = false, options; + + // Handle a deep copy situation + if ( typeof target === "boolean" ) { + deep = target; + target = arguments[1] || {}; + // skip the boolean and the target + i = 2; + } + + // Handle case when target is a string or something (possible in deep copy) + if ( typeof target !== "object" && !jQuery.isFunction(target) ) + target = {}; + + // extend jQuery itself if only one argument is passed + if ( length == i ) { + target = this; + --i; + } + + for ( ; i < length; i++ ) + // Only deal with non-null/undefined values + if ( (options = arguments[ i ]) != null ) + // Extend the base object + for ( var name in options ) { + var src = target[ name ], copy = options[ name ]; + + // Prevent never-ending loop + if ( target === copy ) + continue; + + // Recurse if we're merging object values + if ( deep && copy && typeof copy === "object" && !copy.nodeType ) + target[ name ] = jQuery.extend( deep, + // Never move original objects, clone them + src || ( copy.length != null ? [ ] : { } ) + , copy ); + + // Don't bring in undefined values + else if ( copy !== undefined ) + target[ name ] = copy; + + } + + // Return the modified object + return target; +}; + +// exclude the following css properties to add px +var exclude = /z-?index|font-?weight|opacity|zoom|line-?height/i, + // cache defaultView + defaultView = document.defaultView || {}, + toString = Object.prototype.toString; + +jQuery.extend({ + noConflict: function( deep ) { + window.$ = _$; + + if ( deep ) + window.jQuery = _jQuery; + + return jQuery; + }, + + // See test/unit/core.js for details concerning isFunction. + // Since version 1.3, DOM methods and functions like alert + // aren't supported. They return false on IE (#2968). + isFunction: function( obj ) { + return toString.call(obj) === "[object Function]"; + }, + + isArray: function( obj ) { + return toString.call(obj) === "[object Array]"; + }, + + // check if an element is in a (or is an) XML document + isXMLDoc: function( elem ) { + return elem.nodeType === 9 && elem.documentElement.nodeName !== "HTML" || + !!elem.ownerDocument && jQuery.isXMLDoc( elem.ownerDocument ); + }, + + // Evalulates a script in a global context + globalEval: function( data ) { + if ( data && /\S/.test(data) ) { + // Inspired by code by Andrea Giammarchi + // http://webreflection.blogspot.com/2007/08/global-scope-evaluation-and-dom.html + var head = document.getElementsByTagName("head")[0] || document.documentElement, + script = document.createElement("script"); + + script.type = "text/javascript"; + if ( jQuery.support.scriptEval ) + script.appendChild( document.createTextNode( data ) ); + else + script.text = data; + + // Use insertBefore instead of appendChild to circumvent an IE6 bug. + // This arises when a base node is used (#2709). + head.insertBefore( script, head.firstChild ); + head.removeChild( script ); + } + }, + + nodeName: function( elem, name ) { + return elem.nodeName && elem.nodeName.toUpperCase() == name.toUpperCase(); + }, + + // args is for internal usage only + each: function( object, callback, args ) { + var name, i = 0, length = object.length; + + if ( args ) { + if ( length === undefined ) { + for ( name in object ) + if ( callback.apply( object[ name ], args ) === false ) + break; + } else + for ( ; i < length; ) + if ( callback.apply( object[ i++ ], args ) === false ) + break; + + // A special, fast, case for the most common use of each + } else { + if ( length === undefined ) { + for ( name in object ) + if ( callback.call( object[ name ], name, object[ name ] ) === false ) + break; + } else + for ( var value = object[0]; + i < length && callback.call( value, i, value ) !== false; value = object[++i] ){} + } + + return object; + }, + + prop: function( elem, value, type, i, name ) { + // Handle executable functions + if ( jQuery.isFunction( value ) ) + value = value.call( elem, i ); + + // Handle passing in a number to a CSS property + return typeof value === "number" && type == "curCSS" && !exclude.test( name ) ? + value + "px" : + value; + }, + + className: { + // internal only, use addClass("class") + add: function( elem, classNames ) { + jQuery.each((classNames || "").split(/\s+/), function(i, className){ + if ( elem.nodeType == 1 && !jQuery.className.has( elem.className, className ) ) + elem.className += (elem.className ? " " : "") + className; + }); + }, + + // internal only, use removeClass("class") + remove: function( elem, classNames ) { + if (elem.nodeType == 1) + elem.className = classNames !== undefined ? + jQuery.grep(elem.className.split(/\s+/), function(className){ + return !jQuery.className.has( classNames, className ); + }).join(" ") : + ""; + }, + + // internal only, use hasClass("class") + has: function( elem, className ) { + return elem && jQuery.inArray( className, (elem.className || elem).toString().split(/\s+/) ) > -1; + } + }, + + // A method for quickly swapping in/out CSS properties to get correct calculations + swap: function( elem, options, callback ) { + var old = {}; + // Remember the old values, and insert the new ones + for ( var name in options ) { + old[ name ] = elem.style[ name ]; + elem.style[ name ] = options[ name ]; + } + + callback.call( elem ); + + // Revert the old values + for ( var name in options ) + elem.style[ name ] = old[ name ]; + }, + + css: function( elem, name, force, extra ) { + if ( name == "width" || name == "height" ) { + var val, props = { position: "absolute", visibility: "hidden", display:"block" }, which = name == "width" ? [ "Left", "Right" ] : [ "Top", "Bottom" ]; + + function getWH() { + val = name == "width" ? elem.offsetWidth : elem.offsetHeight; + + if ( extra === "border" ) + return; + + jQuery.each( which, function() { + if ( !extra ) + val -= parseFloat(jQuery.curCSS( elem, "padding" + this, true)) || 0; + if ( extra === "margin" ) + val += parseFloat(jQuery.curCSS( elem, "margin" + this, true)) || 0; + else + val -= parseFloat(jQuery.curCSS( elem, "border" + this + "Width", true)) || 0; + }); + } + + if ( elem.offsetWidth !== 0 ) + getWH(); + else + jQuery.swap( elem, props, getWH ); + + return Math.max(0, Math.round(val)); + } + + return jQuery.curCSS( elem, name, force ); + }, + + curCSS: function( elem, name, force ) { + var ret, style = elem.style; + + // We need to handle opacity special in IE + if ( name == "opacity" && !jQuery.support.opacity ) { + ret = jQuery.attr( style, "opacity" ); + + return ret == "" ? + "1" : + ret; + } + + // Make sure we're using the right name for getting the float value + if ( name.match( /float/i ) ) + name = styleFloat; + + if ( !force && style && style[ name ] ) + ret = style[ name ]; + + else if ( defaultView.getComputedStyle ) { + + // Only "float" is needed here + if ( name.match( /float/i ) ) + name = "float"; + + name = name.replace( /([A-Z])/g, "-$1" ).toLowerCase(); + + var computedStyle = defaultView.getComputedStyle( elem, null ); + + if ( computedStyle ) + ret = computedStyle.getPropertyValue( name ); + + // We should always get a number back from opacity + if ( name == "opacity" && ret == "" ) + ret = "1"; + + } else if ( elem.currentStyle ) { + var camelCase = name.replace(/\-(\w)/g, function(all, letter){ + return letter.toUpperCase(); + }); + + ret = elem.currentStyle[ name ] || elem.currentStyle[ camelCase ]; + + // From the awesome hack by Dean Edwards + // http://erik.eae.net/archives/2007/07/27/18.54.15/#comment-102291 + + // If we're not dealing with a regular pixel number + // but a number that has a weird ending, we need to convert it to pixels + if ( !/^\d+(px)?$/i.test( ret ) && /^\d/.test( ret ) ) { + // Remember the original values + var left = style.left, rsLeft = elem.runtimeStyle.left; + + // Put in the new values to get a computed value out + elem.runtimeStyle.left = elem.currentStyle.left; + style.left = ret || 0; + ret = style.pixelLeft + "px"; + + // Revert the changed values + style.left = left; + elem.runtimeStyle.left = rsLeft; + } + } + + return ret; + }, + + clean: function( elems, context, fragment ) { + context = context || document; + + // !context.createElement fails in IE with an error but returns typeof 'object' + if ( typeof context.createElement === "undefined" ) + context = context.ownerDocument || context[0] && context[0].ownerDocument || document; + + // If a single string is passed in and it's a single tag + // just do a createElement and skip the rest + if ( !fragment && elems.length === 1 && typeof elems[0] === "string" ) { + var match = /^<(\w+)\s*\/?>$/.exec(elems[0]); + if ( match ) + return [ context.createElement( match[1] ) ]; + } + + var ret = [], scripts = [], div = context.createElement("div"); + + jQuery.each(elems, function(i, elem){ + if ( typeof elem === "number" ) + elem += ''; + + if ( !elem ) + return; + + // Convert html string into DOM nodes + if ( typeof elem === "string" ) { + // Fix "XHTML"-style tags in all browsers + elem = elem.replace(/(<(\w+)[^>]*?)\/>/g, function(all, front, tag){ + return tag.match(/^(abbr|br|col|img|input|link|meta|param|hr|area|embed)$/i) ? + all : + front + ">"; + }); + + // Trim whitespace, otherwise indexOf won't work as expected + var tags = elem.replace(/^\s+/, "").substring(0, 10).toLowerCase(); + + var wrap = + // option or optgroup + !tags.indexOf("", "" ] || + + !tags.indexOf("", "" ] || + + tags.match(/^<(thead|tbody|tfoot|colg|cap)/) && + [ 1, "", "
" ] || + + !tags.indexOf("", "" ] || + + // matched above + (!tags.indexOf("", "" ] || + + !tags.indexOf("", "" ] || + + // IE can't serialize and