canjs-rails 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,7 @@
1
+ pkg/*
2
+ tmp
3
+ spec/support/*/Gemfile.lock
4
+ spec/support/*/public/javascripts
5
+ .rvmrc
6
+ .bundle
7
+ imports/*
data/CHANGELOG.md ADDED
@@ -0,0 +1,3 @@
1
+ ## 0.1.0 (26 June 2012)
2
+
3
+ - initial release
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source :rubygems
2
+
3
+ gemspec
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License
2
+
3
+ Copyright (c) 2012 Craig Wickesser
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,36 @@
1
+ # canjs-rails
2
+
3
+ CanJS for Rails!
4
+
5
+ This gem provides:
6
+
7
+ * can.jquery 1.0.7 (and can.jquery.min)
8
+ * all can.js plugins available as of CanJS 1.0.7
9
+
10
+ This gem requires the asset pipeline, so it should work with Rails 3.1 or later. The version of CanJS included with this gem (can.jquery) requires jQuery, conveniently Rails 3.1 and later includes jquery-rails by default, so you won't need to explicitly install jQuery. However, if you aren't using jquery-rails make sure you install jQuery and require it before can.jquery in your `app/assets/javascripts/application.js`.
11
+
12
+ ## Installation
13
+
14
+ Add the canjs-rails gem to your Gemfile.
15
+
16
+ ```ruby
17
+ gem "canjs-rails"
18
+ ```
19
+
20
+ And run `bundle install`.
21
+
22
+ ### Rails 3.1 or greater (with asset pipeline *enabled*)
23
+
24
+ To make the core CanJS library available add these lines to `app/assets/javascripts/application.js`:
25
+
26
+ ```js
27
+ //= require can.jquery
28
+ ```
29
+
30
+ You're done!
31
+
32
+ ## Acknowledgements
33
+
34
+ Many thanks are due to [the jquery-rails project](https://github.com/rails/jquery-rails/) as it was used as the basis for this gem.
35
+
36
+ Copyright [Craig Wickesser](http://mindscratch.org), released under the MIT License.
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require 'bundler'
2
+ Bundler::GemHelper.install_tasks
@@ -0,0 +1,23 @@
1
+ # -*- encoding: utf-8 -*-
2
+ require File.expand_path('../lib/canjs/rails/version', __FILE__)
3
+
4
+ Gem::Specification.new do |s|
5
+ s.name = "canjs-rails"
6
+ s.version = Canjs::Rails::VERSION
7
+ s.platform = Gem::Platform::RUBY
8
+ s.authors = ["Craig Wickesser"]
9
+ s.email = ["craig@mindscratch.org"]
10
+ s.homepage = "https://github.com/mindscratch/canjs-rails"
11
+ s.summary = "Use CanJS with Rails 3.1+"
12
+ s.description = "This gem provides CanJS for your Rails 3.1+ application."
13
+
14
+ s.required_rubygems_version = ">= 1.3.6"
15
+ s.rubyforge_project = "canjs-rails"
16
+
17
+ s.add_dependency "railties", ">= 3.2.0", "< 5.0"
18
+ s.add_dependency "thor", "~> 0.14"
19
+
20
+ s.files = `git ls-files`.split("\n")
21
+ s.executables = `git ls-files -- bin/*`.split("\n").map { |f| File.basename(f) }
22
+ s.require_path = 'lib'
23
+ end
@@ -0,0 +1 @@
1
+ require 'canjs/rails'
@@ -0,0 +1,7 @@
1
+ require 'canjs/rails/engine'
2
+ require 'canjs/rails/version'
3
+
4
+ module Canjs
5
+ module Rails
6
+ end
7
+ end
@@ -0,0 +1,6 @@
1
+ module Canjs
2
+ module Rails
3
+ class Engine < ::Rails::Engine
4
+ end
5
+ end
6
+ end
@@ -0,0 +1,6 @@
1
+ module Canjs
2
+ module Rails
3
+ VERSION = "0.1.0"
4
+ CANJS_VERSION = "1.0.7"
5
+ end
6
+ end
@@ -0,0 +1,60 @@
1
+ (function(can, window, undefined){
2
+ var isFunction = can.isFunction,
3
+ isArray = can.isArray,
4
+ makeArray = can.makeArray,
5
+
6
+ proxy = function( funcs ) {
7
+
8
+ //args that should be curried
9
+ var args = makeArray(arguments),
10
+ self;
11
+
12
+ // get the functions to callback
13
+ funcs = args.shift();
14
+
15
+ // if there is only one function, make funcs into an array
16
+ if (!isArray(funcs) ) {
17
+ funcs = [funcs];
18
+ }
19
+
20
+ // keep a reference to us in self
21
+ self = this;
22
+
23
+
24
+ return function class_cb() {
25
+ // add the arguments after the curried args
26
+ var cur = args.concat(makeArray(arguments)),
27
+ isString,
28
+ length = funcs.length,
29
+ f = 0,
30
+ func;
31
+
32
+ // go through each function to call back
33
+ for (; f < length; f++ ) {
34
+ func = funcs[f];
35
+ if (!func ) {
36
+ continue;
37
+ }
38
+
39
+ // set called with the name of the function on self (this is how this.view works)
40
+ isString = typeof func == "string";
41
+
42
+ // call the function
43
+ cur = (isString ? self[func] : func).apply(self, cur || []);
44
+
45
+ // pass the result to the next function (if there is a next function)
46
+ if ( f < length - 1 ) {
47
+ cur = !isArray(cur) || cur._use_call ? [cur] : cur
48
+ }
49
+ }
50
+ return cur;
51
+ }
52
+ }
53
+ can.Construct.proxy = can.Construct.prototype.proxy = proxy;
54
+
55
+
56
+
57
+
58
+
59
+
60
+ })(this.can, this )
@@ -0,0 +1,44 @@
1
+ (function(can, window, undefined){
2
+
3
+ // tests if we can get super in .toString()
4
+ var isFunction = can.isFunction,
5
+
6
+ fnTest = /xyz/.test(function() {
7
+ xyz;
8
+ }) ? /\b_super\b/ : /.*/;
9
+
10
+ // overwrites a single property so it can still call super
11
+ can.Construct._overwrite = function(addTo, base, name, val){
12
+ // Check if we're overwriting an existing function
13
+ addTo[name] = isFunction(val) &&
14
+ isFunction(base[name]) &&
15
+ fnTest.test(val) ? (function( name, fn ) {
16
+ return function() {
17
+ var tmp = this._super,
18
+ ret;
19
+
20
+ // Add a new ._super() method that is the same method
21
+ // but on the super-class
22
+ this._super = base[name];
23
+
24
+ // The method only need to be bound temporarily, so we
25
+ // remove it when we're done executing
26
+ ret = fn.apply(this, arguments);
27
+ this._super = tmp;
28
+ return ret;
29
+ };
30
+ })(name, val) : val;
31
+ }
32
+ // overwrites an object with methods, sets up _super
33
+ // newProps - new properties
34
+ // oldProps - where the old properties might be
35
+ // addTo - what we are adding to
36
+ can.Construct._inherit = function( newProps, oldProps, addTo ) {
37
+ addTo = addTo || newProps
38
+ for ( var name in newProps ) {
39
+ can.Construct._overwrite(addTo, oldProps, name, newProps[name]);
40
+ }
41
+ }
42
+
43
+
44
+ })(this.can, this )
@@ -0,0 +1,245 @@
1
+ (function(can, window, undefined){
2
+
3
+
4
+
5
+ //used to determine if a control instance is one of controllers
6
+ //controllers can be strings or classes
7
+ var i,
8
+ isAControllerOf = function( instance, controllers ) {
9
+ for ( i = 0; i < controllers.length; i++ ) {
10
+ if ( typeof controllers[i] == 'string' ? instance.constructor._shortName == controllers[i] : instance instanceof controllers[i] ) {
11
+ return true;
12
+ }
13
+ }
14
+ return false;
15
+ },
16
+ data = function(el, data){
17
+ return $el.data('controls');
18
+ },
19
+ makeArray = can.makeArray,
20
+ old = can.Control.setup;
21
+
22
+ /*
23
+ * static
24
+ */
25
+ can.Control.setup = function() {
26
+ // if you didn't provide a name, or are control, don't do anything
27
+ if ( this !== can.Control ) {
28
+
29
+ /**
30
+ * @attribute can.Control.plugin.static.pluginName
31
+ * @parent can.Control.plugin
32
+ *
33
+ * Setting the static `pluginName` property allows you to override the default name
34
+ * with your own.
35
+ *
36
+ * var Filler = can.Control({
37
+ * pluginName: 'fillWith'
38
+ * },{});
39
+ *
40
+ * $("#foo").fillWith();
41
+ *
42
+ * If you don't provide a `pluginName`, the control falls back to the
43
+ * [can.Construct.fullName fullName] attribute:
44
+ *
45
+ * can.Control('Ui.Layout.FillWith', {}, {});
46
+ * $("#foo").ui_layout_fill_with();
47
+ *
48
+ */
49
+ var pluginName = this.pluginName || this._fullName;
50
+
51
+ // create jQuery plugin
52
+ if(pluginName !== 'can_control'){
53
+ this.plugin(pluginName);
54
+ }
55
+
56
+ old.apply(this, arguments);
57
+ }
58
+ };
59
+
60
+ /*
61
+ * prototype
62
+ */
63
+ $.fn.extend({
64
+
65
+ /**
66
+ * @function jQuery.fn.controls
67
+ * @parent can.Control.plugin
68
+ *
69
+ * When the widget is initialized, the plugin control creates an array
70
+ * of control instance(s) with the DOM element it was initialized on using
71
+ * [can.data] method.
72
+ *
73
+ * The `controls` method allows you to get the control instance(s) for any element.
74
+ *
75
+ * //- Inits the widgets
76
+ * $('.widgets:eq(0)').my_box();
77
+ * $('.widgets:eq(1)').my_clock();
78
+ *
79
+ * <div class="widgets my_box" />
80
+ * <div class="widgets my_clock" />
81
+ *
82
+ * $('.widgets').controls() //-> [ MyBox, MyClock ]
83
+ *
84
+ * Additionally, you can invoke it passing the name of a control
85
+ * to fetch a specific instance(s).
86
+ *
87
+ * //- Inits the widgets
88
+ * $('.widgets:eq(0)').my_box();
89
+ * $('.widgets:eq(1)').my_clock();
90
+ *
91
+ * <div class="widgets my_box" />
92
+ * <div class="widgets my_clock" />
93
+ *
94
+ * $('.widgets').controls('MyBox') //-> [ MyBox ]
95
+ *
96
+ * @param {Object} control (optional) if exists the control instance(s) with that constructor function or type will be returned.
97
+ * @return {Array} an array of control instance(s).
98
+ */
99
+ controls: function() {
100
+ var controllerNames = makeArray(arguments),
101
+ instances = [],
102
+ controls, c, cname;
103
+ //check if arguments
104
+ this.each(function() {
105
+
106
+ controls = can.$(this).data("controls");
107
+ if(!controls){
108
+ return;
109
+ }
110
+ for(var i=0; i<controls.length; i++){
111
+ c = controls[i];
112
+ if (!controllerNames.length || isAControllerOf(c, controllerNames) ) {
113
+ instances.push(c);
114
+ }
115
+ }
116
+ });
117
+ return instances;
118
+ },
119
+
120
+ /**
121
+ * @function jQuery.fn.control
122
+ * @parent can.Control.plugin
123
+ *
124
+ * The `control` does the same as [jQuery.fn.controls controls] execept it only
125
+ * returns the first instance found.
126
+ *
127
+ * //- Init MyBox widget
128
+ * $('.widgets').my_box();
129
+ *
130
+ * <div class="widgets my_box" />
131
+ *
132
+ * $('.widgets').controls() //-> MyBox
133
+ *
134
+ * @param {Object} control (optional) if exists the first control instance with that constructor function or type will be returned.
135
+ * @return {can.Control} the first control.
136
+ */
137
+ control: function( control ) {
138
+ return this.controls.apply(this, arguments)[0];
139
+ }
140
+ });
141
+
142
+ can.Control.plugin = function(pluginname){
143
+ var control = this;
144
+
145
+ if (!$.fn[pluginname]) {
146
+ $.fn[pluginname] = function(options){
147
+
148
+ var args = makeArray(arguments), //if the arg is a method on this control
149
+ isMethod = typeof options == "string" && $.isFunction(control.prototype[options]), meth = args[0];
150
+ return this.each(function(){
151
+ //check if created
152
+ var plugin = can.$(this).control(control);
153
+
154
+ if (plugin) {
155
+ if (isMethod) {
156
+ // call a method on the control with the remaining args
157
+ plugin[meth].apply(plugin, args.slice(1));
158
+ }
159
+ else {
160
+ // call the plugin's update method
161
+ plugin.update.apply(plugin, args);
162
+ }
163
+ }
164
+ else {
165
+ //create a new control instance
166
+ control.newInstance.apply(control, [this].concat(args));
167
+ }
168
+ });
169
+ };
170
+ }
171
+ }
172
+
173
+ /**
174
+ * @function can.Control.prototype.update
175
+ * @parent can.Control.plugin
176
+ *
177
+ * Update extends [can.Control.prototype.options options]
178
+ * with the `options` argument and rebinds all events. It
179
+ * re-configures the control.
180
+ *
181
+ * For example, the following control wraps a recipe form. When the form
182
+ * is submitted, it creates the recipe on the server. When the recipe
183
+ * is `created`, it resets the form with a new instance.
184
+ *
185
+ * var Creator = can.Control({
186
+ * "{recipe} created" : function(){
187
+ * this.update({recipe : new Recipe()});
188
+ * this.element[0].reset();
189
+ * this.element.find("[type=submit]").val("Create Recipe")
190
+ * },
191
+ * "submit" : function(el, ev){
192
+ * ev.preventDefault();
193
+ * var recipe = this.options.recipe;
194
+ * recipe.attrs( this.element.formParams() );
195
+ * this.element.find("[type=submit]").val("Saving...")
196
+ * recipe.save();
197
+ * }
198
+ * });
199
+ *
200
+ * $('#createRecipes').creator({ recipe : new Recipe() })
201
+ *
202
+ * *Update* is called if a control's plugin helper is called with the plugin options on an element
203
+ * that already has a control instance of the same type. If you want to implement your
204
+ * own update method make sure to call the old one either using the [can.Construct.super super] plugin or
205
+ * by calling `can.Control.prototype.update.apply(this, arguments);`.
206
+ * For example, you can change the content of the control element every time the options change:
207
+ *
208
+ * var Plugin = can.Control({
209
+ * pluginName: 'myPlugin'
210
+ * }, {
211
+ * init : function(el, options) {
212
+ * this.updateCount = 0;
213
+ * this.update({
214
+ * text : 'Initialized'
215
+ * });
216
+ * },
217
+ * update : function(options) {
218
+ * // Call the can.Control update first.
219
+ * // Use this._super when using can/construct/super
220
+ * can.Control.prototype.update.call(this, options);
221
+ * this.element.html(this.options.text + ' ' +
222
+ * (++this.updateCount) + ' times');
223
+ * }
224
+ * });
225
+ *
226
+ * $('#control').myPlugin();
227
+ * $('#control').html();
228
+ * // Initialized. Updated 1 times
229
+ *
230
+ * $('#control').myPlugin({ text : 'Calling update. Updated' });
231
+ * $('#control').html();
232
+ * // Calling update. Updated 2 times
233
+ *
234
+ * @demo can/control/plugin/demo-update.html
235
+ *
236
+ * @param {Object} options A list of options to merge with
237
+ * [can.Control.prototype.options this.options]. Often this method
238
+ * is called by the [can.Control.plugin jQuery helper function].
239
+ */
240
+ can.Control.prototype.update = function( options ) {
241
+ can.extend(this.options, options);
242
+ this.on();
243
+ };
244
+
245
+ })(this.can, this )