Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

reimporting, phase 2

git-svn-id: http://svn.mootools.net/tags/0-87@130 4db308c1-fb21-0410-9919-de62e267375e
  • Loading branch information...
commit 41b0bdedce3adeb921c181145d7c79a8ecbf4763 0 parents
kamicane authored
205 Addons/Ajax.js
... ... @@ -0,0 +1,205 @@
  1 +/*
  2 +Script: Ajax.js
  3 + Contains the ajax class. Also contains methods to generate querystings from forms and Objects.
  4 +
  5 +Dependencies:
  6 + <Moo.js>, <Function.js>, <Array.js>, <String.js>, <Element.js>
  7 +
  8 +Author:
  9 + Valerio Proietti, <http://mad4milk.net>
  10 +
  11 +License:
  12 + MIT-style license.
  13 +*/
  14 +
  15 +/*
  16 +Class: Ajax
  17 + For all your asynchronous needs. Note: this class implements <Chain>
  18 +
  19 +Arguments:
  20 + url - the url pointing to the server-side script.
  21 + options - optional, an object containing options.
  22 +
  23 +Options:
  24 + method - 'post' or 'get' - the prototcol for the request; optional, defaults to 'post'.
  25 + postBody - if method is post, you can write parameters here. Can be a querystring, an object or a Form element.
  26 + async - boolean: asynchronous option; true uses asynchronous requests. Defaults to true.
  27 + onComplete - function to execute when the ajax request completes.
  28 + onStateChange - function to execute when the state of the XMLHttpRequest changes.
  29 + update - $(element) to insert the response text of the XHR into, upon completion of the request.
  30 + evalScripts - boolean; default is false. Execute scripts in the response text onComplete.
  31 +
  32 +Example:
  33 + >var myAjax = new Ajax(url, {method: 'get'}).request();
  34 +*/
  35 +
  36 +var Ajax = ajax = new Class({
  37 +
  38 + setOptions: function(options){
  39 + this.options = {
  40 + method: 'post',
  41 + postBody: null,
  42 + async: true,
  43 + onComplete: Class.empty,
  44 + onStateChange: Class.empty,
  45 + update: null,
  46 + evalScripts: false
  47 + };
  48 + Object.extend(this.options, options || {});
  49 + },
  50 +
  51 + initialize: function(url, options){
  52 + this.setOptions(options);
  53 + this.url = url;
  54 + this.transport = this.getTransport();
  55 + },
  56 +
  57 + /*
  58 + Property: request
  59 + Executes the ajax request.
  60 +
  61 + Example:
  62 + >var myAjax = new Ajax(url, {method: 'get'});
  63 + >myAjax.request();
  64 +
  65 + OR
  66 +
  67 + >new Ajax(url, {method: 'get'}).request();
  68 + */
  69 +
  70 + request: function(){
  71 + this.transport.open(this.options.method, this.url, this.options.async);
  72 + this.transport.onreadystatechange = this.onStateChange.bind(this);
  73 + if (this.options.method == 'post'){
  74 + this.transport.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
  75 + if (this.transport.overrideMimeType) this.transport.setRequestHeader('Connection', 'close');
  76 + }
  77 + switch($type(this.options.postBody)){
  78 + case 'element': this.options.postBody = $(this.options.postBody).toQueryString(); break;
  79 + case 'object': this.options.postBody = Object.toQueryString(this.options.postBody);
  80 + }
  81 + if($type(this.options.postBody) == 'string') this.transport.send(this.options.postBody);
  82 + else this.transport.send(null);
  83 + return this;
  84 + },
  85 +
  86 + onStateChange: function(){
  87 + this.options.onStateChange.delay(10, this);
  88 + if (this.transport.readyState == 4 && this.transport.status == 200){
  89 + if (this.options.update) $(this.options.update).setHTML(this.transport.responseText);
  90 + this.options.onComplete.pass([this.transport.responseText, this.transport.responseXML], this).delay(20);
  91 + if (this.options.evalScripts) this.evalScripts.delay(30, this);
  92 + this.transport.onreadystatechange = Class.empty;
  93 + this.callChain();
  94 + }
  95 + },
  96 +
  97 + /*
  98 + Property: evalScripts
  99 + Executes scripts in the response text
  100 + */
  101 +
  102 + evalScripts: function(){
  103 + if(scripts = this.transport.responseText.match(/<script[^>]*?>[\S\s]*?<\/script>/g)){
  104 + scripts.each(function(script){
  105 + eval(script.replace(/^<script[^>]*?>/, '').replace(/<\/script>$/, ''));
  106 + });
  107 + }
  108 + },
  109 +
  110 + getTransport: function(){
  111 + if (window.XMLHttpRequest) return new XMLHttpRequest();
  112 + else if (window.ActiveXObject) return new ActiveXObject('Microsoft.XMLHTTP');
  113 + }
  114 +
  115 +});
  116 +
  117 +Ajax.implement(new Chain);
  118 +
  119 +/* Section: Object related Functions */
  120 +
  121 +/*
  122 +Function: Object.toQuerySTring
  123 + Generates a querysting from a key/pair values in an object
  124 +
  125 +Arguments:
  126 + source - the object to generate the querystring from.
  127 +
  128 +Returns:
  129 + the query string.
  130 +
  131 +Example:
  132 + >Object.toQueryString({apple: "red", lemon: "yellow"}); //returns "apple=red&lemon=yellow"
  133 +*/
  134 +
  135 +Object.toQueryString = function(source){
  136 + var queryString = [];
  137 + for (var property in source) queryString.push(encodeURIComponent(property)+'='+encodeURIComponent(source[property]));
  138 + return queryString.join('&');
  139 +};
  140 +
  141 +/*
  142 +Class: Element
  143 + Custom class to allow all of its methods to be used with any DOM element via the dollar function <$>.
  144 +*/
  145 +
  146 +Element.extend({
  147 +
  148 + /*
  149 + Property: send
  150 + Sends a form with an ajax post request
  151 +
  152 + Arguments:
  153 + options - option collection for ajax request. See <Ajax.initialize> for option list.
  154 +
  155 + Returns:
  156 + The Ajax Class Instance
  157 +
  158 + Example:
  159 + (start code)
  160 + <form id="myForm" action="submit.php">
  161 + <input name="email" value="bob@bob.com">
  162 + <input name="zipCode" value="90210">
  163 + </form>
  164 + <script>
  165 + $('myForm').send()
  166 + </script>
  167 + (end)
  168 + */
  169 +
  170 + send: function(options){
  171 + options = Object.extend(options, {postBody: this.toQueryString(), method: 'post'});
  172 + return new Ajax(this.getProperty('action'), options).request();
  173 + },
  174 +
  175 + /*
  176 + Property: toQueryString
  177 + Reads the children inputs of the Element and generates a query string, based on their values. Used internally in <Ajax>
  178 +
  179 + Example:
  180 + (start code)
  181 + <form id="myForm" action="submit.php">
  182 + <input name="email" value="bob@bob.com">
  183 + <input name="zipCode" value="90210">
  184 + </form>
  185 +
  186 + <script>
  187 + $('myForm').toQueryString()
  188 + </script>
  189 + (end)
  190 +
  191 + Returns:
  192 + email=bob@bob.com&zipCode=90210
  193 + */
  194 +
  195 + toQueryString: function(){
  196 + var queryString = [];
  197 + $A(this.getElementsByTagName('*')).each(function(el){
  198 + var name = $(el).name;
  199 + var value = el.getValue();
  200 + if (value && name) queryString.push(encodeURIComponent(name)+'='+encodeURIComponent(value));
  201 + });
  202 + return queryString.join('&');
  203 + }
  204 +
  205 +});
