unpoly-rails 0.55.1 → 0.56.0

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of unpoly-rails might be problematic. Click here for more details.

Files changed (50) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +59 -2
  3. data/dist/unpoly-bootstrap3.js +6 -4
  4. data/dist/unpoly-bootstrap3.min.js +1 -1
  5. data/dist/unpoly.js +1323 -805
  6. data/dist/unpoly.min.js +4 -3
  7. data/lib/assets/javascripts/unpoly-bootstrap3/{navigation-ext.coffee → feedback-ext.coffee} +2 -0
  8. data/lib/assets/javascripts/unpoly/browser.coffee.erb +7 -7
  9. data/lib/assets/javascripts/unpoly/bus.coffee.erb +5 -6
  10. data/lib/assets/javascripts/unpoly/classes/css_transition.coffee +127 -0
  11. data/lib/assets/javascripts/unpoly/classes/extract_plan.coffee +1 -1
  12. data/lib/assets/javascripts/unpoly/classes/motion_tracker.coffee +62 -32
  13. data/lib/assets/javascripts/unpoly/classes/url_set.coffee +27 -0
  14. data/lib/assets/javascripts/unpoly/dom.coffee.erb +78 -99
  15. data/lib/assets/javascripts/unpoly/feedback.coffee +147 -96
  16. data/lib/assets/javascripts/unpoly/form.coffee.erb +26 -2
  17. data/lib/assets/javascripts/unpoly/history.coffee +2 -1
  18. data/lib/assets/javascripts/unpoly/layout.coffee.erb +68 -12
  19. data/lib/assets/javascripts/unpoly/link.coffee.erb +10 -4
  20. data/lib/assets/javascripts/unpoly/modal.coffee.erb +11 -9
  21. data/lib/assets/javascripts/unpoly/{motion.coffee → motion.coffee.erb} +184 -322
  22. data/lib/assets/javascripts/unpoly/popup.coffee.erb +13 -12
  23. data/lib/assets/javascripts/unpoly/radio.coffee +1 -1
  24. data/lib/assets/javascripts/unpoly/syntax.coffee +8 -17
  25. data/lib/assets/javascripts/unpoly/tooltip.coffee +11 -11
  26. data/lib/assets/javascripts/unpoly/util.coffee +332 -145
  27. data/lib/unpoly/rails/version.rb +1 -1
  28. data/package.json +1 -1
  29. data/spec_app/Gemfile.lock +1 -1
  30. data/spec_app/app/assets/javascripts/integration_test.coffee +1 -0
  31. data/spec_app/app/assets/stylesheets/integration_test.sass +1 -0
  32. data/spec_app/app/assets/stylesheets/jasmine_specs.sass +4 -0
  33. data/spec_app/app/views/motion_test/transitions.erb +13 -0
  34. data/spec_app/app/views/pages/start.erb +1 -0
  35. data/spec_app/spec/javascripts/helpers/to_be_attached.coffee +5 -0
  36. data/spec_app/spec/javascripts/helpers/to_be_detached.coffee +5 -0
  37. data/spec_app/spec/javascripts/helpers/to_contain.js.coffee +1 -1
  38. data/spec_app/spec/javascripts/helpers/to_have_opacity.coffee +11 -0
  39. data/spec_app/spec/javascripts/helpers/to_have_own_property.js.coffee +5 -0
  40. data/spec_app/spec/javascripts/up/dom_spec.js.coffee +217 -102
  41. data/spec_app/spec/javascripts/up/feedback_spec.js.coffee +162 -44
  42. data/spec_app/spec/javascripts/up/layout_spec.js.coffee +97 -10
  43. data/spec_app/spec/javascripts/up/link_spec.js.coffee +3 -3
  44. data/spec_app/spec/javascripts/up/modal_spec.js.coffee +22 -20
  45. data/spec_app/spec/javascripts/up/motion_spec.js.coffee +344 -228
  46. data/spec_app/spec/javascripts/up/popup_spec.js.coffee +1 -1
  47. data/spec_app/spec/javascripts/up/syntax_spec.js.coffee +1 -1
  48. data/spec_app/spec/javascripts/up/tooltip_spec.js.coffee +1 -1
  49. data/spec_app/spec/javascripts/up/util_spec.js.coffee +194 -0
  50. metadata +11 -4
