opal-jquery 0.3.0.beta1 → 0.3.0.beta2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 25363d75e66b1ceff1ee1cf42b8043e042bda7d1
4
- data.tar.gz: 4ebc01fd931f21b6b564ea6ad5276019b6eef6ee
3
+ metadata.gz: 499866c99d33ceac2b97f71b4f121ef64a21f6a5
4
+ data.tar.gz: 4136e110a9ea3c53c7bfe34fc8a12f115389fbca
5
5
  SHA512:
6
- metadata.gz: fd980b4568e6e68c2aa5998fae67bc3b7a463e1c87c8984f95e3d66c343cb040a95c030aa032c5f2f0c3760ca38e560f0a00aef381c5c901a5641d253df4970d
7
- data.tar.gz: a5f79ef93073c297f2458d1d0f5d804616f55add80a000e16a04915198130049cf6d530f6e2212ad69e1f2b36c40ca123f00e012ac3897875d99dd74d1ba7826
6
+ metadata.gz: 5e6e27e0bfbec3a81f3460fa2f624fbeaf6dafe20c1e64bf9f74667fadadd6fc99ca8e037c15928309a004b83817bd1af888ac770535558d1505e193793d4987
7
+ data.tar.gz: 6cd277e4dba261e78d4439dc14347779411160c2b26909fcea0ebd274f2d5827e6601dbc4b646d34b6ba0619baad300d17bb50237911922f29514378f6c481a9
data/.gitignore CHANGED
@@ -5,3 +5,4 @@ build
5
5
  gh-pages
6
6
  /.bundle
7
7
  .yardoc
8
+ /doc
data/.travis.yml CHANGED
@@ -1,7 +1,6 @@
1
1
  language: ruby
2
2
 
3
3
  rvm:
4
- - 1.8.7
5
4
  - 1.9.3
6
5
  - 2.0.0
7
- - 2.1.0
6
+ - 2.1
data/.yardopts ADDED
@@ -0,0 +1,3 @@
1
+ --markup markdown
2
+ -
3
+ CHANGELOG.md
data/CHANGELOG.md CHANGED
@@ -1,4 +1,17 @@
1
- ## edge
1
+ # EDGE
2
+
3
+ * Move all files under `opal/jquery` require namespace, rather than
4
+ current `opal-jquery` require paths.
5
+
6
+ * Add `Browser::Window` class, and make `::Window` an instance of it.
7
+
8
+ * Make `Document` include `Browser::DocumentMethods` which is a simple
9
+ module to define custom methods for `Document`.
10
+
11
+ * Cleanup HTTP implementation.
12
+
13
+ * `Element#[]` and `Element#attr` now return `nil` for empty attributes,
14
+ instead of returning an empty string.
2
15
 
3
16
  * Add `HTTP.setup` and `HTTP.setup=` to access `$.ajaxSetup`
4
17
 
@@ -10,7 +23,7 @@
10
23
  * Add Promise support to `HTTP` get/post/put/delete methods. Also remove
11
24
  `HTTP#callback` and `#errback` methods.
12
25
 
13
- ## 0.2.0 2014-03-12
26
+ # 0.2.0 - March 12, 2013
14
27
 
15
28
  * Add `Document.body` and `Document.head` shortcut to element instances.
16
29
 
@@ -24,18 +37,18 @@
24
37
 
25
38
  * Expose `#detach` method on `Element`.
26
39
 
27
- ## 0.1.2 2013-12-01
40
+ # 0.1.2 - December 1, 2013
28
41
 
29
42
  * Support setting html content through `Element#html()`.
30
43
 
31
44
  * Add `Element` methods: `#get`, `#attr` and `#prop` by aliasing them to
32
45
  jquery implementations.
33
46
 
34
- ## 0.1.1 2013-11-11
47
+ # 0.1.1 - November 11, 2013
35
48
 
36
49
  * Require `native` from stdlib for `HTTP` to use.
37
50
 
38
- ## 0.1.0 2013-11-03
51
+ # 0.1.0 - November 3, 2013
39
52
 
40
53
  * Add `Window` and `$window` alias.
41
54
 
@@ -43,7 +56,7 @@
43
56
 
44
57
  * `Event` is now a wrapper around native event from dom listeners.
45
58
 
46
- ## 0.0.9 2013-06-15
59
+ # 0.0.9 - June 15, 2013
47
60
 
48
61
  * Revert earlier commit, and use `$document` as reference to jquery
49
62
  wrapped `document`.
@@ -52,13 +65,13 @@
52
65
 
53
66
  * Depreceate $document.title and $document.title=.
54
67
 
55
- ## 0.0.8 2013-05-02
68
+ # 0.0.8 - May 2, 2013
56
69
 