298 Addons/Dom.js
... ... @@ -0,0 +1,298 @@
  1 +/*
  2 +Script: Dom.js
  3 + Css Query related function and <Element> extensions
  4 +
  5 +Dependencies:
  6 + <Moo.js>, <Function.js>, <Array.js>, <String.js>, <Element.js>
  7 +
  8 +Author:
  9 + Valerio Proietti, <http://mad4milk.net>
  10 +
  11 +License:
  12 + MIT-style license.
  13 +*/
  14 +
  15 +/* Section: Utility Functions */
  16 +
  17 +/*
  18 +Function: $S()
  19 + Selects DOM elements based on css selector(s). Extends the elements upon matching.
  20 +
  21 +Arguments:
  22 + any number of css selectors
  23 +
  24 +Example:
  25 + >$S('a') //an array of all anchor tags on the page
  26 + >$S('a', 'b') //an array of all anchor and bold tags on the page
  27 + >$S('#myElement') //array containing only the element with id = myElement
  28 + >$S('#myElement a.myClass') //an array of all anchor tags with the class "myClass" within the DOM element with id "myElement"
  29 +
  30 +Returns:
  31 + array - array of all the dom elements matched
  32 +*/
  33 +
  34 +function $S(){
  35 + var els = [];
  36 + $A(arguments).each(function(sel){
  37 + if ($type(sel) == 'string') els.extend(document.getElementsBySelector(sel));
  38 + else if ($type(sel) == 'element') els.push($(sel));
  39 + });
  40 + return $Elements(els);
  41 +};
  42 +
  43 +
  44 +/*
  45 +Function: $$
  46 + Same as <$S>
  47 +*/
  48 +
  49 +var $$ = $S;
  50 +
  51 +/*
  52 +Function: $E
  53 + Selects a single (i.e. the first found) Element based on the selector passed in and an optional filter element.
  54 +
  55 +Arguments:
  56 + selector - the css selector to match
  57 + filter - optional; a DOM element to limit the scope of the selector match; defaults to document.
  58 +
  59 +Example:
  60 +>$E('a', 'myElement') //find the first anchor tag inside the DOM element with id 'myElement'
  61 +
  62 +Returns:
  63 + a DOM element - the first element that matches the selector
  64 +*/
  65 +
  66 +function $E(selector, filter){
  67 + return ($(filter) || document).getElement(selector);
  68 +};
  69 +
  70 +/*
  71 +Function: $ES
  72 + Returns a collection of Elements that match the selector passed in limited to the scope of the optional filter.
  73 + See Also: <Element.getElements> for an alternate syntax.
  74 +
  75 +Retunrs:
  76 + array - an array of dom elements that match the selector within the filter
  77 +
  78 +Arguments:
  79 + selector - css selector to match
  80 + filter - optional; a DOM element to limit the scope of the selector match; defaults to document.
  81 +
  82 +Examples:
  83 + >$ES("a") //gets all the anchor tags; synonymous with $S("a")
  84 + >$ES('a','myElement') //get all the anchor tags within $('myElement')
  85 +*/
  86 +
  87 +function $ES(selector, filter){
  88 + return ($(filter) || document).getElementsBySelector(selector);
  89 +};
  90 +
  91 +function $Elements(elements){
  92 + return Object.extend(elements, new Elements);
  93 +};
  94 +
  95 +/*
  96 +Class: Element
  97 + Custom class to allow all of its methods to be used with any DOM element via the dollar function <$>.
  98 +*/
  99 +
  100 +Element.extend({
  101 +
  102 +/*
  103 + Property: getElements
  104 + Gets all the elements within an element that match the given (single) selector.
  105 +
  106 + Arguments:
  107 + selector - the css selector to match
  108 +
  109 + Example:
  110 + >$('myElement').getElements('a'); // get all anchors within myElement
  111 +
  112 + Credits:
  113 + Say thanks to Christophe Beyls <http://digitalia.be> for the new regular expression that rules getElements, a big step forward in terms of speed.
  114 + */
  115 +
  116 + getElements: function(selector){
  117 + var filters = [];
  118 + selector.clean().split(' ').each(function(sel, i){
  119 + var bits = sel.test('^(\\w*|\\*)(?:#([\\w_-]+)|\\.([\\w_-]+))?(?:\\[["\']?(\\w+)["\']?(?:([\\*\\^\\$]?=)["\']?(\\w*)["\']?)?\\])?$');
  120 + if (!bits) return;
  121 + if (!bits[1]) bits[1] = '*';
  122 + var param = bits.remove(bits[0]).associate(['tag', 'id', 'class', 'attribute', 'operator', 'value']);
  123 + if (i == 0){
  124 + if (param['id']){
  125 + var el = this.getElementById(param['id']);
  126 + if (!el || ((param['tag'] != '*') && ($Element(el, 'getTag') != param['tag']))) return;
  127 + filters = [el];
  128 + } else {
  129 + filters = $A(this.getElementsByTagName(param['tag']));
  130 + }
  131 + } else {
  132 + filters = $Elements(filters).filterByTagName(param['tag']);
  133 + if (param['id']) filters = $Elements(filters).filterById(param['id']);
  134 + }
  135 + if (param['class']) filters = $Elements(filters).filterByClassName(param['class']);
  136 + if (param['attribute']) filters = $Elements(filters).filterByAttribute(param['attribute'], param['value'], param['operator']);
  137 +
  138 + }, this);
  139 + filters.each(function(el){
  140 + $(el);
  141 + });
  142 + return $Elements(filters);
  143 + },
  144 +
  145 + /*
  146 + Property: getElementById
  147 + Targets an element with the specified id found inside the Element. Does not overwrite document.getElementById.
  148 +
  149 + Arguments:
  150 + id - the id of the element to find.
  151 + */
  152 +
  153 + getElementById: function(id){
  154 + var el = document.getElementById(id);
  155 + if (!el) return false;
  156 + for(var parent = el.parentNode; parent != this; parent = parent.parentNode){
  157 + if (!parent) return false;
  158 + }
  159 + return el;
  160 + },
  161 +
  162 + /*
  163 + Property: getElement
  164 + Same as <Element.getElements>, but returns only the first. Alternate syntax for <$E>, where filter is the Element.
  165 +
  166 + */
  167 +
  168 + getElement: function(selector){
  169 + return this.getElementsBySelector(selector)[0];
  170 + },
  171 +
  172 + /*
  173 + Property: getElement
  174 + Same as <Element.getElements>, but allows for comma separated selectors, as in css. Alternate syntax for <$S>, where filter is the Element.
  175 +
  176 + */
  177 +
  178 + getElementsBySelector: function(selector){
  179 + var els = [];
  180 + selector.split(',').each(function(sel){
  181 + els.extend(this.getElements(sel));
  182 + }, this);
  183 + return $Elements(els);
  184 + }
  185 +
  186 +});
  187 +
  188 +document.extend = Object.extend;
  189 +
  190 +/* Section: document related functions */
  191 +
  192 +document.extend({
  193 + /*
  194 + Function: document.getElementsByClassName
  195 + Returns all the elements that match a specific class name.
  196 + Here for compatibility purposes. can also be written: document.getElements('.className'), or $S('.className')
  197 + */
  198 +
  199 + getElementsByClassName: function(className){
  200 + return document.getElements('.'+className);
  201 + },
  202 + getElement: Element.prototype.getElement,
  203 + getElements: Element.prototype.getElements,
  204 + getElementsBySelector: Element.prototype.getElementsBySelector
  205 +
  206 +});
  207 +
  208 +/*
  209 +Class: Elements
  210 + Methods for dom queries arrays, as <$S>.
  211 +*/
  212 +
  213 +var Elements = new Class({
  214 +
  215 + /*
  216 + Property: action
  217 + Applies the supplied actions collection to each Element in the collection.
  218 +
  219 + Arguments:
  220 + actions - an Object with key/value pairs for the actions to apply.
  221 + The initialize key is executed immediatly.
  222 + Keys beginning with on will add a simple event (onclick for example).
  223 + Keys ending with event will add an event with <Element.addEvent>.
  224 + Other keys are useless.
  225 +
  226 + Example:
  227 + >$S('a').action({
  228 + > initialize: function() {
  229 + > this.addClassName("anchor");
  230 + > },
  231 + > onclick: function(){
  232 + > alert('clicked!');
  233 + > },
  234 + > mouseoverevent: function(){
  235 + > alert('mouseovered!');
  236 + > }
  237 + >});
  238 + */
  239 +
  240 + action: function(actions){
  241 + this.each(function(el){
  242 + el = $(el);
  243 + if (actions.initialize) actions.initialize.apply(el);
  244 + for(var action in actions){
  245 + var evt = false;
  246 + if (action.test('^on[\\w]{1,}')) el[action] = actions[action];
  247 + else if (evt = action.test('([\\w-]{1,})event$')) el.addEvent(evt[1], actions[action]);
  248 + }
  249 + });
  250 + },
  251 +
  252 + //internal methods
  253 +
  254 + filterById: function(id){
  255 + var found = [];
  256 + this.each(function(el){
  257 + if (el.id == id) found.push(el);
  258 + });
  259 + return found;
  260 + },
  261 +
  262 + filterByClassName: function(className){
  263 + var found = [];
  264 + this.each(function(el){
  265 + if ($Element(el, 'hasClass', className)) found.push(el);
  266 + });
  267 + return found;
  268 + },
  269 +
  270 + filterByTagName: function(tagName){
  271 + var found = [];
  272 + this.each(function(el){
  273 + found.extend($A(el.getElementsByTagName(tagName)));
  274 + });
  275 + return found;
  276 + },
  277 +
  278 + filterByAttribute: function(name, value, operator){
  279 + var found = [];
  280 + this.each(function(el){
  281 + var att = el.getAttribute(name);
  282 + if(!att) return;
  283 + if (!operator) return found.push(el);
  284 +
  285 + switch(operator){
  286 + case '*=': if (att.test(value)) found.push(el); break;
  287 + case '=': if (att == value) found.push(el); break;
  288 + case '^=': if (att.test('^'+value)) found.push(el); break;
  289 + case '$=': if (att.test(value+'$')) found.push(el);
  290 + }
  291 +
  292 + });
  293 + return found;
  294 + }
  295 +
  296 +});
  297 +
  298 +new Object.Native(Elements);