@@ -16,7 +16,7 @@ describe 'up.popup', ->
16
16
  Math.abs(popupDims.right - linkDims.right) < 1.0 && Math.abs(popupDims.top - linkDims.bottom) < 1.0
17
17
 
18
18
  beforeEach ->
19
- @restoreBodyHeight = u.temporaryCss('body', 'min-height': '3000px')
19
+ @restoreBodyHeight = u.writeTemporaryStyle('body', minHeight: '3000px')
20
20
 
21
21
  afterEach ->
22
22
  @restoreBodyHeight()
@@ -13,7 +13,7 @@ describe 'up.syntax', ->
13
13
  up.hello(affix('.container .child'))
14
14
 
15
15
  expect(observeClass).not.toHaveBeenCalledWith('container')
16
- expect(observeClass).toHaveBeenCalledWith('child')
16
+ expect(observeClass).toHaveBeenCalledWith('child')
17
17
 
18
18
  describe 'destructors', ->
19
19
 
@@ -40,7 +40,7 @@ describe 'up.tooltip', ->
40
40
  )
41
41
 
42
42
  beforeEach ->
43
- @restoreBodyHeight = u.temporaryCss('body', 'min-height': '3000px')
43
+ @restoreBodyHeight = u.writeTemporaryStyle('body', minHeight: '3000px')
44
44
 
45
45
  afterEach ->
46
46
  @restoreBodyHeight()
@@ -135,6 +135,82 @@ describe 'up.util', ->
135
135
  expect(callback).toHaveBeenCalledWith('return value')
136
136
  done()
137
137
 
138
+ describe 'up.util.kebabCase', ->
139
+
140
+ it 'converts a string of multiple words from camel-case to kebap-case', ->
141
+ result = up.util.kebabCase('fooBarBaz')
142
+ expect(result).toEqual('foo-bar-baz')
143
+
144
+ it 'does not change a single word', ->
145
+ result = up.util.kebabCase('foo')
146
+ expect(result).toEqual('foo')
147
+
148
+ it 'downcases the first word when it starts with a capital letter', ->
149
+ result = up.util.kebabCase('FooBar')
150
+ expect(result).toEqual('foo-bar')
151
+
152
+ it 'does not change a string that is already in kebab-case', ->
153
+ result = up.util.kebabCase('foo-bar-baz')
154
+ expect(result).toEqual('foo-bar-baz')
155
+
156
+ describe 'up.util.camelCase', ->
157
+
158
+ it 'converts a string of multiple words from kebap-case to camel-case', ->
159
+ result = up.util.camelCase('foo-bar-baz')
160
+ expect(result).toEqual('fooBarBaz')
161
+
162
+ it 'does not change a single word', ->
163
+ result = up.util.camelCase('foo')
164
+ expect(result).toEqual('foo')
165
+
166
+ it 'downcases the first word when it starts with a capital letter', ->
167
+ result = up.util.camelCase('Foo-Bar')
168
+ expect(result).toEqual('fooBar')
169
+
170
+ it 'does not change a string that is already in camel-case', ->
171
+ result = up.util.camelCase('fooBarBaz')
172
+ expect(result).toEqual('fooBarBaz')
173
+
174
+ describe 'up.util.kebabCaseKeys', ->
175
+
176
+ it "converts the given object's keys from camel-case to kebab-case", ->
177
+ input =
178
+ fooBar: 'one'
179
+ barBaz: 'two'
180
+ result = up.util.kebabCaseKeys(input)
181
+ expect(result).toEqual
182
+ 'foo-bar': 'one'
183
+ 'bar-baz': 'two'
184
+
185
+ it "does not change an object whose keys are already kebab-case", ->
186
+ input =
187
+ 'foo-bar': 'one'
188
+ 'bar-baz': 'two'
189
+ result = up.util.kebabCaseKeys(input)
190
+ expect(result).toEqual
191
+ 'foo-bar': 'one'
192
+ 'bar-baz': 'two'
193
+
194
+ describe 'up.util.camelCaseKeys', ->
195
+
196
+ it "converts the given object's keys from kebab-case to camel-case", ->
197
+ input =
198
+ 'foo-bar': 'one'
199
+ 'bar-baz': 'two'
200
+ result = up.util.camelCaseKeys(input)
201
+ expect(result).toEqual
202
+ fooBar: 'one'
203
+ barBaz: 'two'
204
+
205
+ it "does not change an object whose keys are already camel-case", ->
206
+ input =
207
+ fooBar: 'one'
208
+ barBaz: 'two'
209
+ result = up.util.camelCaseKeys(input)
210
+ expect(result).toEqual
211
+ fooBar: 'one'
212
+ barBaz: 'two'
213
+
138
214
  describe 'up.util.DivertibleChain', ->