57
70
  * Depreceate Document in favor of $document global.
58
71
 
59
72
  * Add HTTP.delete() for creating DELETE request.
60
73
 
61
- ## 0.0.7 2013-02-20
74
+ # 0.0.7 - February 20, 2013
62
75
 
63
76
  * Add Element#method_missing which forwards missing calls to try and call
64
77
  method as a native jquery function/plugin.
data/Gemfile CHANGED
@@ -1,5 +1,5 @@
1
1
  source 'https://rubygems.org'
2
2
  gemspec
3
3
 
4
- gem 'opal', github: 'opal/opal'
5
- # gem 'opal', path: '../opal'
4
+ gem 'opal', github: 'opal/opal'
5
+ gem 'opal-rspec', github: 'opal/opal-rspec'
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # opal-jquery
1
+ # opal-jquery: jQuery Wrapper For Opal
2
2
 
3
3
  [![Build Status](http://img.shields.io/travis/opal/opal-jquery/master.svg)](http://travis-ci.org/opal/opal-jquery)
4
4
 
@@ -7,23 +7,7 @@ and providing a nice ruby syntax for dealing with jQuery instances.
7
7
 
8
8
  See the Opal website for [documentation](http://opalrb.org/docs/jquery).
9
9
 
10
- ## Documentation
11
-
12
- ```ruby
13
- elements = Element.find('.foo')
14
- # => [<div class="foo">, ...]
15
-
16
- elements.class
17
- # => JQuery
18
-
19
- elements.on(:click) do
20
- alert "element was clicked"
21
- end
22
- ```
23
-
24
- ### Getting Started
25
-
26
- #### Installation
10
+ ## Installation
27
11
 
28
12
  Install opal-jquery from RubyGems:
29
13
 
@@ -36,10 +20,77 @@ Or include it in your Gemfile for Bundler:
36
20
  ```ruby
37
21
  gem 'opal-jquery'
38
22
  ```
23
+ ## Running Specs
24
+
25
+ Get the dependencies:
26
+
27
+ $ bundle install
28
+
29
+ ### Browser
30
+
31
+ You can run the specs in any web browser, by running the `config.ru` rack file:
32
+
33
+ $ bundle exec rackup
34
+
35
+ And then visiting `http://localhost:9292` in any web browser.
36
+
37
+ ### Phantomjs
38
+
39
+ You will need phantomjs to run the specs outside the browser. It can
40
+ be downloaded at [http://phantomjs.org/download.html](http://phantomjs.org/download.html)
41
+
42
+ On osx you can install through homebrew
43
+
44
+ $ brew update; brew install phantomjs
45
+
46
+ Run the tests inside a phantom.js runner:
47
+
48
+ $ bundle exec rake
49
+
50
+ ### Zepto
51
+
52
+ opal-jquery also supports zepto. To run specs for zepto use the rake task:
53
+
54
+ $ bundle exec rake zepto
55
+
56
+ ## Getting Started
57
+
58
+ ### Usage
59
+
60
+ `opal-jquery` can now be easily added to your opal application sources using a
61
+ standard require:
62
+
63
+ ```ruby
64
+ # app/application.rb
65
+ require 'opal'
66
+ require 'jquery'
67
+ require 'opal-jquery'
68
+
69
+ alert "Hello from jquery + opal"
70
+ ```
71
+
72
+ > **Note**: this file requires two important dependencies, `jquery` and `opal-jquery`.
73
+ > You need to bring your own `jquery.js` file as the gem does not include one. If
74
+ > you are using the asset pipeline with rails, then this should be available
75
+ > already, otherwise download a copy and place it into `app/` or whichever directory
76
+ > you are compiling assets from. You can alternatively require a zepto instance.
77
+
78
+ The `#alert` method is provided by `opal-jquery`. If the message displays, then
79
+ `jquery` support should be working.
39
80
 
40
- ### Interacting with the DOM
81
+ ### How does opal-jquery work
41
82
 
42
- #### Finding elements
83
+ `opal-jquery` provides an `Element` class, whose instances are toll-free
84
+ bridged instances of jquery objects. Just like ruby arrays are just javascript
85
+ arrays, `Element` instances are just jquery objects. This makes interaction
86
+ with jquery plugins much easier.
87
+
88
+ Also, `Element` will try to bridge with Zepto if it cannot find jQuery loaded,
89
+ making it ideal for mobile applications as well.
90
+
91
+ ## Interacting with the DOM
92
+
93
+ ### Finding Elements
43
94
 
44
95
  opal-jquery provides the `Element` class, which can be used to find elements in
45
96
  the current document:
@@ -79,7 +130,7 @@ el.find '.foo'
79
130
  # => #<Element .... >
80
131
  ```
81
132
 
82
- #### Running code on document ready
133
+ ### Running code on document ready
83
134
 
84
135
  Just like jQuery, opal-jquery requires the document to be ready to
85
136
  be able to fully interact with the page. Any top level access should
@@ -93,7 +144,7 @@ end
93
144
 
94
145
  The `Kernel#alert` method is shown above too.
95
146
 
96
- #### Event handling
147
+ ### Event handling
97
148
 
98
149
  The `Element#on` method is used to attach event handlers to elements:
99
150
 
@@ -122,7 +173,15 @@ Element.find('#my_link').on(:click) do |evt|
122
173
  end
123
174
  ```
124
175
 
125
- #### CSS styles and classnames
176
+ You can access the element which triggered the event by `#current_target`.
177
+
178
+ ```ruby
179
+ Document.on :click do |evt|
180
+ puts "clicked on: #{evt.current_target}"
181
+ end
182
+ ```
183
+
184
+ ### CSS styles and classnames
126
185
 
127
186
  The various jQuery methods are available on `Element` instances:
128
187
 
@@ -157,7 +216,7 @@ el.css 'color'
157
216
  # => 'blue'
158
217
  ```
159
218
 
160
- ### HTTP/AJAX requests
219
+ ## HTTP/AJAX requests
161
220
 
162
221
  jQuery's Ajax implementation is also wrapped in the top level HTTP
163
222
  class.
@@ -201,7 +260,7 @@ The request is actually triggered inside the `HTTP.get` method, but due
201
260
  to the async nature of the request, the callback and errback handlers can
202
261
  be added anytime before the request returns.
203
262
 
204
- #### Handling responses
263
+ ### Handling responses
205
264
 
206
265
  Web apps deal with JSON responses quite frequently, so there is a useful
207
266
  `#json` helper method to get the JSON content from a request:
@@ -231,49 +290,6 @@ request.errback { |response|
231
290
  }
232
291
  ```
233
292
 
234
- #### Other options
235
-
236
- `HTTP` accepts the usual `$.ajax` options:
237
-
238
- ```ruby
239
- HTTP.get '/search', data: {q: 'foo'}, async: false do |response|
240
- p response.body
241
- end
242
- ```
243
-
244
- ## Running Specs
245
-
246
- Get the dependencies:
247
-
248
- $ bundle install
249
-
250
- ### Browser
251
-
252
- You can run the specs in any web browser, by running the `config.ru` rack file:
253
-
254
- $ bundle exec rackup
255
-
256
- And then visiting `http://localhost:9292` in any web browser.
257
-
258
- ### Phantomjs
259
-
260
- You will need phantomjs to run the specs outside the browser. It can
261
- be downloaded at [http://phantomjs.org/download.html](http://phantomjs.org/download.html)
262
-
263
- On osx you can install through homebrew
264
-
265
- $ brew update; brew install phantomjs
266
-
267
- Run the tests inside a phantom.js runner:
268
-
269
- $ bundle exec rake
270
-
271
- ### Zepto
272
-
273
- opal-jquery also supports zepto. To run specs for zepto use the rake task:
274
-
275
- $ bundle exec rake zepto
276
-
277
293
  ## License
278
294
 
279
295
  (The MIT License)
@@ -297,3 +313,4 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
297
313
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
298
314
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
299
315
  THE SOFTWARE.
316
+
data/lib/opal/jquery.rb CHANGED
@@ -1,4 +1,13 @@
1
- require 'opal'
2
- require 'opal/jquery/version'
1
+ if RUBY_ENGINE == 'opal'
2
+ require 'opal/jquery/window'
3
+ require 'opal/jquery/document'
4
+ require 'opal/jquery/element'
5
+ require 'opal/jquery/event'
6
+ require 'opal/jquery/http'
7
+ require 'opal/jquery/kernel'
8
+ else
9
+ require 'opal'
10
+ require 'opal/jquery/version'
3
11
 
4
- Opal.append_path File.expand_path('../../../opal', __FILE__).untaint
12
+ Opal.append_path File.expand_path('../..', __FILE__).untaint
13
+ end
File without changes
@@ -0,0 +1,93 @@
1
+ require 'opal/jquery/constants'
2
+ require 'opal/jquery/element'
3
+
4
+ module Browser
5
+ # {Document} includes these methods to extend {Element}.
6
+ #
7
+ # Generally, you will want to use the {::Document} top level instance of
8
+ # {Element}.
9
+ #
10
+ # ## Usage
11
+ #
12
+ # A useful method on {Document} is the {#ready?} method, which can be used to
13
+ # run a block once the document is ready. This is equivalent to passing a
14
+ # function to the `jQuery` constructor.
15
+ #
16
+ # Document.ready? do
17
+ # puts "Page is ready to use!"
18
+ # end
19
+ #
20
+ # Just like jQuery, multiple blocks may be passed to {#ready?}.
21
+ #
22
+ # ### Document head and body elements
23
+ #
24
+ # Every document has atleast two elements: a `head` and `body`. For
25
+ # convenience, these are both exposed as {#head} and {#body} respectively,
26
+ # and are just instances of {Element}.
27
+ #
28
+ # puts Document.head
29
+ # puts Document.body
30
+ #
31
+ # # => #<Element: [<head>]>
32
+ # # => #<Element: [<body>]>
33
+ #
34
+ # ### Events
35
+ #
36
+ # {Document} instances also have {#on}, {#off} and {#trigger} methods for
37
+ # handling events. These all just delegate to their respective methods on
38
+ # {Element}, using `document` as the context.
39
+ #
40
+ # Document.on :click do |evt|
41
+ # puts "someone clicked somewhere in the document"
42
+ # end
43
+ #
44
+ module DocumentMethods
45
+ `var $ = #{JQUERY_SELECTOR.to_n}` # cache $ for SPEED
46
+
47
+ # Register a block to run once the document/page is ready.
48
+ #
49
+ # @example
50
+ # Document.ready? do
51
+ # puts "ready to go"
52
+ # end
53
+ #
54
+ def ready?(&block)
55
+ `$(#{block})` if block_given?
56
+ end
57
+
58
+ # Returns document title.
59
+ #
60
+ # @return [String]
61
+ def title
62
+ `document.title`
63
+ end
64
+
65
+ # Set document title.
66
+ #
67
+ # @param title [String]
68
+ def title=(title)
69
+ `document.title = title`
70
+ end
71
+
72
+ # {Element} instance wrapping `document.head`.
73
+ #
74
+ # @return [Element]
75
+ def head
76
+ Element.find `document.head`
77
+ end
78
+
79
+ # {Element} instance wrapping `document.body`.
80
+ #
81
+ # @return [Element]
82
+ def body
83
+ Element.find `document.body`
84
+ end
85
+ end
86
+ end
87
+
88
+ # Top level {Document} instance wrapping `window.document`.
89
+ Document = Element.find(`document`)
90
+ Document.send(:extend, Browser::DocumentMethods)
91
+
92
+ # TODO: this will be removed soon (here for compatibility)
93
+ $document = Document
@@ -0,0 +1,669 @@
1
+ require 'native'
2
+ require 'opal/jquery/constants'
3
+
4
+ # {Element} is a toll-free bridged class that maps to native jQuery instances.
5
+ #
6
+ # As {Element} maps to a jQuery object, it can be used to represent 0, 1, or
7
+ # more actual DOM elements. {Element} exposes a more ruby-esqe interface to
8
+ # jQuery.
9
+ #
10
+ # ## Usage
11
+ #
12
+ # {Element} instances can be created in a number of ways.
13
+ #
14
+ # ### Creating new Elements
15
+ #
16
+ # A new element can be created using the {Element.new} method.
17
+ #
18
+ # el = Element.new(:div)
19
+ # el.id = "title"
20
+ # p el
21
+ # # => #<Element [<div id="title">]>
22
+ #
23
+ # This is a nicer version of creating a javascript element using
24
+ # `document.createElement` and then wrapping it in a jquery object.
25
+ #
26
+ # ### Finding existing elements in dom
27
+ #
28
+ # Any valid jQuery selector expressions can be used with either {Element.find}
29
+ # or {Element.[]}.
30
+ #
31
+ # foos = Element.find('.foo')
32
+ # # => #<Element [<div class="foo">]>
33
+ #
34
+ # links = Element['a']
35
+ # # => #<Element [<a>, <a class="bar">]>
36
+ #
37
+ # Alternatively, {Element.id} can be used to find an element by its document
38
+ # id (or nil is returned for no match).
39
+ #
40
+ # bar = Element.id 'bar'
41
+ # # => Element or nil
42
+ #
43
+ # ### DOM Content from string
44
+ #
45
+ # Finally, an {Element} instance can be created by parsing a string of html
46
+ # content. This will parse multiple elements, like jquery, if string content
47
+ # contains them:
48
+ #
49
+ # Element.parse '<div id="title">hello world</div>'
50
+ # # => #<Element [<div id="title">]>
51
+ #
52
+ class Element < `#{JQUERY_CLASS.to_n}`
53
+ `var $ = #{JQUERY_SELECTOR.to_n}` # cache $ for SPEED
54
+
55
+ include Enumerable
56
+
57
+ # Find elements by the given css selector.
58
+ #
59
+ # Returns an empty {Element} if no matching elements.
60
+ #
61
+ # @param selector [String] css selector
62
+ # @return [Element]
63
+ def self.find(selector)
64
+ `$(#{selector})`
65
+ end
66
+
67
+ # Find elements by the given css selector.
68
+ #
69
+ # Returns an empty {Element} if no matching elements.
70
+ #
71
+ # @param selector [String] css selector
72
+ # @return [Element]
73
+ def self.[](selector)
74
+ `$(#{selector})`
75
+ end
76
+
77
+ # Find an element by the given id.
78
+ #
79
+ # If no matching element, then `nil` will be returned. A matching element
80
+ # becomes the sole element in the returned collection.
81
+ #
82
+ # @param id [String] dom element id
83
+ # @return [Element, nil]
84
+ def self.id(id)
85
+ %x{
86
+ var el = document.getElementById(id);
87
+
88
+ if (!el) {
89
+ return nil;
90
+ }
91
+
92
+ return $(el);
93
+ }
94
+ end
95
+
96
+ # Create a new dom element, wrapped as {Element} instance with the given
97
+ # `tag` name.
98
+ #
99
+ # @param tag [String] valid html tag name
100
+ # @return [Element]
101
+ def self.new(tag = 'div')
102
+ `$(document.createElement(tag))`
103
+ end
104
+
105
+ # Parse a string of html content into an {Element} instance.
106
+ #
107
+ # If no valid elements in string, then an empty collection will be returned.
108
+ #
109
+ # @param str [String] html content to parse
110
+ # @return [Element]
111
+ def self.parse(str)
112
+ `$(str)`
113
+ end
114
+
115
+ # Expose jQuery plugins to become available in ruby code. By default,
116
+ # jQuery methods or plugins must be manually exposed as ruby methods.
117
+ # This method simply creates an aliasing ruby method to call the original
118
+ # javascript function.
119
+ #
120
+ # @example
121
+ # # Expose bootstraps jQuery `modal` function
122
+ # Element.expose :modal
123
+ #
124
+ # Element.find('.my-modal').modal
125
+ #
126
+ # @param methods [String, Symbol] all methods to expose to ruby
127
+ # @return nil
128
+ def self.expose(*methods)
129
+ methods.each do |method|
130
+ alias_native method
131
+ end
132
+ end
133
+
134
+ # @return The original css selector used to create {Element}
135
+ attr_reader :selector
136
+
137
+ # @!method after(content)
138
+ #
139
+ # Inserts the given `content` after each element in this set of elements.
140
+ # This method can accept either another {Element}, or a string.
141
+ #
142
+ # @param content [String, Element] string or element to insert
143
+ alias_native :after
144
+
145
+ # @!method before(content)
146
+ #
147
+ # Insert the given `content` before each element in this set of elements.
148
+ # The given `content` can be either an {Element}, or a string.
149
+ #
150
+ # @param content [String, Element] string or element to insert
151
+ alias_native :before
152
+
153
+ # @!method parent(selector = nil)
154
+ #
155
+ # Returns a new {Element} set with the parents of each element in this
156
+ # collection. An optional `selector` argument can be used to filter the
157
+ # results to match the given selector. Result may be empty.
158
+ #
159
+ # @param selector [String] optional filter
160
+ # @return [Element]
161
+ alias_native :parent
162
+
163
+ # @!method parents(selector = nil)
164
+ #
165
+ # Returns a new {Element} set with all parents of each element in this
166
+ # collection. An optional `selector` may be provided to filter the
167
+ # selection. Resulting collection may be empty.
168
+ #
169
+ # @example Without filtering collection
170
+ # Element.find('#foo').parents
171
+ # # => #<Element [<div id="wrapper">, <body>, <html>]>
172
+ #
173
+ # @example Using a filter
174
+ # Element.find('#foo').parents('div')
175
+ # # => #<Element [<div id="wrapper">]
176
+ #
177
+ # @param selector [String] optional filter
178
+ # @return [Element]
179
+ alias_native :parents
180
+
181
+ # @!method prev(selector = nil)
182
+ alias_native :prev
183
+
184
+ # @!method remove(selector = nil)
185
+ alias_native :remove
186
+
187
+ # @!method hide(duration = 400)
188
+ alias_native :hide
189
+
190
+ # @!method show(duration = 400)
191
+ alias_native :show
192
+
193
+ # @!method toggle(duration = 400)
194
+ alias_native :toggle
195
+
196
+ # @!method children(selector = nil)
197
+ alias_native :children
198
+
199
+ # @!method blur
200
+ alias_native :blur
201
+
202
+ # @!method closest(selector)
203
+ alias_native :closest
204
+
205
+ # @!method detach(selector = nil)
206
+ alias_native :detach
207
+
208
+ # @!method focus
209
+ alias_native :focus
210
+
211
+ # @!method find(selector)
212
+ alias_native :find
213
+
214
+ # @!method next(selector = nil)
215
+ alias_native :next
216
+
217
+ # @!method siblings(selector = nil)
218
+ alias_native :siblings
219
+
220
+ # @!method text(text = nil)
221
+ #
222
+ # Get or set the text content of each element in this collection. Setting
223
+ # the content is provided as a compatibility method for jquery. Instead
224
+ # {#text=} should be used for setting text content.
225
+ #
226
+ # If no `text` content is provided, then the text content of this element
227
+ # will be returned.
228
+ #
229
+ # @see #text=
230
+ # @param text [String] text content to set
231
+ # @return [String]
232
+ alias_native :text
233
+
234
+ # @!method trigger(event)
235
+ #
236
+ # Trigger an event on this element. The given `event` specifies the event
237
+ # type.
238
+ #
239
+ # @param event [String, Symbol] event type
240
+ alias_native :trigger
241
+
242
+ # @!method append(content)
243
+ #
244
+ # @param content [String, Element]
245
+ alias_native :append
246
+
247
+ # @!method serialize
248
+ alias_native :serialize
249
+
250
+ # @!method is(selector)
251
+ # @return [true, false]
252
+ alias_native :is
253
+
254
+ # @!method filter(selector)
255
+ # @param selector [String]
256
+ # @return [Element]
257
+ alias_native :filter
258
+
259
+ # @!method last
260
+ #
261
+ # Returns a new {Element} instance containing the last element in this
262
+ # current set.
263
+ #
264
+ # @return [Element]
265
+ alias_native :last
266
+
267
+ # @!method wrap(wrapper)
268
+ # @param wrapper [String, Element] html content, selector or element
269
+ # @return [Element]
270
+ alias_native :wrap
271
+
272
+ # @!method stop
273
+ #
274
+ # Stop any currently running animations on element.
275
+ alias_native :stop
276
+
277
+ # @!method clone
278
+ #
279
+ # Clone all elements inside this collection, and return as a new instance.
280
+ # @return [Element]
281
+ alias_native :clone
282
+
283
+ # @!method empty
284
+ #
285
+ # Remove all child nodes from each element in this collection.
286
+ alias_native :empty
287
+
288
+ # @!method get
289
+ alias_native :get
290
+
291
+ # @!method prop(name, value = nil)
292
+ #
293
+ # Get or set the property `name` on each element in collection.
294
+ alias_native :prop
295
+
296
+ alias succ next
297
+ alias << append
298
+
299
+ # @!method []=(attr, value)
300
+ #
301
+ # Set the given attribute `attr` on each element in this collection.
302
+ #
303
+ # @see http://api.jquery.com/attr/
304
+ alias_native :[]=, :attr
305
+
306
+ # @!method add_class(class_name)
307
+ alias_native :add_class, :addClass
308
+
309
+ # @!method append_to(element)
310
+ alias_native :append_to, :appendTo
311
+
312
+ # @!method has_class?(class_name)
313
+ alias_native :has_class?, :hasClass
314
+
315
+ # @!method html=(content)
316
+ #
317
+ # Set the html content of each element in this collection to the passed
318
+ # content. Content can either be a string or another {Element}.
319
+ #
320
+ # @param content [String, Element]
321
+ alias_native :html=, :html
322
+
323
+ # @!method remove_attr(attr)
324
+ alias_native :remove_attr, :removeAttr
325
+
326
+ # @!method remove_class(class_name)
327
+ alias_native :remove_class, :removeClass
328
+
329
+ # @!method text=(text)
330
+ #
331
+ # Set text content of each element in this collection.
332
+ #
333
+ # @see #text
334
+ # @param text [String]
335
+ alias_native :text=, :text
336
+
337
+ # @!method toggle_class
338
+ alias_native :toggle_class, :toggleClass
339
+
340
+ # @!method value=(value)
341
+ alias_native :value=, :val
342
+
343
+ # @!method scroll_top=(value)
344
+ alias_native :scroll_top=, :scrollTop
345
+
346
+ # @!method scroll_top
347
+ alias_native :scroll_top, :scrollTop
348
+
349
+ # @!method scroll_left=(value)
350
+ alias_native :scroll_left=, :scrollLeft
351
+
352
+ # @!method scroll_left
353
+ alias_native :scroll_left, :scrollLeft
354
+
355
+ # @!method remove_attribute(attr)
356
+ alias_native :remove_attribute, :removeAttr
357
+
358
+ # @!method slide_down(duration = 400)
359
+ alias_native :slide_down, :slideDown
360
+
361
+ # @!method slide_up(duration = 400)
362
+ alias_native :slide_up, :slideUp
363
+
364
+ # @!method slide_toggle(duration = 400)
365
+ alias_native :slide_toggle, :slideToggle
366
+
367
+ # @!method fade_toggle(duration = 400)
368
+ alias_native :fade_toggle, :fadeToggle
369
+
370
+ # @!method height=(value)
371
+ alias_native :height=, :height
372
+
373
+ # @!method width=(value)
374
+ alias_native :width=, :width
375
+
376
+ # @!method outer_width(include_margin = false)
377
+ alias_native :outer_width, :outerWidth
378
+
379
+ # @!method outer_height(include_margin = false)
380
+ alias_native :outer_height, :outerHeight
381
+
382
+ def to_n
383
+ self
384
+ end
385
+
386
+ def [](name)
387
+ `self.attr(name) || nil`
388
+ end
389
+
390
+ def attr(name, value=nil)
391
+ if value.nil?
392
+ `self.attr(name) || nil`
393
+ else
394
+ `self.attr(name, value)`
395
+ end
396
+ end
397
+
398
+ def has_attribute?(name)
399
+ `!!self.attr(name)`
400
+ end
401
+
402
+ def append_to_body
403
+ `self.appendTo(document.body)`
404
+ end
405
+
406
+ def append_to_head
407
+ `self.appendTo(document.head)`
408
+ end
409
+
410
+ # Returns the element at the given index as a new {Element} instance.
411
+ # Negative indexes can be used and are counted from the end. If the
412
+ # given index is outside the range then `nil` is returned.
413
+ #
414
+ # @param index [Integer] index
415
+ # @return [Element, nil]
416
+ def at(index)
417
+ %x{
418
+ var length = self.length;
419
+
420
+ if (index < 0) {
421
+ index += length;
422
+ }
423
+
424
+ if (index < 0 || index >= length) {
425
+ return nil;
426
+ }
427
+
428
+ return $(self[index]);
429
+ }
430
+ end
431
+
432
+ # Returns the CSS class name of the firt element in self collection.
433
+ # If the collection is empty then an empty string is returned. Only
434
+ # the class name of the first element will ever be returned.
435
+ #
436
+ # @return [String]
437
+ def class_name
438
+ %x{
439
+ var first = self[0];
440
+ return (first && first.className) || "";
441
+ }
442
+ end
443
+
444
+ # Sets the CSS class name of every element in self collection to the
445
+ # given string. self does not append the class names, it replaces
446
+ # the entire current class name.
447
+ #
448
+ # @param name [String] class name to set
449
+ def class_name=(name)
450
+ %x{
451
+ for (var i = 0, length = self.length; i < length; i++) {
452
+ self[i].className = name;
453
+ }
454
+ }
455
+ self
456
+ end
457
+
458
+ # Get or set css properties on each element in self collection. If
459
+ # only the `name` is given, then that css property name is read from
460
+ # the first element in the collection and returned. If the `value`
461
+ # property is also given then the given css property is set to the
462
+ # given value for each of the elements in self collection. The
463
+ # property can also be a hash of properties and values.
464
+ def css(name, value=nil)
465
+ if value.nil? && name.is_a?(String)
466
+ return `self.css(name)`
467
+ else
468
+ name.is_a?(Hash) ? `self.css(#{name.to_n})` : `self.css(name, value)`
469
+ end
470
+ self
471
+ end
472
+
473
+ # Set css values over time to create animations. The first parameter is a
474
+ # set of css properties and values to animate to. The first parameter
475
+ # also accepts a special :speed value to set animation speed. If a block
476
+ # is given, the block is run as a callback when the animation finishes.
477
+ def animate(params, &block)
478
+ speed = params.has_key?(:speed) ? params.delete(:speed) : 400
479
+ %x{
480
+ self.animate(#{params.to_n}, #{speed}, function() {
481
+ #{block.call if block_given?}
482
+ })
483
+ }
484
+ end
485
+
486
+ def data(*args)
487
+ %x{
488
+ var result = self.data.apply(self, args);
489
+ return result == null ? nil : result;
490
+ }
491
+ end
492
+
493
+ # Start a visual effect (e.g. fadeIn, fadeOut, …) passing its name.
494
+ # Underscored style is automatically converted (e.g. `effect(:fade_in)`).
495
+ # Also accepts additional arguments and a block for the finished callback.
496
+ def effect(name, *args, &block)
497
+ name = name.gsub(/_\w/) { |match| match[1].upcase }
498
+ args = args.map { |a| a.to_n if a.respond_to? :to_n }.compact
499
+ args << `function() { #{block.call if block_given?} }`
500
+ `self[#{name}].apply(self, #{args})`
501
+ end
502
+
503
+ def visible?
504
+ `self.is(':visible')`
505
+ end
506
+
507
+ def offset
508
+ Native(`self.offset()`)
509
+ end
510
+
511
+ def each
512
+ `for (var i = 0, length = self.length; i < length; i++) {`
513
+ yield `$(self[i])`
514
+ `}`
515
+ self
516
+ end
517
+
518
+ def first
519
+ `self.length ? self.first() : nil`
520
+ end
521
+
522
+ def html(content = undefined)
523
+ %x{
524
+ if (content != null) {
525
+ return self.html(content);
526
+ }
527
+
528
+ return self.html() || '';
529
+ }
530
+ end
531
+
532
+ def id
533
+ %x{
534
+ var first = self[0];
535
+ return (first && first.id) || "";
536
+ }
537
+ end
538
+
539
+ def id=(id)
540
+ %x{
541
+ var first = self[0];
542
+
543
+ if (first) {
544
+ first.id = id;
545
+ }
546
+
547
+ return self;
548
+ }
549
+ end
550
+
551
+ def tag_name
552
+ `self.length > 0 ? self[0].tagName.toLowerCase() : #{nil}`
553
+ end
554
+
555
+ def inspect
556
+ %x{
557
+ if (self[0] === document) return '#<Element [document]>'
558
+ else if (self[0] === window ) return '#<Element [window]>'
559
+
560
+ var val, el, str, result = [];
561
+
562
+ for (var i = 0, length = self.length; i < length; i++) {
563
+ el = self[i];
564
+ if (!el.tagName) { return '#<Element ['+el.toString()+']'; }
565
+
566
+ str = "<" + el.tagName.toLowerCase();
567
+
568
+ if (val = el.id) str += (' id="' + val + '"');
569
+ if (val = el.className) str += (' class="' + val + '"');
570
+
571
+ result.push(str + '>');
572
+ }
573
+
574
+ return '#<Element [' + result.join(', ') + ']>';
575
+ }
576
+ end
577
+
578
+ def to_s
579
+ %x{
580
+ var val, el, result = [];
581
+
582
+ for (var i = 0, length = self.length; i < length; i++) {
583
+ el = self[i];
584
+
585
+ result.push(el.outerHTML)
586
+ }
587
+
588
+ return result.join(', ');
589
+ }
590
+ end
591
+
592
+ # Returns the number of elements in this collection. May be zero.
593
+ # @return [Integer]
594
+ def length
595
+ `self.length`
596
+ end
597
+
598
+ # Returns `true` if this collection has 1 or more elements, `false`
599
+ # otherwise.
600
+ #
601
+ # @return [true, false]
602
+ def any?
603
+ `self.length > 0`
604
+ end
605
+
606
+ # Returns `true` if this collection contains no elements, `false` otherwise.
607
+ #
608
+ # @return [true, false]
609
+ def empty?
610
+ `self.length === 0`
611
+ end
612
+
613
+ alias empty? none?
614
+
615
+ def on(name, sel = nil, &block)
616
+ %x{
617
+ var wrapper = function(evt) {
618
+ if (evt.preventDefault) {
619
+ evt = #{Event.new `evt`};
620
+ }
621
+
622
+ return block.apply(null, arguments);
623
+ };
624
+
625
+ block._jq_wrap = wrapper;
626
+
627
+ if (sel == nil) {
628
+ self.on(name, wrapper);
629
+ }
630
+ else {
631
+ self.on(name, sel, wrapper);
632
+ }
633
+ }
634
+
635
+ block
636
+ end
637
+
638
+ def off(name, sel, block = nil)
639
+ %x{
640
+ if (sel == null) {
641
+ return self.off(name);
642
+ }
643
+ else if (block === nil) {
644
+ return self.off(name, sel._jq_wrap);
645
+ }
646
+ else {
647
+ return self.off(name, sel, block._jq_wrap);
648
+ }
649
+ }
650
+ end
651
+
652
+ alias size length
653
+
654
+ def value
655
+ `self.val() || ""`
656
+ end
657
+
658
+ def height
659
+ `self.height() || nil`
660
+ end
661
+
662
+ def width
663
+ `self.width() || nil`
664
+ end
665
+
666
+ def position
667
+ Native(`self.position()`)
668
+ end
669
+ end