289 Addons/Drag.js
... ... @@ -0,0 +1,289 @@
  1 +/*
  2 +Script: Drag.js
  3 + Contains Classes Drag.Base, Drag.Move and a couple of element methods to drag and resize your elements.
  4 +
  5 +Dependencies:
  6 + <Moo.js>, <Function.js>, <Array.js>, <String.js>, <Element.js>
  7 +
  8 +Author:
  9 + Valerio Proietti, <http://mad4milk.net>
  10 +
  11 +License:
  12 + MIT-style license.
  13 +*/
  14 +
  15 +var Drag = {};
  16 +
  17 +/*
  18 +Class: Drag.Base
  19 + Modify two css properties of an element based on the position of the mouse.
  20 +
  21 +Arguments:
  22 + el - the $(element) to apply the transformations to.
  23 + xModifier - required. The css property to modify, based to the position on the X axis of the mouse. defaults to none.
  24 + yModifier - required. The css property to modify, based to the position on the Y axis of the mouse pointer. defaults to none.
  25 + options - optional. The options object.
  26 +
  27 +Options:
  28 + handle - the $(element) to act as the handle for the draggable element. defaults to the $(element) itself.
  29 + onStart - function to execute when the user starts to drag (on mousedown); optional.
  30 + onComplete - optional, function to execute when the user completes the drag.
  31 + onDrag - optional, function to execute at every step of the dragged $(element).
  32 + xMax - optional, the maximum value for the x property of the dragged $(element).
  33 + xMin - optional, the minium value for the x property of the dragged $(element).
  34 + yMax - optional, the maximum value for the y property of the dragged $(element).
  35 + yMin - optional, the minium value for the y property of the dragged $(element).
  36 +*/
  37 +
  38 +Drag.Base = new Class({
  39 +
  40 + setOptions: function(options){
  41 + this.options = Object.extend({
  42 + handle: false,
  43 + unit: 'px',
  44 + onStart: Class.empty,
  45 + onComplete: Class.empty,
  46 + onDrag: Class.empty,
  47 + xMax: false,
  48 + xMin: false,
  49 + yMax: false,
  50 + yMin: false
  51 + }, options || {});
  52 + },
  53 +
  54 + initialize: function(el, xModifier, yModifier, options){
  55 + this.setOptions(options);
  56 + this.element = $(el);
  57 + this.handle = $(this.options.handle) || this.element;
  58 + if (xModifier) this.xp = xModifier.camelCase();
  59 + if (yModifier) this.yp = yModifier.camelCase();
  60 + this.handle.onmousedown = this.start.bind(this);
  61 + },
  62 +
  63 + start: function(evt){
  64 + evt = evt || window.event;
  65 + this.startX = evt.clientX;
  66 + this.startY = evt.clientY;
  67 +
  68 + this.handleX = this.startX - this.handle.getLeft();
  69 + this.handleY = this.startY - this.handle.getTop();
  70 +
  71 + this.set(evt);
  72 + this.options.onStart.pass(this.element, this).delay(10);
  73 + document.onmousemove = this.drag.bind(this);
  74 + document.onmouseup = this.end.bind(this);
  75 + return false;
  76 + },
  77 +
  78 + addStyles: function(x, y){
  79 + if (this.xp){
  80 + var stylex = this.element.getStyle(this.xp).toInt();
  81 +
  82 + var movex = function(val){
  83 + this.element.setStyle(this.xp, val+this.options.unit);
  84 + }.bind(this);
  85 +
  86 + if (this.options.xMax && stylex >= this.options.xMax){
  87 + if (this.clientX <= this.handleX+this.handle.getLeft()) movex(stylex+x);
  88 + if (stylex > this.options.xMax) movex(this.options.xMax);
  89 + } else if(this.options.xMin && stylex <= this.options.xMin){
  90 + if (this.clientX >= this.handleX+this.handle.getLeft()) movex(stylex+x);
  91 + if (stylex < this.options.xMin) movex(this.options.xMin);
  92 + } else movex(stylex+x);
  93 + }
  94 + if (this.yp){
  95 + var styley = this.element.getStyle(this.yp).toInt();
  96 +
  97 + var movey = function(val){
  98 + this.element.setStyle(this.yp, val+this.options.unit);
  99 + }.bind(this);
  100 +
  101 + if (this.options.yMax && styley >= this.options.yMax){
  102 + if (this.clientY <= this.handleY+this.handle.getTop()) movey(styley+y);
  103 + if (styley > this.options.yMax) movey(this.options.yMax);
  104 + } else if(this.options.yMin && styley <= this.options.yMin){
  105 + if (this.clientY >= this.handleY+this.handle.getTop()) movey(styley+y);
  106 + if (styley < this.options.yMin) movey(this.options.yMin);
  107 + } else movey(styley+y);
  108 + }
  109 + },
  110 +
  111 + drag: function(evt){
  112 + evt = evt || window.event;
  113 + this.clientX = evt.clientX;
  114 + this.clientY = evt.clientY;
  115 + this.options.onDrag.pass(this.element, this).delay(5);
  116 + this.addStyles((this.clientX-this.lastMouseX), (this.clientY-this.lastMouseY));
  117 + this.set(evt);
  118 + return false;
  119 + },
  120 +
  121 + set: function(evt){
  122 + this.lastMouseX = evt.clientX;
  123 + this.lastMouseY = evt.clientY;
  124 + return false;
  125 + },
  126 +
  127 + end: function(){
  128 + document.onmousemove = null;
  129 + document.onmouseup = null;
  130 + this.options.onComplete.pass(this.element, this).delay(10);
  131 + }
  132 +
  133 +});
  134 +
  135 +/*
  136 +Class: Drag.Move
  137 + Extends <Drag.Base>, has additional functionality for dragging an element (modifying its left and top values).
  138 +
  139 +Arguments:
  140 + el - the $(element) to apply the transformations to.
  141 + options - optional. The options object.
  142 +
  143 +Options:
  144 + all the drag.Base options, plus:
  145 + snap - if true the element will start dragging after a certain distance has been reached from the mousedown. defaults to true.
  146 + snapDistance - integer representing the snapping distance. Default is 8.
  147 + onSnap - function to execute when the element has been dragged the snapDistance.
  148 + xModifier - the modifier to handle left and right dragging; defaults to left.
  149 + yModifier - the modifier to handle up and down dragging; defaults to top.
  150 + container - if set to an element will fill automatically xMin/xMax/yMin/yMax based on the $(element) size and position. defaults to false.
  151 +*/
  152 +
  153 +Drag.Move = Drag.Base.extend({
  154 +
  155 + extendOptions: function(options){
  156 + this.options = Object.extend(this.options || {}, Object.extend({
  157 + onSnap: Class.empty,
  158 + droppables: [],
  159 + snapDistance: 8,
  160 + snap: true,
  161 + xModifier: 'left',
  162 + yModifier: 'top',
  163 + container: false
  164 + }, options || {}));
  165 + },
  166 +
  167 + initialize: function(el, options){
  168 + this.extendOptions(options);
  169 + this.container = $(this.options.container);
  170 + this.parent(el, this.options.xModifier, this.options.yModifier, this.options);
  171 + },
  172 +
  173 + start: function(evt){
  174 + if (this.options.container) {
  175 + var cont = $(this.options.container).getPosition();
  176 + Object.extend(this.options, {
  177 + xMax: cont.right-this.element.offsetWidth,
  178 + xMin: cont.left,
  179 + yMax: cont.bottom-this.element.offsetHeight,
  180 + yMin: cont.top
  181 + });
  182 + }
  183 + this.parent(evt);
  184 + if (this.options.snap) document.onmousemove = this.checkAndDrag.bind(this);
  185 + return false;
  186 + },
  187 +
  188 + drag: function(evt){
  189 + this.parent(evt);
  190 + this.options.droppables.each(function(drop){
  191 + if (this.checkAgainst(drop)){
  192 + if (drop.onOver && !drop.dropping) drop.onOver.pass([this.element, this], drop).delay(10);
  193 + drop.dropping = true;
  194 + } else {
  195 + if (drop.onLeave && drop.dropping) drop.onLeave.pass([this.element, this], drop).delay(10);
  196 + drop.dropping = false;
  197 + }
  198 + }, this);
  199 + return false;
  200 + },
  201 +
  202 + checkAndDrag: function(evt){
  203 + evt = evt || window.event;
  204 + var distance = Math.round(Math.sqrt(Math.pow(evt.clientX - this.startX, 2)+Math.pow(evt.clientY - this.startY, 2)));
  205 + if (distance > this.options.snapDistance){
  206 + this.set(evt);
  207 + this.options.onSnap.pass(this.element, this).delay(10);
  208 + document.onmousemove = this.drag.bind(this);
  209 + this.addStyles(-(this.startX-evt.clientX), -(this.startY-evt.clientY));
  210 + }
  211 + return false;
  212 + },
  213 +
  214 + checkAgainst: function(el){
  215 + x = this.clientX+Window.getScrollLeft();
  216 + y = this.clientY+Window.getScrollTop();
  217 + var el = $(el).getPosition();
  218 + return (x > el.left && x < el.right && y < el.bottom && y > el.top);
  219 + },
  220 +
  221 + end: function(){
  222 + this.parent();
  223 + this.options.droppables.each(function(drop){
  224 + if (drop.onDrop && this.checkAgainst(drop)) drop.onDrop.pass([this.element, this], drop).delay(10);
  225 + }, this);
  226 + }
  227 +
  228 +});
  229 +
  230 +/*
  231 +Class: Element
  232 + Custom class to allow all of its methods to be used with any DOM element via the dollar function <$>.
  233 +*/
  234 +
  235 +Element.extend({
  236 +
  237 + /*
  238 + Property: makeDraggable
  239 + Makes an element draggable with the supplied options.
  240 +
  241 + Arguments:
  242 + options - see <Drag.Move> and <Drag.Base> for acceptable options.
  243 + */
  244 +
  245 + makeDraggable: function(options){
  246 + return new Drag.Move(this, options);
  247 + },
  248 +
  249 + /*
  250 + Property: makeResizable
  251 + Makes an element resizable (by dragging) with the supplied options.
  252 +
  253 + Arguments:
  254 + options - see <Drag.Base> for acceptable options.
  255 + */
  256 +
  257 + makeResizable: function(options){
  258 + return new Drag.Base(this, 'width', 'height', options);
  259 + },
  260 +
  261 + /*
  262 + Property: getPosition
  263 + Returns an object with width, height, left, right, top, and bottom, representing the values of the Element
  264 +
  265 + Example:
  266 + >var myValues = $('myElement').getPosition();
  267 + >//myValues will be..
  268 + >{
  269 + > width: 200,
  270 + > height: 300,
  271 + > left: 100,
  272 + > top: 50,
  273 + > right: 300,
  274 + > bottom: 350
  275 + >}
  276 + */
  277 +
  278 + getPosition: function(){
  279 + var obj = {};
  280 + obj.width = this.offsetWidth;
  281 + obj.height = this.offsetHeight;
  282 + obj.left = this.getLeft();
  283 + obj.top = this.getTop();
  284 + obj.right = obj.left + obj.width;
  285 + obj.bottom = obj.top + obj.height;
  286 + return obj;
  287 + }
  288 +
  289 +});
