roda-component 0.1.15 → 0.1.16
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Gemfile +1 -0
- data/lib/roda/component/dom.rb +21 -7
- data/lib/roda/component/element.rb +8 -0
- data/lib/roda/component/events.rb +15 -2
- data/lib/roda/component/history.rb +82 -0
- data/lib/roda/component/location.rb +78 -0
- data/lib/roda/component/titleize.rb +4 -4
- data/lib/roda/component/version.rb +1 -1
- data/lib/roda/component.rb +6 -3
- data/lib/roda/plugins/component.rb +4 -3
- data/test/dummy/components/forms/address.rb +1 -1
- data/test/dummy/config.ru +5 -0
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e05764f5a7a8fe5b77136f9891195edaca1359e2
|
4
|
+
data.tar.gz: 1d11a49a6c6c760fa831f26467c98f5fc36f8837
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f214e8ef5271ff4dff4cc64f90da2218169416ed066b75e1b757a62ad64413d375e8f46ce26330f8079560095ad1a5e25ff58f6c22a56e3841a3a0ddcb3e71ad
|
7
|
+
data.tar.gz: 5091aee707250510f74705c00f842c79bde57a9fcaaf96a6106616302db4bdba578e7ab9f39d58fed1412ed158f4de1c6939545d4115d8a17ccfcf978bae312e
|
data/Gemfile
CHANGED
data/lib/roda/component/dom.rb
CHANGED
@@ -7,17 +7,17 @@ class Roda
|
|
7
7
|
@raw_html = html
|
8
8
|
|
9
9
|
if server?
|
10
|
-
@dom = raw_html.is_a?(String) ? Component::HTML(raw_html): raw_html
|
10
|
+
@dom = raw_html.is_a?(String) ? Component::HTML(raw_html.dup): raw_html
|
11
11
|
else
|
12
|
-
@dom = raw_html.is_a?(String) ? Element[raw_html] : raw_html
|
12
|
+
@dom = raw_html.is_a?(String) ? Element[raw_html.dup] : raw_html
|
13
13
|
end
|
14
14
|
end
|
15
15
|
|
16
16
|
def find string, &block
|
17
17
|
if server?
|
18
|
-
|
18
|
+
node = DOM.new dom.css(string)
|
19
19
|
else
|
20
|
-
|
20
|
+
node = DOM.new dom.find(string)
|
21
21
|
end
|
22
22
|
|
23
23
|
if block
|
@@ -26,15 +26,29 @@ class Roda
|
|
26
26
|
end
|
27
27
|
else
|
28
28
|
if server?
|
29
|
-
|
30
|
-
else
|
31
|
-
@node = DOM.new node
|
29
|
+
node = DOM.new node.first
|
32
30
|
end
|
33
31
|
end
|
34
32
|
|
35
33
|
node
|
36
34
|
end
|
37
35
|
|
36
|
+
def data key = false, value = false
|
37
|
+
if server?
|
38
|
+
d = Hash[node.xpath("@*[starts-with(name(), 'data-')]").map{|a| [a.name, a.value]}]
|
39
|
+
|
40
|
+
if !key
|
41
|
+
d
|
42
|
+
elsif key && !value
|
43
|
+
d[key]
|
44
|
+
else
|
45
|
+
node["data-#{key}"] = value
|
46
|
+
end
|
47
|
+
else
|
48
|
+
super
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
38
52
|
def html= content
|
39
53
|
if server?
|
40
54
|
node.inner_html = content
|
@@ -9,6 +9,8 @@ class Roda
|
|
9
9
|
|
10
10
|
class Events < Struct.new(:klass, :component_opts, :scope, :request)
|
11
11
|
def on name, options = {}, form_klass = false, extra_opts = false, &block
|
12
|
+
options = '' if options.empty? && (name.to_s == 'history_change' || name.to_s == 'ready')
|
13
|
+
|
12
14
|
if client? && options.is_a?(String)
|
13
15
|
class_name = klass._name
|
14
16
|
class_events = (events[class_name] ||= {})
|
@@ -34,7 +36,14 @@ class Roda
|
|
34
36
|
def trigger_jquery_events
|
35
37
|
return unless e = events[klass._name]
|
36
38
|
|
37
|
-
|
39
|
+
vip_list = ['history_change']
|
40
|
+
|
41
|
+
j_events = (e[:_jquery_events] || [])
|
42
|
+
j_events = j_events.sort_by do |x|
|
43
|
+
[vip_list.index(x.last.to_s) || vip_list.length, j_events.index(x)]
|
44
|
+
end
|
45
|
+
|
46
|
+
j_events.each do |event|
|
38
47
|
block, comp, selector, form_klass, opts, name = event
|
39
48
|
|
40
49
|
opts = {} unless opts
|
@@ -43,9 +52,13 @@ class Roda
|
|
43
52
|
|
44
53
|
case name.to_s
|
45
54
|
when 'ready'
|
46
|
-
el = Element.find(selector)
|
55
|
+
el = Element.find(selector != '' ? selector : 'body')
|
47
56
|
|
48
57
|
Component::Instance.new(component(comp), scope).instance_exec el, &block
|
58
|
+
when 'history_change'
|
59
|
+
$window.history.change do |he|
|
60
|
+
Component::Instance.new(component(comp), scope).instance_exec he, &block
|
61
|
+
end
|
49
62
|
when 'form'
|
50
63
|
warn 'missing form class option' unless form_klass
|
51
64
|
|
@@ -0,0 +1,82 @@
|
|
1
|
+
require 'roda/component/location'
|
2
|
+
|
3
|
+
module Browser
|
4
|
+
# {Window} instances are {Native} objects used to wrap native window instances.
|
5
|
+
#
|
6
|
+
# Generally, you will want to use the top level {::Window} instance, which
|
7
|
+
# wraps `window` from the main page.
|
8
|
+
class Window
|
9
|
+
include Native
|
10
|
+
|
11
|
+
# @!attribute [r] history
|
12
|
+
# @return [History] the history for this window
|
13
|
+
def history
|
14
|
+
History.new(`#@native.history`) if `#@native.history`
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
# {History} allows manipulation of the session history.
|
19
|
+
#
|
20
|
+
# @see https://developer.mozilla.org/en-US/docs/Web/API/History
|
21
|
+
class History
|
22
|
+
include Native
|
23
|
+
|
24
|
+
# @!attribute [r] length
|
25
|
+
# @return [Integer] how many items are in the history
|
26
|
+
alias_native :length
|
27
|
+
|
28
|
+
# Go back in the history.
|
29
|
+
#
|
30
|
+
# @param number [Integer] how many items to go back
|
31
|
+
def back(number = 1)
|
32
|
+
`History.go(-number)`
|
33
|
+
end
|
34
|
+
|
35
|
+
# Go forward in the history.
|
36
|
+
#
|
37
|
+
# @param number [Integer] how many items to go forward
|
38
|
+
def forward(number = 1)
|
39
|
+
`History.go(number)`
|
40
|
+
end
|
41
|
+
|
42
|
+
# Push an item in the history.
|
43
|
+
#
|
44
|
+
# @param item [String] the item to push in the history
|
45
|
+
# @param data [Object] additional state to push
|
46
|
+
def push(item, data = nil)
|
47
|
+
data = `null` if data.nil?
|
48
|
+
|
49
|
+
`History.pushState(jQuery.parseJSON(data.$to_json()), null, item)`
|
50
|
+
end
|
51
|
+
|
52
|
+
# Replace the current history item with another.
|
53
|
+
#
|
54
|
+
# @param item [String] the item to replace with
|
55
|
+
# @param data [Object] additional state to replace
|
56
|
+
def replace(item, data = nil)
|
57
|
+
data = `null` if data.nil?
|
58
|
+
|
59
|
+
`History.replaceState(data, null, item)`
|
60
|
+
end
|
61
|
+
|
62
|
+
def get_state
|
63
|
+
Native(`History.getState()`)
|
64
|
+
end
|
65
|
+
|
66
|
+
# @!attribute [r] current
|
67
|
+
# @return [String] the current item
|
68
|
+
def current
|
69
|
+
$window.location.path
|
70
|
+
end
|
71
|
+
|
72
|
+
def change &block
|
73
|
+
%x{
|
74
|
+
History.Adapter.bind(window,'statechange',function(e){
|
75
|
+
var state = History.getState();
|
76
|
+
state = #{Native(`state`)}
|
77
|
+
return #{block.call(`state`)}
|
78
|
+
});
|
79
|
+
}
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
@@ -0,0 +1,78 @@
|
|
1
|
+
module Browser
|
2
|
+
|
3
|
+
# Allows manipulation of a location, usually from {Window} and {DOM::Document}.
|
4
|
+
#
|
5
|
+
# @see https://developer.mozilla.org/en-US/docs/Web/API/Location
|
6
|
+
class Location
|
7
|
+
include Native
|
8
|
+
|
9
|
+
# Change the location.
|
10
|
+
#
|
11
|
+
# @param url [String, #to_s] the URL to go to
|
12
|
+
def assign(url)
|
13
|
+
`#@native.assign(#{url.to_s})`
|
14
|
+
end
|
15
|
+
|
16
|
+
# Replace the current URL.
|
17
|
+
#
|
18
|
+
# @param url [String, #to_s] the URL to go to
|
19
|
+
def replace(url)
|
20
|
+
`#@native.replace(#{url.to_s})`
|
21
|
+
end
|
22
|
+
|
23
|
+
# Reload the page.
|
24
|
+
#
|
25
|
+
# @param force [Boolean] whether to force the reload
|
26
|
+
def reload(force = false)
|
27
|
+
`#@native.reload(force)`
|
28
|
+
end
|
29
|
+
|
30
|
+
# Convert the location to a string.
|
31
|
+
def to_s
|
32
|
+
`#@native.toString()`
|
33
|
+
end
|
34
|
+
|
35
|
+
# @!attribute fragment
|
36
|
+
# @return [String] the hash fragment of the location URI
|
37
|
+
alias_native :fragment, :hash
|
38
|
+
alias_native :fragment=, :hash=
|
39
|
+
|
40
|
+
# @!attribute host
|
41
|
+
# @return [String] the host part of the location URI
|
42
|
+
alias_native :host
|
43
|
+
alias_native :host=
|
44
|
+
|
45
|
+
# @!attribute uri
|
46
|
+
# @return [String] the whole location URI
|
47
|
+
alias_native :uri, :href
|
48
|
+
alias_native :uri=, :href=
|
49
|
+
|
50
|
+
# @!attribute path
|
51
|
+
# @return [String] the path part of the location URI
|
52
|
+
alias_native :path, :pathname
|
53
|
+
alias_native :path=, :pathname=
|
54
|
+
|
55
|
+
# @!attribute port
|
56
|
+
# @return [Integer] the port part of the location URI
|
57
|
+
alias_native :port
|
58
|
+
alias_native :port=
|
59
|
+
|
60
|
+
# @!attribute scheme
|
61
|
+
# @return [String] the scheme part of the location URI
|
62
|
+
alias_native :scheme, :protocol
|
63
|
+
alias_native :scheme=, :protocol=
|
64
|
+
|
65
|
+
# @!attribute query
|
66
|
+
# @return [String] the query part of the location URI
|
67
|
+
alias_native :query, :search
|
68
|
+
alias_native :query=, :search=
|
69
|
+
end
|
70
|
+
|
71
|
+
class Window
|
72
|
+
# @!attribute [r] location
|
73
|
+
# @return [Location] the location for the window
|
74
|
+
def location
|
75
|
+
Location.new(`#@native.location`) if `#@native.location`
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
@@ -82,11 +82,11 @@ class String
|
|
82
82
|
# "notes on a scandal" # => "Notes on a Scandal"
|
83
83
|
# "the good german" # => "The Good German"
|
84
84
|
def titleize(opts={})
|
85
|
-
if defined? ActiveSupport
|
86
|
-
|
87
|
-
else
|
85
|
+
# if defined? ActiveSupport
|
86
|
+
# ActiveSupport::Inflector.titleize(self, opts)
|
87
|
+
# else
|
88
88
|
Titleize.titleize(self)
|
89
|
-
end
|
89
|
+
# end
|
90
90
|
end
|
91
91
|
alias_method :titlecase, :titleize
|
92
92
|
|
data/lib/roda/component.rb
CHANGED
@@ -14,6 +14,7 @@ require 'roda/component/titleize'
|
|
14
14
|
|
15
15
|
if RUBY_ENGINE == 'opal'
|
16
16
|
require 'roda/component/element'
|
17
|
+
require 'roda/component/history'
|
17
18
|
|
18
19
|
$component_opts ||= {
|
19
20
|
events: {},
|
@@ -172,7 +173,7 @@ class Roda
|
|
172
173
|
else
|
173
174
|
parsed_html = Nokogiri::HTML.fragment(raw_html)
|
174
175
|
|
175
|
-
if parsed_html.children.length
|
176
|
+
if parsed_html.children.length >= 1
|
176
177
|
parsed_html.children.first
|
177
178
|
else
|
178
179
|
parsed_html
|
@@ -309,7 +310,7 @@ class Roda
|
|
309
310
|
l_dom.find("[data-if]") do |field_dom|
|
310
311
|
value = get_value_for field_dom['data-if'], data
|
311
312
|
|
312
|
-
unless value
|
313
|
+
unless value.present?
|
313
314
|
field_dom.remove
|
314
315
|
end
|
315
316
|
end
|
@@ -317,7 +318,7 @@ class Roda
|
|
317
318
|
l_dom.find("[data-unless]") do |field_dom|
|
318
319
|
value = get_value_for field_dom['data-unless'], data
|
319
320
|
|
320
|
-
if value
|
321
|
+
if value.present?
|
321
322
|
field_dom.remove
|
322
323
|
end
|
323
324
|
end
|
@@ -344,6 +345,8 @@ class Roda
|
|
344
345
|
end
|
345
346
|
end
|
346
347
|
end
|
348
|
+
|
349
|
+
l_dom
|
347
350
|
end
|
348
351
|
|
349
352
|
def get_value_for field, data
|
@@ -90,8 +90,8 @@ class Roda
|
|
90
90
|
Document.ready? do
|
91
91
|
c = $component_opts[:comp][:"#{comp_name}"] = #{comp.class}.new
|
92
92
|
c.instance_variable_set(:@_cache, JSON.parse(Base64.decode64('#{cache}')))
|
93
|
-
c.#{action}(JSON.parse(Base64.decode64('#{options}')))
|
94
93
|
c.events.trigger_jquery_events
|
94
|
+
c.#{action}(JSON.parse(Base64.decode64('#{options}')))
|
95
95
|
end
|
96
96
|
end
|
97
97
|
EOF
|
@@ -110,6 +110,7 @@ class Roda
|
|
110
110
|
|
111
111
|
action = options.delete(:call) || :display
|
112
112
|
trigger = options.delete(:trigger) || false
|
113
|
+
js = options.delete(:js)
|
113
114
|
|
114
115
|
# call action
|
115
116
|
# TODO: make sure the single method parameter isn't a block
|
@@ -131,11 +132,11 @@ class Roda
|
|
131
132
|
|
132
133
|
load_component_js comp, action
|
133
134
|
|
134
|
-
if comp_response.is_a?
|
135
|
+
if js && comp_response.is_a?(Roda::Component::DOM)
|
135
136
|
comp_response = comp_response.to_xml
|
136
137
|
end
|
137
138
|
|
138
|
-
if comp_response.is_a?(String) && js
|
139
|
+
if comp_response.is_a?(String) && js
|
139
140
|
comp_response << component_js
|
140
141
|
end
|
141
142
|
|
data/test/dummy/config.ru
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: roda-component
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.16
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- cj
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-01-
|
11
|
+
date: 2015-01-27 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: opal
|
@@ -326,7 +326,9 @@ files:
|
|
326
326
|
- lib/roda/component/faye.rb
|
327
327
|
- lib/roda/component/form.rb
|
328
328
|
- lib/roda/component/form/validations.rb
|
329
|
+
- lib/roda/component/history.rb
|
329
330
|
- lib/roda/component/instance.rb
|
331
|
+
- lib/roda/component/location.rb
|
330
332
|
- lib/roda/component/titleize.rb
|
331
333
|
- lib/roda/component/version.rb
|
332
334
|
- lib/roda/plugins/component.rb
|