139
215
 
140
216
  it "instantiates a task queue whose (2..n)th tasks can be changed by calling '.asap'", (done) ->
@@ -351,6 +427,98 @@ describe 'up.util', ->
351
427
  baz: 'baz-value'
352
428
  bam: 'bam-value'
353
429
 
430
+ it 'does not add empty keys to the returned object if the given object does not have that key', ->
431
+ original =
432
+ foo: 'foo-value'
433
+ whitelisted = up.util.only(original, 'foo', 'bar')
434
+ expect(whitelisted).toHaveOwnProperty('foo')
435
+ expect(whitelisted).not.toHaveOwnProperty('bar')
436
+
437
+ describe 'up.util.readInlineStyle', ->
438
+
439
+ describe 'with a string as second argument', ->
440
+
441
+ it 'returns a CSS value string from an inline [style] attribute', ->
442
+ $div = affix('div').attr('style', 'background-color: #ff0000')
443
+ style = up.util.readInlineStyle($div, 'backgroundColor')
444
+ # Browsers convert colors to rgb() values, even IE11
445
+ expect(style).toEqual('rgb(255, 0, 0)')
446
+
447
+ it 'returns a blank value if the element does not have the given property in the [style] attribute', ->
448
+ $div = affix('div').attr('style', 'background-color: red')
449
+ style = up.util.readInlineStyle($div, 'color')
450
+ expect(style).toBeBlank()
451
+
452
+ it 'returns a blank value the given property is a computed property, but not in the [style] attribute', ->
453
+ $div = affix('div[class="red-background"]')
454
+ inlineStyle = up.util.readInlineStyle($div, 'backgroundColor')
455
+ computedStyle = up.util.readComputedStyle($div, 'backgroundColor')
456
+ expect(computedStyle).toEqual('rgb(255, 0, 0)')
457
+ expect(inlineStyle).toBeBlank()
458
+
459
+ describe 'with an array as second argument', ->
460
+
461
+ it 'returns an object with the given inline [style] properties', ->
462
+ $div = affix('div').attr('style', 'background-color: #ff0000; color: #0000ff')
463
+ style = up.util.readInlineStyle($div, ['backgroundColor', 'color'])
464
+ expect(style).toEqual
465
+ backgroundColor: 'rgb(255, 0, 0)'
466
+ color: 'rgb(0, 0, 255)'
467
+
468
+ it 'returns blank keys if the element does not have the given property in the [style] attribute', ->
469
+ $div = affix('div').attr('style', 'background-color: #ff0000')
470
+ style = up.util.readInlineStyle($div, ['backgroundColor', 'color'])
471
+ expect(style).toHaveOwnProperty('color')
472
+ expect(style.color).toBeBlank()
473
+
474
+ it 'returns a blank value the given property is a computed property, but not in the [style] attribute', ->
475
+ $div = affix('div[class="red-background"]')
476
+ inlineStyleHash = up.util.readInlineStyle($div, ['backgroundColor'])
477
+ computedBackground = up.util.readComputedStyle($div, 'backgroundColor')
478
+ expect(computedBackground).toEqual('rgb(255, 0, 0)')
479
+ expect(inlineStyleHash).toHaveOwnProperty('backgroundColor')
480
+ expect(inlineStyleHash.backgroundColor).toBeBlank()
481
+
482
+ describe 'up.util.writeInlineStyle', ->
483
+
484
+ it "sets the given style properties as the given element's [style] attribute", ->
485
+ $div = affix('div')
486
+ up.util.writeInlineStyle($div, { color: 'red', backgroundColor: 'blue' })
487
+ style = $div.attr('style')
488
+ expect(style).toContain('color: red')
489
+ expect(style).toContain('background-color: blue')
490
+
491
+ it "merges the given style properties into the given element's existing [style] value", ->
492
+ $div = affix('div[style="color: red"]')
493
+ up.util.writeInlineStyle($div, { backgroundColor: 'blue' })
494
+ style = $div.attr('style')
495
+ expect(style).toContain('color: red')
496
+ expect(style).toContain('background-color: blue')
497
+
498
+ it "converts the values of known length properties to px values automatically", ->
499
+ $div = affix('div')
500
+ up.util.writeInlineStyle($div, { paddingTop: 100 })
501
+ style = $div.attr('style')
502
+ expect(style).toContain('padding-top: 100px')
503
+
504
+ describe 'up.util.writeTemporaryStyle', ->
505
+
506
+ it "sets the given inline styles and returns a function that will restore the previous inline styles", ->
507
+ $div = affix('div[style="color: red"]')
508
+ restore = up.util.writeTemporaryStyle($div, { color: 'blue' })
509
+ expect($div.attr('style')).toContain('color: blue')
510
+ expect($div.attr('style')).not.toContain('color: red')
511
+ restore()
512
+ expect($div.attr('style')).not.toContain('color: blue')
513
+ expect($div.attr('style')).toContain('color: red')
514
+
515
+ it "does not restore inherited styles", ->
516
+ $div = affix('div[class="red-background"]')
517
+ restore = up.util.writeTemporaryStyle($div, { backgroundColor: 'blue' })
518
+ expect($div.attr('style')).toContain('background-color: blue')
519
+ restore()
520
+ expect($div.attr('style')).not.toContain('background-color')
521
+
354
522
  describe 'up.util.except', ->
