Last active
August 29, 2015 14:07
-
-
Save datchley/8299b27961fbf44b0684 to your computer and use it in GitHub Desktop.
jQuery extension - $.moveTo() and a `DOMChanged` event implementation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <!DOCTYPE html> | |
| <html> | |
| <head> | |
| <style type="text/css"> | |
| .moveable { | |
| border: 1px solid red; | |
| display: inline-block; | |
| padding: 2px; | |
| font-family: sans-serif; | |
| } | |
| #moveto { | |
| border: 1px solid green; | |
| height: 100px; | |
| width: 100%; | |
| } | |
| .controls { | |
| margin-top: 20px; | |
| } | |
| </style> | |
| <script src="//code.jquery.com/jquery-1.11.1.min.js"></script> | |
| <meta charset="utf-8"> | |
| </head> | |
| <body> | |
| <div class="moveable" id="moveme1">Move Me 1</div> | |
| <div class="moveable" id="moveme2">Move Me 2</div> | |
| <div class="moveable" id="moveme3">Move Me 3</div> | |
| <hr/> | |
| <div id="moveto"></div> | |
| <div class="controls"> | |
| <button id="btn-inside">Move Inside</button> | |
| <button id="btn-before">Move Before</button> | |
| <button id="btn-after">Move After</button> | |
| </div> | |
| <script src="moveto.jquery.js"></script> | |
| <script> | |
| var $target = $('#moveto'); | |
| // Listen for DOM changes on our target | |
| $target.on('DOMChanged', function(ev, data) { | |
| console.log("[debug] DOMChanged fired: %o", data); | |
| }); | |
| // detach and move elements in and around a target | |
| $('#btn-inside').click(function() { | |
| $('#moveme1').moveTo($target, 'inside'); | |
| }); | |
| $('#btn-before').click(function() { | |
| $('#moveme2').moveTo($target,'before'); | |
| }); | |
| $('#btn-after').click(function() { | |
| $('#moveme3').moveTo($target,'after'); | |
| }); | |
| </script> | |
| </body> | |
| </html> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| !function (factory) { | |
| if (typeof exports == 'object') { | |
| factory(require('jquery')); | |
| } else if (typeof define == 'function' && define.amd) { | |
| define(['jquery'], factory); | |
| } else { | |
| factory(jQuery); | |
| } | |
| }(function($) { | |
| 'use strict'; | |
| /** | |
| * isDOM - Check if an object is a DOM Node/Element | |
| * @param obj {mixed} - the object to check | |
| * @return {boolean} - true if obj is a DOM Element | |
| */ | |
| function isDOM(obj) { | |
| try { | |
| return obj instanceof HTMLElement; | |
| } catch(e) { | |
| return (typeof obj === "object") && | |
| (obj['nodeType'] && obj.nodeType === 1) && | |
| (obj['style'] && typeof obj.style === "object"); | |
| } | |
| } | |
| /** | |
| * after - AOP method to fire a function after an existing | |
| * function already defined in jQuery's $.fn environment. | |
| * @param method {string} - the name of the jQuery method | |
| * @param fn {function} - the function to execute 'after' the jQuery method | |
| * @return {jQuery} - the standard context object of the call | |
| */ | |
| function after(method, fn) { | |
| var _orig = $.fn[method]; | |
| if (fn && _orig) { | |
| $.fn[method] = function() { | |
| var args = [].slice.call(arguments), | |
| results; | |
| results = _orig.apply(this, args); | |
| fn.apply(this, args); | |
| return results; | |
| }; | |
| } | |
| } | |
| /** | |
| * fireDOMChanged - fires a 'DOMChanged' event on the element | |
| * passing in an event data object denoting the type of method | |
| * called originally that triggered the event. | |
| * @param el {jQuery|selector} - the element to trigger the event on | |
| * @param type {string} - the original method name called that triggered the event | |
| * @return {jQuery} - object the event is fired on | |
| */ | |
| function fireDOMChanged(el, method) { | |
| return $(el).trigger('DOMChanged', { 'method': method }); | |
| } | |
| // jQuery manipulation methods to augment | |
| var hooks = [ | |
| 'append', | |
| 'before', | |
| 'prepend', | |
| 'after', | |
| 'html', | |
| 'remove', | |
| 'empty' | |
| ] | |
| // Wrap each original jQuery method to call our fireDOMChanged() | |
| // method after executing, passing the original method name | |
| hooks.forEach(function(hook) { | |
| after(hook, function() { | |
| return fireDOMChanged(this, hook); | |
| }); | |
| }); | |
| $.fn.extend({ | |
| /** | |
| * moveTo - move the element to another element, it's positioning | |
| * determined by the location passed in, either 'before', 'inside' | |
| * or 'after'. | |
| * @param el {jQuery|selector} - the target element to move to | |
| * @param location {string} - one of inside, before or after | |
| * @param [wrap=undefined] {HTML|Element|jQuery} - optionally wrap the moved elements | |
| * @return {jQuery} the original context | |
| */ | |
| moveTo: function(el, location, wrap) { | |
| if (!el && !location) { | |
| throw Error('missing argument to $.moveTo'); | |
| } | |
| var mmap = { | |
| 'before': 'insertBefore', | |
| 'after': 'insertAfter', | |
| 'inside': 'appendTo' | |
| }, | |
| method = mmap[location], | |
| target = el.jquery ? el : $(el), | |
| source = this.detach(); | |
| return (wrap && (wrap.jquery || isDOM(wrap) || typeof wrap === 'string')) | |
| ? source[method](target).wrapAll(wrap) | |
| : source[method](target); | |
| } | |
| }); | |
| }); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment