| ;(function ($, window, document, undefined) { |
| 'use strict'; |
| |
| Foundation.libs.interchange = { |
| name : 'interchange', |
| |
| version : '5.2.2', |
| |
| cache : {}, |
| |
| images_loaded : false, |
| nodes_loaded : false, |
| |
| settings : { |
| load_attr : 'interchange', |
| |
| named_queries : { |
| 'default' : 'only screen', |
| small : Foundation.media_queries.small, |
| medium : Foundation.media_queries.medium, |
| large : Foundation.media_queries.large, |
| xlarge : Foundation.media_queries.xlarge, |
| xxlarge: Foundation.media_queries.xxlarge, |
| landscape : 'only screen and (orientation: landscape)', |
| portrait : 'only screen and (orientation: portrait)', |
| retina : 'only screen and (-webkit-min-device-pixel-ratio: 2),' + |
| 'only screen and (min--moz-device-pixel-ratio: 2),' + |
| 'only screen and (-o-min-device-pixel-ratio: 2/1),' + |
| 'only screen and (min-device-pixel-ratio: 2),' + |
| 'only screen and (min-resolution: 192dpi),' + |
| 'only screen and (min-resolution: 2dppx)' |
| }, |
| |
| directives : { |
| replace: function (el, path, trigger) { |
| // The trigger argument, if called within the directive, fires |
| // an event named after the directive on the element, passing |
| // any parameters along to the event that you pass to trigger. |
| // |
| // ex. trigger(), trigger([a, b, c]), or trigger(a, b, c) |
| // |
| // This allows you to bind a callback like so: |
| // $('#interchangeContainer').on('replace', function (e, a, b, c) { |
| // console.log($(this).html(), a, b, c); |
| // }); |
| |
| if (/IMG/.test(el[0].nodeName)) { |
| var orig_path = el[0].src; |
| |
| if (new RegExp(path, 'i').test(orig_path)) return; |
| |
| el[0].src = path; |
| |
| return trigger(el[0].src); |
| } |
| var last_path = el.data(this.data_attr + '-last-path'); |
| |
| if (last_path == path) return; |
| |
| if (/\.(gif|jpg|jpeg|tiff|png)([?#].*)?/i.test(path)) { |
| $(el).css('background-image', 'url('+path+')'); |
| el.data('interchange-last-path', path); |
| return trigger(path); |
| } |
| |
| return $.get(path, function (response) { |
| el.html(response); |
| el.data(this.data_attr + '-last-path', path); |
| trigger(); |
| }); |
| |
| } |
| } |
| }, |
| |
| init : function (scope, method, options) { |
| Foundation.inherit(this, 'throttle random_str'); |
| |
| this.data_attr = this.set_data_attr(); |
| $.extend(true, this.settings, method, options); |
| this.bindings(method, options); |
| this.load('images'); |
| this.load('nodes'); |
| }, |
| |
| get_media_hash : function() { |
| var mediaHash=''; |
| for (var queryName in this.settings.named_queries ) { |
| mediaHash += matchMedia(this.settings.named_queries[queryName]).matches.toString(); |
| } |
| return mediaHash; |
| }, |
| |
| events : function () { |
| var self = this, prevMediaHash; |
| |
| $(window) |
| .off('.interchange') |
| .on('resize.fndtn.interchange', self.throttle(function () { |
| var currMediaHash = self.get_media_hash(); |
| if (currMediaHash !== prevMediaHash) { |
| self.resize(); |
| } |
| prevMediaHash = currMediaHash; |
| }, 50)); |
| |
| return this; |
| }, |
| |
| resize : function () { |
| var cache = this.cache; |
| |
| if(!this.images_loaded || !this.nodes_loaded) { |
| setTimeout($.proxy(this.resize, this), 50); |
| return; |
| } |
| |
| for (var uuid in cache) { |
| if (cache.hasOwnProperty(uuid)) { |
| var passed = this.results(uuid, cache[uuid]); |
| |
| if (passed) { |
| this.settings.directives[passed |
| .scenario[1]].call(this, passed.el, passed.scenario[0], function () { |
| if (arguments[0] instanceof Array) { |
| var args = arguments[0]; |
| } else { |
| var args = Array.prototype.slice.call(arguments, 0); |
| } |
| |
| passed.el.trigger(passed.scenario[1], args); |
| }); |
| } |
| } |
| } |
| |
| }, |
| |
| results : function (uuid, scenarios) { |
| var count = scenarios.length; |
| |
| if (count > 0) { |
| var el = this.S('[' + this.add_namespace('data-uuid') + '="' + uuid + '"]'); |
| |
| while (count--) { |
| var mq, rule = scenarios[count][2]; |
| if (this.settings.named_queries.hasOwnProperty(rule)) { |
| mq = matchMedia(this.settings.named_queries[rule]); |
| } else { |
| mq = matchMedia(rule); |
| } |
| if (mq.matches) { |
| return {el: el, scenario: scenarios[count]}; |
| } |
| } |
| } |
| |
| return false; |
| }, |
| |
| load : function (type, force_update) { |
| if (typeof this['cached_' + type] === 'undefined' || force_update) { |
| this['update_' + type](); |
| } |
| |
| return this['cached_' + type]; |
| }, |
| |
| update_images : function () { |
| var images = this.S('img[' + this.data_attr + ']'), |
| count = images.length, |
| i = count, |
| loaded_count = 0, |
| data_attr = this.data_attr; |
| |
| this.cache = {}; |
| this.cached_images = []; |
| this.images_loaded = (count === 0); |
| |
| while (i--) { |
| loaded_count++; |
| if (images[i]) { |
| var str = images[i].getAttribute(data_attr) || ''; |
| |
| if (str.length > 0) { |
| this.cached_images.push(images[i]); |
| } |
| } |
| |
| if (loaded_count === count) { |
| this.images_loaded = true; |
| this.enhance('images'); |
| } |
| } |
| |
| return this; |
| }, |
| |
| update_nodes : function () { |
| var nodes = this.S('[' + this.data_attr + ']').not('img'), |
| count = nodes.length, |
| i = count, |
| loaded_count = 0, |
| data_attr = this.data_attr; |
| |
| this.cached_nodes = []; |
| this.nodes_loaded = (count === 0); |
| |
| |
| while (i--) { |
| loaded_count++; |
| var str = nodes[i].getAttribute(data_attr) || ''; |
| |
| if (str.length > 0) { |
| this.cached_nodes.push(nodes[i]); |
| } |
| |
| if(loaded_count === count) { |
| this.nodes_loaded = true; |
| this.enhance('nodes'); |
| } |
| } |
| |
| return this; |
| }, |
| |
| enhance : function (type) { |
| var i = this['cached_' + type].length; |
| |
| while (i--) { |
| this.object($(this['cached_' + type][i])); |
| } |
| |
| return $(window).trigger('resize'); |
| }, |
| |
| parse_params : function (path, directive, mq) { |
| return [this.trim(path), this.convert_directive(directive), this.trim(mq)]; |
| }, |
| |
| convert_directive : function (directive) { |
| |
| var trimmed = this.trim(directive); |
| |
| if (trimmed.length > 0) { |
| return trimmed; |
| } |
| |
| return 'replace'; |
| }, |
| |
| object : function(el) { |
| var raw_arr = this.parse_data_attr(el), |
| scenarios = [], |
| i = raw_arr.length; |
| |
| if (i > 0) { |
| while (i--) { |
| var split = raw_arr[i].split(/\((.*?)(\))$/); |
| |
| if (split.length > 1) { |
| var cached_split = split[0].split(','), |
| params = this.parse_params(cached_split[0], |
| cached_split[1], split[1]); |
| |
| scenarios.push(params); |
| } |
| } |
| } |
| |
| return this.store(el, scenarios); |
| }, |
| |
| store : function (el, scenarios) { |
| var uuid = this.random_str(), |
| current_uuid = el.data(this.add_namespace('uuid', true)); |
| |
| if (this.cache[current_uuid]) return this.cache[current_uuid]; |
| |
| el.attr(this.add_namespace('data-uuid'), uuid); |
| |
| return this.cache[uuid] = scenarios; |
| }, |
| |
| trim : function(str) { |
| |
| if (typeof str === 'string') { |
| return $.trim(str); |
| } |
| |
| return str; |
| }, |
| |
| set_data_attr: function (init) { |
| if (init) { |
| if (this.namespace.length > 0) { |
| return this.namespace + '-' + this.settings.load_attr; |
| } |
| |
| return this.settings.load_attr; |
| } |
| |
| if (this.namespace.length > 0) { |
| return 'data-' + this.namespace + '-' + this.settings.load_attr; |
| } |
| |
| return 'data-' + this.settings.load_attr; |
| }, |
| |
| parse_data_attr : function (el) { |
| var raw = el.attr(this.attr_name()).split(/\[(.*?)\]/), |
| i = raw.length, |
| output = []; |
| |
| while (i--) { |
| if (raw[i].replace(/[\W\d]+/, '').length > 4) { |
| output.push(raw[i]); |
| } |
| } |
| |
| return output; |
| }, |
| |
| reflow : function () { |
| this.load('images', true); |
| this.load('nodes', true); |
| } |
| |
| }; |
| |
| }(jQuery, this, this.document)); |