355
523
 
356
524
  it 'returns a copy of the given object but omits the given blacklisted properties', ->
@@ -418,6 +586,29 @@ describe 'up.util', ->
418
586
  expect(up.util.selectorForElement($element)).toBe('[aria-label="foo\\"bar"]')
419
587
 
420
588
 
589
+ describe 'up.util.addTemporaryClass', ->
590
+
591
+ it 'adds the given class to the given element', ->
592
+ $element = affix('.foo.bar')
593
+ element = $element.get(0)
594
+
595
+ expect(element.className).toEqual('foo bar')
596
+
597
+ up.util.addTemporaryClass(element, 'baz')
598
+
599
+ expect(element.className).toEqual('foo bar baz')
600
+
601
+ it 'returns a function that restores the original class', ->
602
+ $element = affix('.foo.bar')
603
+ element = $element.get(0)
604
+
605
+ restoreClass = up.util.addTemporaryClass(element, 'baz')
606
+ expect(element.className).toEqual('foo bar baz')
607
+
608
+ restoreClass()
609
+ expect(element.className).toEqual('foo bar')
610
+
611
+
421
612
  describe 'up.util.castedAttr', ->
422
613
 
423
614
  it 'returns true if the attribute value is the string "true"', ->
@@ -578,6 +769,9 @@ describe 'up.util', ->
578
769
  it 'returns true for an empty object', ->
579
770
  expect(up.util.isBlank({})).toBe(true)
580
771
 
772
+ it 'returns false for a function', ->
773
+ expect(up.util.isBlank((->))).toBe(false)
774
+
581
775
  it 'returns true for an object with at least one key', ->
582
776
  expect(up.util.isBlank({key: 'value'})).toBe(false)
583
777
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: unpoly-rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.55.1
4
+ version: 0.56.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Henning Koch
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-04-13 00:00:00.000000000 Z
11
+ date: 2018-05-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -89,14 +89,15 @@ files:
89
89
  - dist/unpoly.min.css
90
90
  - dist/unpoly.min.js
91
91
  - lib/assets/javascripts/unpoly-bootstrap3.coffee
92
+ - lib/assets/javascripts/unpoly-bootstrap3/feedback-ext.coffee
92
93
  - lib/assets/javascripts/unpoly-bootstrap3/form-ext.coffee
93
94
  - lib/assets/javascripts/unpoly-bootstrap3/layout-ext.coffee