287 Addons/Fx.js
... ... @@ -0,0 +1,287 @@
  1 +/*
  2 +Script: Fx.js
  3 + Applies visual transitions to any element. Contains Fx.Base, Fx.Style and Fx.Styles
  4 +
  5 +Dependencies:
  6 + <Moo.js>, <Function.js>, <Array.js>, <String.js>, <Element.js>
  7 +
  8 +Author:
  9 + Valerio Proietti, <http://mad4milk.net>
  10 +
  11 +License:
  12 + MIT-style license.
  13 +*/
  14 +
  15 +var Fx = fx = {};
  16 +
  17 +/*
  18 +Class: Fx.Base
  19 + Base class for the Mootools fx library.
  20 +
  21 +Options:
  22 + onStart - the function to execute as the effect begins; nothing (<Class.empty>) by default.
  23 + onComplete - the function to execute after the effect has processed; nothing (<Class.empty>) by default.
  24 + transition - the equation to use for the effect see <Fx.Transitions>; default is <Fx.Transitions.sineInOut>
  25 + duration - the duration of the effect in ms; 500 is the default.
  26 + unit - the unit is 'px' by default (other values include things like 'em' for fonts or '%').
  27 + wait - boolean: to wait or not to wait for a current transition to end before running another of the same instance. defaults to true.
  28 + fps - the frames per second for the transition; default is 30
  29 +*/
  30 +
  31 +Fx.Base = new Class({
  32 +
  33 + setOptions: function(options){
  34 + this.options = Object.extend({
  35 + onStart: Class.empty,
  36 + onComplete: Class.empty,
  37 + transition: Fx.Transitions.sineInOut,
  38 + duration: 500,
  39 + unit: 'px',
  40 + wait: true,
  41 + fps: 50
  42 + }, options || {});
  43 + },
  44 +
  45 + step: function(){
  46 + var time = new Date().getTime();
  47 + if (time < this.time + this.options.duration){
  48 + this.cTime = time - this.time;
  49 + this.setNow();
  50 + } else {
  51 + this.options.onComplete.pass(this.element, this).delay(10);
  52 + this.clearTimer();
  53 + this.callChain();
  54 + this.now = this.to;
  55 + }
  56 + this.increase();
  57 + },
  58 +
  59 + /*
  60 + Property: set
  61 + Immediately sets the value with no transition.
  62 +
  63 + Arguments:
  64 + to - the point to jump to
  65 +
  66 + Example:
  67 + >var myFx = new Fx.Style('myElement', 'opacity').set(0); //will make it immediately transparent
  68 + */
  69 +
  70 + set: function(to){
  71 + this.now = to;
  72 + this.increase();
  73 + return this;
  74 + },
  75 +
  76 + setNow: function(){
  77 + this.now = this.compute(this.from, this.to);
  78 + },
  79 +
  80 + compute: function(from, to){
  81 + return this.options.transition(this.cTime, from, (to - from), this.options.duration);
  82 + },
  83 +
  84 + /*
  85 + Property: custom
  86 + Executes an effect from one position to the other.
  87 +
  88 + Arguments:
  89 + from - integer: staring value
  90 + to - integer: the ending value
  91 +
  92 + Examples:
  93 + >var myFx = new Fx.Style('myElement', 'opacity').custom(0,1); //display a transition from transparent to opaque.
  94 + */
  95 +
  96 + custom: function(from, to){
  97 + if (!this.options.wait) this.clearTimer();
  98 + if (this.timer) return;
  99 + this.options.onStart.pass(this.element, this).delay(10);
  100 + this.from = from;
  101 + this.to = to;
  102 + this.time = new Date().getTime();
  103 + this.timer = this.step.periodical(Math.round(1000/this.options.fps), this);
  104 + return this;
  105 + },
  106 +
  107 + /*
  108 + Property: clearTimer
  109 + Stops processing the transition.
  110 + */
  111 + clearTimer: function(){
  112 + this.timer = $clear(this.timer);
  113 + return this;
  114 + },
  115 +
  116 + setStyle: function(element, property, value){
  117 + element.setStyle(property, value + this.options.unit);
  118 + }
  119 +
  120 +});
  121 +
  122 +Fx.Base.implement(new Chain);
  123 +
  124 +/*
  125 +Class: Fx.Style
  126 + The Style effect; Extends <Fx.Base>, inherits all its properties. Used to transition any css property from one value to another.
  127 +
  128 +Arguments:
  129 + el - the $(element) to apply the style transition to
  130 + property - the property to transition
  131 + options - the Fx.Base options (see: <Fx.Base>)
  132 +
  133 +Example:
  134 + >var marginChange = new fx.Style('myElement', 'margin-top', {duration:500});
  135 + >marginChange.custom(10, 100);
  136 +*/
  137 +
  138 +Fx.Style = Fx.Base.extend({
  139 +
  140 + initialize: function(el, property, options){
  141 + this.element = $(el);
  142 + this.setOptions(options);
  143 + this.property = property.camelCase();
  144 + },
  145 +
  146 + /*
  147 + Property: hide
  148 + Same as <Fx.Base.set>(0)
  149 + */
  150 +
  151 + hide: function(){
  152 + return this.set(0);
  153 + },
  154 +
  155 + /*
  156 + Property: goTo
  157 + will apply <Fx.Base.custom>, setting the starting point to the current position.
  158 +
  159 + Arguments:
  160 + val - the ending value
  161 + */
  162 +
  163 + goTo: function(val){
  164 + return this.custom(this.now || 0, val);
  165 + },
  166 +
  167 + increase: function(){
  168 + this.setStyle(this.element, this.property, this.now);
  169 + }
  170 +
  171 +});
  172 +
  173 +/*
  174 +Class: Fx.Styles
  175 + Allows you to animate multiple css properties at once; Extends <Fx.Base>, inherits all its properties.
  176 +
  177 +Arguments:
  178 + el - the $(element) to apply the styles transition to
  179 + options - the fx options (see: <Fx.Base>)
  180 +
  181 +Example:
  182 + >var myEffects = new fx.Styles('myElement', {duration: 1000, transition: fx.linear});
  183 + >myEffects.custom({
  184 + > 'height': [10, 100],
  185 + > 'width': [900, 300]
  186 + >});
  187 +*/
  188 +
  189 +Fx.Styles = Fx.Base.extend({
  190 +
  191 + initialize: function(el, options){
  192 + this.element = $(el);
  193 + this.setOptions(options);
  194 + this.now = {};
  195 + },
  196 +
  197 + setNow: function(){
  198 + for (var p in this.from) this.now[p] = this.compute(this.from[p], this.to[p]);
  199 + },
  200 +
  201 + /*
  202 + Property: custom
  203 + The function you'll actually use to execute a transition.
  204 +
  205 + Arguments:
  206 + an object
  207 +
  208 + Example:
  209 + see <Fx.Styles>
  210 + */
  211 +
  212 + custom: function(objFromTo){
  213 + if (this.timer && this.options.wait) return;
  214 + var from = {};
  215 + var to = {};
  216 + for (var p in objFromTo){
  217 + from[p] = objFromTo[p][0];
  218 + to[p] = objFromTo[p][1];
  219 + }
  220 + return this.parent(from, to);
  221 + },
  222 +
  223 + increase: function(){
  224 + for (var p in this.now) this.setStyle(this.element, p, this.now[p]);
  225 + }
  226 +
  227 +});
  228 +
  229 +/*
  230 +Class: Element
  231 + Custom class to allow all of its methods to be used with any DOM element via the dollar function <$>.
  232 +*/
  233 +
  234 +Element.extend({
  235 +
  236 + /*
  237 + Property: effect
  238 + Applies an <Fx.Style> to the Element; This a shortcut for <Fx.Style>.
  239 +
  240 + Example:
  241 + >var myEffect = $('myElement').effect('height', {duration: 1000, transition: Fx.Transitions.linear});
  242 + >myEffect.custom(10, 100);
  243 + */
  244 +
  245 + effect: function(property, options){
  246 + return new Fx.Style(this, property, options);
  247 + },
  248 +
  249 + /*
  250 + Property: effects
  251 + Applies an <Fx.Styles> to the Element; This a shortcut for <Fx.Styles>.
  252 +
  253 + Example:
  254 + >var myEffects = $(myElement).effects({duration: 1000, transition: Fx.Transitions.sineInOut});
  255 + >myEffects.custom({'height': [10, 100], 'width': [900, 300]});
  256 + */
  257 +
  258 + effects: function(options){
  259 + return new Fx.Styles(this, options);
  260 + }
  261 +
  262 +});
  263 +
  264 +/*
  265 +Class: Fx.Transitions
  266 + A collection of transition equations for use with the <Fx> Class.
  267 +
  268 +See Also:
  269 + <Fxtransitions.js> for a whole bunch of transitions.
  270 +
  271 +Credits:
  272 + Easing Equations, (c) 2003 Robert Penner (http://www.robertpenner.com/easing/), Open Source BSD License.
  273 +*/
  274 +
  275 +Fx.Transitions = {
  276 +
  277 + /* Property: linear */
  278 + linear: function(t, b, c, d){
  279 + return c*t/d + b;
  280 + },
  281 +
  282 + /* Property: sineInOut */
  283 + sineInOut: function(t, b, c, d){
  284 + return -c/2 * (Math.cos(Math.PI*t/d) - 1) + b;
  285 + }
  286 +
  287 +};
195 Moo.js
... ... @@ -0,0 +1,195 @@
  1 +/*
  2 +Script: Moo.js
  3 + My Object Oriented javascript.
  4 +
  5 +Dependancies:
  6 + Has no dependancies.
  7 +
  8 +Author:
  9 + Valerio Proietti, <http://mad4milk.net>
  10 +
  11 +License:
  12 + MIT-style license.
  13 +
  14 +Credits:
  15 + - Class is slightly based on Base.js <http://dean.edwards.name/weblog/2006/03/base/> (c) 2006 Dean Edwards, License <http://creativecommons.org/licenses/LGPL/2.1/>
  16 + - Some functions are based on those found in prototype.js <http://prototype.conio.net/> (c) 2005 Sam Stephenson sam [at] conio [dot] net, MIT-style license
  17 + - Documentation by Aaron Newton (aaron.newton [at] cnet [dot] com) and Valerio Proietti.
  18 +*/
  19 +
  20 +/*
  21 +Class: Class
  22 + The base class object of the <http://mootools.net> framework.
  23 +
  24 +Arguments:
  25 + properties - the collection of properties that apply to the class. Creates a new class, its initialize method will fire upon class instantiation.
  26 +
  27 +Example:
  28 + >var Cat = new Class({
  29 + > initialize: function(name){
  30 + > this.name = name;
  31 + > }
  32 + >});
  33 + >var myCat = new Cat('Micia');
  34 + >alert myCat.name; //alerts 'Micia'
  35 +*/
  36 +
  37 +var Class = function(properties){
  38 + var klass = function(){
  39 + for (var p in this){
  40 + if (this[p]) this[p]._proto_ = this;
  41 + }
  42 + if (arguments[0] != 'noinit' && this.initialize) return this.initialize.apply(this, arguments);
  43 + };
  44 + klass.extend = this.extend;
  45 + klass.implement = this.implement;
  46 + klass.prototype = properties;
  47 + return klass;
  48 +};
  49 +
  50 +/*
  51 +Property: empty
  52 + Returns an empty function
  53 +*/
  54 +
  55 +Class.empty = function(){};
  56 +
  57 +/*
  58 +Property: create
  59 + same as new Class. see <Class>
  60 +*/
  61 +
  62 +Class.create = function(properties){
  63 + return new Class(properties);
  64 +};
  65 +
  66 +Class.prototype = {
  67 +
  68 + /*
  69 + Property: extend
  70 + Returns the copy of the Class extended with the passed in properties.
  71 +
  72 + Arguments:
  73 + properties - the properties to add to the base class in this new Class.
  74 +
  75 + Example:
  76 + >var Animal = new Class({
  77 + > initialize: function(age){
  78 + > this.age = age;
  79 + > }
  80 + >});
  81 + >var Cat = Animal.extend({
  82 + > initialize: function(name, age){
  83 + > this.parent(age); //will call the previous initialize;
  84 + > this.name = name;
  85 + > }
  86 + >});
  87 + >var myCat = new Cat('Micia', 20);
  88 + >alert myCat.name; //alerts 'Micia'
  89 + >alert myCat.age; //alerts 20
  90 + */
  91 +
  92 + extend: function(properties){
  93 + var pr0t0typ3 = new this('noinit');
  94 + for (var property in properties){
  95 + var previous = pr0t0typ3[property];
  96 + var current = properties[property];
  97 + if (previous && previous != current) current = previous.parentize(current) || current;
  98 + pr0t0typ3[property] = current;
  99 + }
  100 + return new Class(pr0t0typ3);
  101 + },
  102 +
  103 + /*
  104 + Property: implement
  105 + Implements the passed in properties to the base Class prototypes, altering the base class, unlike <Class.extend>.
  106 +
  107 + Arguments:
  108 + properties - the properties to add to the base class.
  109 +
  110 + Example:
  111 + >var Animal = new Class({
  112 + > initialize: function(age){
  113 + > this.age = age;
  114 + > }
  115 + >});
  116 + >Animal.implement({
  117 + > setName: function(name){
  118 + > this.name = name
  119 + > }
  120 + >});
  121 + >var myAnimal = new Animal(20);
  122 + >myAnimal.setName('Micia');
  123 + >alert(myAnimal.name); //alerts 'Micia'
  124 + */
  125 +
  126 + implement: function(properties){
  127 + for (var property in properties) this.prototype[property] = properties[property];
  128 + }
  129 +
  130 +};
  131 +
  132 +/* Section: Object related Functions */
  133 +
  134 +/*
  135 +Function: Object.extend
  136 + Copies all the properties from the second passed object to the first passed Object.
  137 + If you do myWhatever.extend = Object.extend the first parameter will become myWhatever, and your extend function will only need one parameter.
  138 +
  139 +Example:
  140 + >var firstOb = {
  141 + > 'name': 'John',
  142 + > 'lastName': 'Doe'
  143 + >};
  144 + >var secondOb = {
  145 + > 'age': '20',
  146 + > 'sex': 'male',
  147 + > 'lastName': 'Dorian'
  148 + >};
  149 + >Object.extend(firstOb, secondOb);
  150 + >//firstOb will become:
  151 + >{
  152 + > 'name': 'John',
  153 + > 'lastName': 'Dorian',
  154 + > 'age': '20',
  155 + > 'sex': 'male'
  156 + >};
  157 +
  158 +Returns:
  159 + The first object, extended.
  160 +*/
  161 +
  162 +Object.extend = function(){
  163 + var args = arguments;
  164 + if (args[1]) args = [args[0], args[1]];
  165 + else args = [this, args[0]];
  166 + for (var property in args[1]) args[0][property] = args[1][pro