gumby-framework 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,111 @@
1
+ /**
2
+ * Gumby Fixed
3
+ */
4
+ !function() {
5
+
6
+ 'use strict';
7
+
8
+ function Fixed($el) {
9
+ this.$el = $el;
10
+ this.$holder = Gumby.selectAttr.apply(this.$el, ['holder']);
11
+ this.fixedPoint = Gumby.selectAttr.apply(this.$el, ['fixed']);
12
+ this.unfixPoint = false;
13
+
14
+ // if holder attr set then create jQuery object
15
+ // otherwise use window for scrolling cals
16
+ if(this.$holder) {
17
+ this.$holder = $(this.$holder);
18
+ } else {
19
+ this.$holder = $(window);
20
+ }
21
+
22
+ // fix/unfix points specified
23
+ if(this.fixedPoint.indexOf('|') > -1) {
24
+ var points = this.fixedPoint.split('|');
25
+ this.fixedPoint = points[0];
26
+ this.unfixPoint = points[1];
27
+ }
28
+
29
+ // parse possible parameters
30
+ this.fixedPoint = this.parseAttrValue(this.fixedPoint);
31
+ if(this.unfixPoint) {
32
+ this.unfixPoint = this.parseAttrValue(this.unfixPoint);
33
+ }
34
+
35
+ var scope = this;
36
+ this.$holder.scroll(function() {
37
+ scope.scroll();
38
+ });
39
+ }
40
+
41
+ // handle scroll event on window/specified holder
42
+ Fixed.prototype.scroll = function() {
43
+ var offset = this.$holder.scrollTop(),
44
+ fixedPoint = this.fixedPoint,
45
+ unfixPoint = this.unfixPoint,
46
+ endPoint = this.endPoint;
47
+
48
+ // if fixed point, unfix point or end point are DOM fragements
49
+ // then re-calculate values as could have been updated
50
+ fixedPoint = fixedPoint instanceof jQuery ? this.fixedPoint.offset().top : this.fixedPoint;
51
+ unfixPoint = unfixPoint instanceof jQuery ? this.unfixPoint.offset().top : this.unfixPoint;
52
+
53
+ // ensure unfix point is never reached if not set
54
+ if(!unfixPoint) {
55
+ unfixPoint = offset * 2;
56
+ }
57
+
58
+ // scrolled past fixed point and no fixed class present
59
+ if((offset >= fixedPoint) && (offset < unfixPoint) && !this.$el.hasClass('fixed')) {
60
+ this.$el.addClass('fixed').trigger('gumby.onFixed');
61
+
62
+ // before fixed point, pass 0 to onUnfixed event
63
+ } else if((offset <= fixedPoint) && this.$el.hasClass('fixed')) {
64
+ this.$el.removeClass('fixed').trigger('gumby.onUnfixed', 0);
65
+ }
66
+
67
+ // after unfix point, pass 1 to onUnfixed event
68
+ // separate conditional as should override
69
+ if(unfixPoint && (offset >= unfixPoint) && this.$el.hasClass('fixed')) {
70
+ this.$el.removeClass('fixed').trigger('gumby.onUnfixed', 1);
71
+ }
72
+ };
73
+
74
+ // parse attribute values, could be px, top, selector
75
+ Fixed.prototype.parseAttrValue = function(attr) {
76
+ // px value fixed point
77
+ if($.isNumeric(attr)) {
78
+ return Number(attr);
79
+ // 'top' string fixed point
80
+ } else if(attr === 'top') {
81
+ return this.$el.offset().top;
82
+ // selector specified
83
+ } else {
84
+ var $el = $(attr);
85
+ return $el.length ? $el : false;
86
+ }
87
+ };
88
+
89
+ // add initialisation
90
+ Gumby.addInitalisation('fixed', function() {
91
+ $('[data-fixed],[gumby-fixed],[fixed]').each(function() {
92
+ var $this = $(this);
93
+ // this element has already been initialized
94
+ if($this.data('isFixed')) {
95
+ return true;
96
+ }
97
+ // mark element as initialized
98
+ $this.data('isFixed', true);
99
+ new Fixed($this);
100
+ });
101
+ });
102
+
103
+ // register UI module
104
+ Gumby.UIModule({
105
+ module: 'fixed',
106
+ events: ['onFixed', 'onUnfixed'],
107
+ init: function() {
108
+ Gumby.initialize('fixed');
109
+ }
110
+ });
111
+ }();
@@ -0,0 +1,81 @@
1
+ /**
2
+ * Gumby RadioBtn
3
+ */
4
+ !function() {
5
+
6
+ 'use strict';
7
+
8
+ function RadioBtn($el) {
9
+
10
+ this.$el = $el;
11
+ var scope = this;
12
+
13
+ // listen for click event and custom gumby check event
14
+ this.$el.on(Gumby.click, function(e) {
15
+ scope.click(e);
16
+ }).on('gumby.check', function() {
17
+ scope.update();
18
+ });
19
+
20
+ // update any .checked checkboxes on load
21
+ if(scope.$el.hasClass('checked')) {
22
+ scope.update();
23
+ }
24
+ }
25
+
26
+ // handle radio button click event
27
+ RadioBtn.prototype.click = function(e) {
28
+
29
+ // element responsible for event trigger
30
+ var $target = $(e.target);
31
+
32
+ // prevent propagation
33
+ e.stopPropagation();
34
+
35
+ // prevent radio button checking, we'll do that manually
36
+ e.preventDefault();
37
+
38
+ // check radio button
39
+ this.update();
40
+ };
41
+
42
+ // check radio button, uncheck all others in name group
43
+ RadioBtn.prototype.update = function() {
44
+ var // this specific radio button
45
+ $input = this.$el.find('input[type=radio]'),
46
+ // the group of radio buttons
47
+ group = 'input[name="'+$input.attr('name')+'"]';
48
+
49
+ // uncheck radio buttons in same group - uncheck input, remove checked class, remove <i>
50
+ $('.radio').has(group).removeClass('checked')
51
+ .find('input').attr('checked', false).end()
52
+ .find('i').remove();
53
+
54
+ // check this radio button - check input, add checked class, append <i>
55
+ $input.attr('checked', true);
56
+ this.$el.append('<i class="icon-dot" />').addClass('checked').trigger('gumby.onChange');
57
+ };
58
+
59
+ // add initialisation
60
+ Gumby.addInitalisation('radiobtns', function() {
61
+ $('.radio').each(function() {
62
+ var $this = $(this);
63
+ // this element has already been initialized
64
+ if($this.data('isRadioBtn')) {
65
+ return true;
66
+ }
67
+ // mark element as initialized
68
+ $this.data('isRadioBtn', true);
69
+ new RadioBtn($this);
70
+ });
71
+ });
72
+
73
+ // register UI module
74
+ Gumby.UIModule({
75
+ module: 'radiobtn',
76
+ events: ['onChange', 'check'],
77
+ init: function() {
78
+ Gumby.initialize('radiobtns');
79
+ }
80
+ });
81
+ }();
@@ -0,0 +1,74 @@
1
+ /**
2
+ * Gumby Retina
3
+ */
4
+ !function() {
5
+
6
+ 'use strict';
7
+
8
+ function Retina($el) {
9
+ this.$el = $el;
10
+ this.imageSrc = this.$el.attr('src');
11
+ this.retinaSrc = this.fetchRetinaImage();
12
+ this.$retinaImg = $(new Image());
13
+
14
+ var scope = this
15
+
16
+ // image src not valid
17
+ if(!this.retinaSrc) {
18
+ return false;
19
+ }
20
+
21
+ // load retina image
22
+ this.$retinaImg.attr('src', this.retinaSrc).load(function() {
23
+ scope.retinaImageLoaded();
24
+ });
25
+ }
26
+
27
+ // fetch retina src by appending '@2x' to image string before extension
28
+ Retina.prototype.fetchRetinaImage = function() {
29
+ var imgSrc = this.imageSrc,
30
+ index = this.imageSrc.search(/(\.|\/)(gif|jpe?g|png)$/i);
31
+
32
+ // image src is not valid
33
+ if(index < 0) {
34
+ return false;
35
+ }
36
+
37
+ // return retina src
38
+ return imgSrc.substr(0, index) + '@2x' + imgSrc.substr(index, imgSrc.length);
39
+ };
40
+
41
+ // once retina image loaded swap original src
42
+ Retina.prototype.retinaImageLoaded = function() {
43
+ this.$el.attr('src', this.$retinaImg.attr('src')).trigger('gumby.onRetina');
44
+ };
45
+
46
+ // add initialisation
47
+ Gumby.addInitalisation('retina', function() {
48
+
49
+ // this module is for retina devices only
50
+ if(!window.devicePixelRatio || window.devicePixelRatio <= 1) {
51
+ return;
52
+ }
53
+
54
+ $('img[data-retina],img[gumby-retina],img[retina]').each(function() {
55
+ var $this = $(this);
56
+ // this element has already been initialized
57
+ if($this.data('isRetina')) {
58
+ return true;
59
+ }
60
+ // mark element as initialized
61
+ $this.data('isRetina', true);
62
+ new Retina($this);
63
+ });
64
+ });
65
+
66
+ // register UI module
67
+ Gumby.UIModule({
68
+ module: 'retina',
69
+ events: ['onRetina'],
70
+ init: function() {
71
+ Gumby.initialize('retina');
72
+ }
73
+ });
74
+ }();
@@ -0,0 +1,113 @@
1
+ /**
2
+ * Gumby SkipLink
3
+ */
4
+ !function() {
5
+
6
+ 'use strict';
7
+
8
+ function SkipLink($el) {
9
+
10
+ this.$el = $el;
11
+ this.animateElement = $.browser.webkit ? 'body' : 'html';
12
+ this.targetPos = 0;
13
+ this.duration = Number(Gumby.selectAttr.apply(this.$el, ['duration'])) || 200;
14
+ this.offset = Gumby.selectAttr.apply(this.$el, ['offset']) || false;
15
+ this.easing = Gumby.selectAttr.apply(this.$el, ['easing']) || 'swing';
16
+
17
+ var scope = this;
18
+
19
+ // skip to target element on click or trigger of gumby.skipTo event
20
+ this.$el.on(Gumby.click+' gumby.skip', function(e) {
21
+ e.preventDefault();
22
+ // calculate target on each click
23
+ // other UI interactions could effect this
24
+ scope.calculateTarget();
25
+ });
26
+ }
27
+
28
+ // calculate target px point to skip to
29
+ SkipLink.prototype.calculateTarget = function() {
30
+
31
+ var scope = this,
32
+ target = Gumby.selectAttr.apply(this.$el, ['goto']),
33
+ $target;
34
+
35
+ // 'top' specified so target is 0px
36
+ if(target == 'top') {
37
+ this.targetPos = 0;
38
+
39
+ // px point specified
40
+ } else if($.isNumeric(target)) {
41
+ this.targetPos = Number(target);
42
+ } else {
43
+
44
+ // check for element with target as selector
45
+ $target = $(target);
46
+
47
+ // target does not exist, we need a target
48
+ if(!$target) {
49
+ return false;
50
+ }
51
+
52
+ this.targetPos = $target.offset().top;
53
+ }
54
+
55
+ // skip to target
56
+ this.skipTo();
57
+ };
58
+
59
+ // animate body, html scrollTop value to target px point
60
+ SkipLink.prototype.skipTo = function() {
61
+ var scope = this;
62
+
63
+ // slide to position of target
64
+ $(scope.animateElement).animate({
65
+ 'scrollTop' : this.calculateOffset()
66
+ }, this.duration, this.easing, function() {
67
+ scope.$el.trigger('gumby.onComplete');
68
+ });
69
+ };
70
+
71
+ // calculate offset with current target point
72
+ SkipLink.prototype.calculateOffset = function() {
73
+ // no offset so return target here
74
+ if(!this.offset) {
75
+ return this.targetPos;
76
+ }
77
+
78
+ // negative / positive
79
+ var op = this.offset.substr(0, 1),
80
+ off = Number(this.offset.substr(1, this.offset.length));
81
+
82
+ // subtract offset from target position
83
+ if(op === '-') {
84
+ return this.targetPos - off;
85
+ // add offset to target position
86
+ } else if(op === '+') {
87
+ return this.targetPos + off;
88
+ }
89
+ };
90
+
91
+ // add initialisation
92
+ Gumby.addInitalisation('skiplinks', function() {
93
+ $('.skiplink > a, .skip').each(function() {
94
+ var $this = $(this);
95
+ // this element has already been initialized
96
+ if($this.data('isSkipLink')) {
97
+ return true;
98
+ }
99
+ // mark element as initialized
100
+ $this.data('isSkipLink', true);
101
+ new SkipLink($this);
102
+ });
103
+ });
104
+
105
+ // register UI module
106
+ Gumby.UIModule({
107
+ module: 'skiplink',
108
+ events: ['onComplete', 'skip'],
109
+ init: function() {
110
+ Gumby.initialize('skiplinks');
111
+ }
112
+ });
113
+ }();
@@ -0,0 +1,70 @@
1
+ /**
2
+ * Gumby Tabs
3
+ */
4
+ !function() {
5
+
6
+ 'use strict';
7
+
8
+ function Tabs($el) {
9
+
10
+ this.$el = $el;
11
+ this.$nav = this.$el.find('ul.tab-nav > li');
12
+ this.$content = this.$el.find('.tab-content');
13
+
14
+ var scope = this;
15
+
16
+ // listen for click event on tab nav and custom gumby set event
17
+ this.$nav.children('a').on(Gumby.click, function(e) {
18
+ e.preventDefault();
19
+ scope.click($(this));
20
+ });
21
+
22
+ // listen for gumby.set value for dynamically set tabs
23
+ this.$el.on('gumby.set', function(e, index) {
24
+ scope.set(e, index);
25
+ });
26
+ }
27
+
28
+ // handle tab nav click event
29
+ Tabs.prototype.click = function($this) {
30
+ // index of item to activate
31
+ var index = $this.parent().index();
32
+
33
+ // deactivate other tab navigation and content
34
+ this.$nav.add(this.$content).removeClass('active');
35
+
36
+ // activate this tab nav link and content
37
+ this.$nav.eq(index).add(this.$content.eq(index)).addClass('active');
38
+
39
+ // trigger gumby.change event and pass current active tab index
40
+ this.$el.trigger('gumby.onChange', index);
41
+ };
42
+
43
+ // set specific tab
44
+ Tabs.prototype.set = function(e, index) {
45
+ this.$nav.eq(index).find('a').trigger(Gumby.click);
46
+ };
47
+
48
+ // add initialisation
49
+ Gumby.addInitalisation('tabs', function() {
50
+ $('.tabs').each(function() {
51
+ var $this = $(this);
52
+ // this element has already been initialized
53
+ if($this.data('isTabs')) {
54
+ return true;
55
+ }
56
+ // mark element as initialized
57
+ $this.data('isTabs', true);
58
+ new Tabs($this);
59
+ });
60
+ });
61
+
62
+ // register UI module
63
+ Gumby.UIModule({
64
+ module: 'tabs',
65
+ events: ['onChange', 'set'],
66
+ init: function() {
67
+ Gumby.initialize('tabs');
68
+ }
69
+ });
70
+ }();