94
95
  - lib/assets/javascripts/unpoly-bootstrap3/modal-ext.coffee
95
- - lib/assets/javascripts/unpoly-bootstrap3/navigation-ext.coffee
96
96
  - lib/assets/javascripts/unpoly.coffee
97
97
  - lib/assets/javascripts/unpoly/browser.coffee.erb
98
98
  - lib/assets/javascripts/unpoly/bus.coffee.erb
99
99
  - lib/assets/javascripts/unpoly/classes/cache.coffee
100
+ - lib/assets/javascripts/unpoly/classes/css_transition.coffee
100
101
  - lib/assets/javascripts/unpoly/classes/extract_cascade.coffee
101
102
  - lib/assets/javascripts/unpoly/classes/extract_plan.coffee
102
103
  - lib/assets/javascripts/unpoly/classes/extract_step.coffee
@@ -106,6 +107,7 @@ files:
106
107
  - lib/assets/javascripts/unpoly/classes/record.coffee
107
108
  - lib/assets/javascripts/unpoly/classes/request.coffee
108
109
  - lib/assets/javascripts/unpoly/classes/response.coffee
110
+ - lib/assets/javascripts/unpoly/classes/url_set.coffee
109
111
  - lib/assets/javascripts/unpoly/dom.coffee.erb
110
112
  - lib/assets/javascripts/unpoly/feedback.coffee
111
113
  - lib/assets/javascripts/unpoly/form.coffee.erb
@@ -114,7 +116,7 @@ files:
114
116
  - lib/assets/javascripts/unpoly/link.coffee.erb
115
117
  - lib/assets/javascripts/unpoly/log.coffee
116
118
  - lib/assets/javascripts/unpoly/modal.coffee.erb
117
- - lib/assets/javascripts/unpoly/motion.coffee
119
+ - lib/assets/javascripts/unpoly/motion.coffee.erb
118
120
  - lib/assets/javascripts/unpoly/namespace.coffee.erb
119
121
  - lib/assets/javascripts/unpoly/popup.coffee.erb
120
122
  - lib/assets/javascripts/unpoly/protocol.coffee
@@ -196,6 +198,7 @@ files:
196
198
  - spec_app/app/views/method_test/page1.erb
197
199
  - spec_app/app/views/method_test/page2.erb
198
200
  - spec_app/app/views/motion_test/animations.erb
201
+ - spec_app/app/views/motion_test/transitions.erb
199
202
  - spec_app/app/views/pages/start.erb
200
203
  - spec_app/app/views/replace_test/_nav.erb
201
204
  - spec_app/app/views/replace_test/page1.erb
@@ -260,7 +263,9 @@ files:
260
263
  - spec_app/spec/javascripts/helpers/restore_body_scroll.js.coffee
261
264
  - spec_app/spec/javascripts/helpers/show_lib_versions.coffee
262
265
  - spec_app/spec/javascripts/helpers/to_be_around.js.coffee
266
+ - spec_app/spec/javascripts/helpers/to_be_attached.coffee
263
267
  - spec_app/spec/javascripts/helpers/to_be_blank.js.coffee
268
+ - spec_app/spec/javascripts/helpers/to_be_detached.coffee
264
269
  - spec_app/spec/javascripts/helpers/to_be_error.coffee
265
270
  - spec_app/spec/javascripts/helpers/to_be_given.js.coffee
266
271
  - spec_app/spec/javascripts/helpers/to_be_jquery.js.coffee
@@ -270,6 +275,8 @@ files:
270
275
  - spec_app/spec/javascripts/helpers/to_contain.js.coffee
271
276
  - spec_app/spec/javascripts/helpers/to_end_with.js.coffee
272
277
  - spec_app/spec/javascripts/helpers/to_equal_jquery.js.coffee
278
+ - spec_app/spec/javascripts/helpers/to_have_opacity.coffee
279
+ - spec_app/spec/javascripts/helpers/to_have_own_property.js.coffee
273
280
  - spec_app/spec/javascripts/helpers/to_have_request_method.js.coffee
274
281
  - spec_app/spec/javascripts/helpers/to_have_unhandled_rejections.coffee
275
282
  - spec_app/spec/javascripts/helpers/to_match_text.js.coffee