unpoly-rails 0.22.0 → 0.22.1
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.
Potentially problematic release.
This version of unpoly-rails might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CHANGELOG.md +14 -0
- data/README_RAILS.md +1 -1
- data/dist/unpoly.js +271 -157
- data/dist/unpoly.min.js +2 -2
- data/lib/assets/javascripts/unpoly/bus.js.coffee +52 -26
- data/lib/assets/javascripts/unpoly/flow.js.coffee +10 -5
- data/lib/assets/javascripts/unpoly/history.js.coffee +1 -0
- data/lib/assets/javascripts/unpoly/layout.js.coffee +17 -5
- data/lib/assets/javascripts/unpoly/link.js.coffee +60 -61
- data/lib/assets/javascripts/unpoly/log.js.coffee +8 -0
- data/lib/assets/javascripts/unpoly/motion.js.coffee +20 -9
- data/lib/assets/javascripts/unpoly/proxy.js.coffee +42 -37
- data/lib/assets/javascripts/unpoly/syntax.js.coffee +46 -7
- data/lib/assets/javascripts/unpoly/util.js.coffee +4 -3
- data/lib/unpoly/rails/version.rb +1 -1
- data/spec_app/spec/javascripts/up/link_spec.js.coffee +104 -9
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6109418137600ed7280a7f3ecb2adb7ab5da2b4f
|
4
|
+
data.tar.gz: 118d634ab654710610a010e42d0d55223cd65a6b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4bd0e2d984e5c55654d201fd095eb4424105000d46f1d22273190f8fea325189a9727152a16d5bf549eb9a990f49f3ef9f5366ff06260b012ad81b7343629e87
|
7
|
+
data.tar.gz: 4f8a3ba9acf52274f0a26a21a600e4d0092694366b935de0ba1e992283f43bbf7b2b6979ef844335ab9d7bf16e985362da3ae3a0c67848ee4ff2ef5425730698
|
data/CHANGELOG.md
CHANGED
@@ -14,6 +14,20 @@ Unreleased
|
|
14
14
|
### Breaking changes
|
15
15
|
|
16
16
|
|
17
|
+
0.22.1
|
18
|
+
------
|
19
|
+
|
20
|
+
### Compatible changes
|
21
|
+
|
22
|
+
- Fix a bug where the document title wasn't restored when using the back
|
23
|
+
and forward buttons
|
24
|
+
- Fix a bug where links would be followed multiple times if the link
|
25
|
+
had an [`up-dash`](/up-dash) attribute without a value and also an `up-target` attribute.
|
26
|
+
- Fix a bug where a link would be followed multiple times if the link's
|
27
|
+
click area was expanded using [`[up-expand]`](/up-expand) and if the
|
28
|
+
link also had an [`up-dash`](/up-dash) attribute.
|
29
|
+
|
30
|
+
|
17
31
|
0.22.0
|
18
32
|
------
|
19
33
|
|
data/README_RAILS.md
CHANGED
@@ -17,7 +17,7 @@ To test whether the current request is a [fragment update](http://unpoly.com/up.
|
|
17
17
|
|
18
18
|
To retrieve the CSS selector that is being [updated](http://unpoly.com/up.replace):
|
19
19
|
|
20
|
-
up.
|
20
|
+
up.target
|
21
21
|
|
22
22
|
The Unpoly frontend will expect an HTML response containing an element that matches this selector. If no such element is found, an error is shown to the user. Server-side code is free to optimize its response by only returning HTML that matches this selector.
|
23
23
|
|
data/dist/unpoly.js
CHANGED
@@ -1110,7 +1110,7 @@ that might save you from loading something like [Underscore.js](http://underscor
|
|
1110
1110
|
@internal
|
1111
1111
|
*/
|
1112
1112
|
measure = function($element, opts) {
|
1113
|
-
var $context, box, contextCoords, coordinates, elementCoords
|
1113
|
+
var $context, $viewport, box, contextCoords, coordinates, elementCoords;
|
1114
1114
|
opts = options(opts, {
|
1115
1115
|
relative: false,
|
1116
1116
|
inner: false,
|
@@ -1147,9 +1147,9 @@ that might save you from loading something like [Underscore.js](http://underscor
|
|
1147
1147
|
box.height = $element.outerHeight();
|
1148
1148
|
}
|
1149
1149
|
if (opts.full) {
|
1150
|
-
viewport =
|
1151
|
-
box.right = viewport.width - (box.left + box.width);
|
1152
|
-
box.bottom = viewport.height - (box.top + box.height);
|
1150
|
+
$viewport = up.layout.viewportOf($element);
|
1151
|
+
box.right = $viewport.width() - (box.left + box.width);
|
1152
|
+
box.bottom = $viewport.height() - (box.top + box.height);
|
1153
1153
|
}
|
1154
1154
|
return box;
|
1155
1155
|
};
|
@@ -1890,6 +1890,16 @@ that might save you from loading something like [Underscore.js](http://underscor
|
|
1890
1890
|
up.error = up.util.error;
|
1891
1891
|
|
1892
1892
|
}).call(this);
|
1893
|
+
|
1894
|
+
/**
|
1895
|
+
Logging
|
1896
|
+
=======
|
1897
|
+
|
1898
|
+
Elaborate wrappers around `window.console`.
|
1899
|
+
Should only used internally since they prefix `ᴜᴘ` to each
|
1900
|
+
printed message.
|
1901
|
+
*/
|
1902
|
+
|
1893
1903
|
(function() {
|
1894
1904
|
var slice = [].slice;
|
1895
1905
|
|
@@ -2280,40 +2290,48 @@ we can't currently get rid off.
|
|
2280
2290
|
Events
|
2281
2291
|
======
|
2282
2292
|
|
2283
|
-
Unpoly
|
2284
|
-
|
2285
|
-
up.on('click', 'button', function(event, $button) {
|
2286
|
-
// $button is a jQuery collection containing
|
2287
|
-
// the clicked <button> element
|
2288
|
-
});
|
2289
|
-
|
2290
|
-
This is roughly equivalent to binding an event listener to `document`
|
2291
|
-
using jQuery's [`on`](http://api.jquery.com/on/).
|
2293
|
+
Most Unpoly interactions emit DOM events that are prefixed with `up:`.
|
2292
2294
|
|
2293
|
-
|
2294
|
-
leaving you with an application without Javascript. This is typically preferable to
|
2295
|
-
a soup of randomly broken Javascript in ancient browsers.
|
2296
|
-
- A jQuery object with the target element is automatically passed to the event handler.
|
2297
|
-
- You can [attach structured data](/up.on#attaching-structured-data) to observed elements.
|
2298
|
-
- The call is shorter.
|
2299
|
-
|
2300
|
-
Many Unpoly interactions also emit DOM events that are prefixed with `up:`.
|
2301
|
-
|
2302
|
-
up.on('up:modal:opened', function(event) {
|
2295
|
+
$(document).on('up:modal:opened', function(event) {
|
2303
2296
|
console.log('A new modal has just opened!');
|
2304
2297
|
});
|
2305
2298
|
|
2306
|
-
Events often have both present (`up:modal:open`
|
2299
|
+
Events often have both present ([`up:modal:open`](/up:modal:open))
|
2300
|
+
and past forms ([`up:modal:opened`](/up:modal:opened)).
|
2301
|
+
|
2307
2302
|
You can usually prevent an action by listening to the present form
|
2308
2303
|
and call `preventDefault()` on the `event` object:
|
2309
2304
|
|
2310
|
-
|
2305
|
+
$(document).on('up:modal:open', function(event) {
|
2311
2306
|
if (event.url == '/evil') {
|
2312
2307
|
// Prevent the modal from opening
|
2313
2308
|
event.preventDefault();
|
2314
2309
|
}
|
2315
2310
|
});
|
2316
2311
|
|
2312
|
+
|
2313
|
+
A better way to bind event listeners
|
2314
|
+
------------------------------------
|
2315
|
+
|
2316
|
+
Instead of using jQuery to bind an event handler to `document`, you can also
|
2317
|
+
use the more convenient [`up.on`](/up.on):
|
2318
|
+
|
2319
|
+
up.on('click', 'button', function(event, $button) {
|
2320
|
+
// $button is a jQuery collection containing
|
2321
|
+
// the clicked <button> element
|
2322
|
+
});
|
2323
|
+
|
2324
|
+
This is roughly equivalent to binding an event listener to `document`
|
2325
|
+
using jQuery's [`on`](http://api.jquery.com/on/).
|
2326
|
+
|
2327
|
+
- Event listeners on [unsupported browsers](/up.browser.isSupported) are silently discarded,
|
2328
|
+
leaving you with an application without Javascript. This is typically preferable to
|
2329
|
+
a soup of randomly broken Javascript in ancient browsers.
|
2330
|
+
- A jQuery object with the target element is automatically passed to the event handler
|
2331
|
+
as a second argument.
|
2332
|
+
- You use an [`up-data`](/up-data) attribute to [attach structured data](/up.on#attaching-structured-data)
|
2333
|
+
to observed elements.
|
2334
|
+
|
2317
2335
|
@class up.bus
|
2318
2336
|
*/
|
2319
2337
|
|
@@ -2418,9 +2436,27 @@ and call `preventDefault()` on the `event` object:
|
|
2418
2436
|
|
2419
2437
|
\#\#\#\# Stopping to listen
|
2420
2438
|
|
2421
|
-
`up.on` returns a function that unbinds the event listeners when called
|
2439
|
+
`up.on` returns a function that unbinds the event listeners when called:
|
2440
|
+
|
2441
|
+
// Define the listener
|
2442
|
+
var listener = function() { ... };
|
2443
|
+
|
2444
|
+
// Binding the listener returns an unbind function
|
2445
|
+
unbind = up.on('click', listener);
|
2446
|
+
|
2447
|
+
// Unbind the listener
|
2448
|
+
unbind()
|
2449
|
+
|
2450
|
+
There is also a function [`up.off`](/up.off) which you can use for the same purpose:
|
2451
|
+
|
2452
|
+
// Define the listener
|
2453
|
+
var listener = function() { ... };
|
2454
|
+
|
2455
|
+
// Bind the listener
|
2456
|
+
up.on('click', listener);
|
2422
2457
|
|
2423
|
-
|
2458
|
+
// Unbind the listener
|
2459
|
+
up.off('click', listener)
|
2424
2460
|
|
2425
2461
|
@function up.on
|
2426
2462
|
@param {String} events
|
@@ -2432,7 +2468,7 @@ and call `preventDefault()` on the `event` object:
|
|
2432
2468
|
@param {Function(event, $element, data)} behavior
|
2433
2469
|
The handler that should be called.
|
2434
2470
|
The function takes the affected element as the first argument (as a jQuery object).
|
2435
|
-
If the element has an `up-data` attribute, its value is parsed as JSON
|
2471
|
+
If the element has an [`up-data`](/up-data) attribute, its value is parsed as JSON
|
2436
2472
|
and passed as a second argument.
|
2437
2473
|
@return {Function}
|
2438
2474
|
A function that unbinds the event listeners when called.
|
@@ -2453,13 +2489,13 @@ and call `preventDefault()` on the `event` object:
|
|
2453
2489
|
};
|
2454
2490
|
|
2455
2491
|
/**
|
2456
|
-
|
2492
|
+
Unbinds an event listener previously bound with [`up.on`](/up.on).
|
2457
2493
|
|
2458
2494
|
\#\#\#\# Example
|
2459
2495
|
|
2460
2496
|
Let's say you are listing to clicks on `.button` elements:
|
2461
2497
|
|
2462
|
-
var listener = function() { };
|
2498
|
+
var listener = function() { ... };
|
2463
2499
|
up.on('click', '.button', listener);
|
2464
2500
|
|
2465
2501
|
You can stop listening to these events like this:
|
@@ -2771,11 +2807,11 @@ later.
|
|
2771
2807
|
Registers a function to be called whenever an element with
|
2772
2808
|
the given selector is inserted into the DOM.
|
2773
2809
|
|
2774
|
-
|
2810
|
+
up.compiler('.action', function($element) {
|
2775
2811
|
// your code here
|
2776
2812
|
});
|
2777
2813
|
|
2778
|
-
|
2814
|
+
The functions will be called on elements maching `.action` when
|
2779
2815
|
the page loads, or whenever a matching fragment is [updated through Unpoly](/up.replace)
|
2780
2816
|
later.
|
2781
2817
|
|
@@ -2860,7 +2896,7 @@ later.
|
|
2860
2896
|
{ lat: 48.75, lng: 11.45, title: 'Ingolstadt' }
|
2861
2897
|
]"></div>
|
2862
2898
|
|
2863
|
-
The JSON will parsed and handed to your
|
2899
|
+
The JSON will parsed and handed to your compiler as a second argument:
|
2864
2900
|
|
2865
2901
|
up.compiler('.google-map', function($element, pins) {
|
2866
2902
|
|
@@ -2920,7 +2956,7 @@ later.
|
|
2920
2956
|
@param {Function($element, data)} compiler
|
2921
2957
|
The function to call when a matching element is inserted.
|
2922
2958
|
The function takes the new element as the first argument (as a jQuery object).
|
2923
|
-
If the element has an `up-data` attribute, its value is parsed as JSON
|
2959
|
+
If the element has an [`up-data`](/up-data) attribute, its value is parsed as JSON
|
2924
2960
|
and passed as a second argument.
|
2925
2961
|
|
2926
2962
|
The function may return a destructor function that destroys the compiled
|
@@ -3094,11 +3130,21 @@ later.
|
|
3094
3130
|
};
|
3095
3131
|
|
3096
3132
|
/**
|
3097
|
-
Checks if the given element has an `up-data` attribute.
|
3133
|
+
Checks if the given element has an [`up-data`](/up-data) attribute.
|
3098
3134
|
If yes, parses the attribute value as JSON and returns the parsed object.
|
3099
3135
|
|
3100
3136
|
Returns an empty object if the element has no `up-data` attribute.
|
3101
3137
|
|
3138
|
+
\#\#\#\# Example
|
3139
|
+
|
3140
|
+
You have an element with JSON data serialized into an `up-data` attribute:
|
3141
|
+
|
3142
|
+
<span class="person" up-data="{ age: 18, name: 'Bob' }">Bob</span>
|
3143
|
+
|
3144
|
+
Calling `up.syntax.data` will deserialize the JSON string into a Javascript object:
|
3145
|
+
|
3146
|
+
up.syntax.data('.person') // returns { age: 18, name: 'Bob' }
|
3147
|
+
|
3102
3148
|
@function up.syntax.data
|
3103
3149
|
@param {String|Element|jQuery} elementOrSelector
|
3104
3150
|
@return
|
@@ -3108,15 +3154,44 @@ later.
|
|
3108
3154
|
@experimental
|
3109
3155
|
*/
|
3110
3156
|
|
3111
|
-
|
3157
|
+
/**
|
3112
3158
|
If an element annotated with [`up-data`] is inserted into the DOM,
|
3113
3159
|
Up will parse the JSON and pass the resulting object to any matching
|
3114
|
-
[`up.compiler`](/up.
|
3160
|
+
[`up.compiler`](/up.compiler) handlers.
|
3161
|
+
|
3162
|
+
For instance, a container for a [Google Map](https://developers.google.com/maps/documentation/javascript/tutorial)
|
3163
|
+
might attach the location and names of its marker pins:
|
3164
|
+
|
3165
|
+
<div class="google-map" up-data="[
|
3166
|
+
{ lat: 48.36, lng: 10.99, title: 'Friedberg' },
|
3167
|
+
{ lat: 48.75, lng: 11.45, title: 'Ingolstadt' }
|
3168
|
+
]"></div>
|
3169
|
+
|
3170
|
+
The JSON will parsed and handed to your compiler as a second argument:
|
3171
|
+
|
3172
|
+
up.compiler('.google-map', function($element, pins) {
|
3173
|
+
|
3174
|
+
var map = new google.maps.Map($element);
|
3175
|
+
|
3176
|
+
pins.forEach(function(pin) {
|
3177
|
+
var position = new google.maps.LatLng(pin.lat, pin.lng);
|
3178
|
+
new google.maps.Marker({
|
3179
|
+
position: position,
|
3180
|
+
map: map,
|
3181
|
+
title: pin.title
|
3182
|
+
});
|
3183
|
+
});
|
3184
|
+
|
3185
|
+
});
|
3115
3186
|
|
3116
3187
|
Similarly, when an event is triggered on an element annotated with
|
3117
3188
|
[`up-data`], the parsed object will be passed to any matching
|
3118
3189
|
[`up.on`](/up.on) handlers.
|
3119
3190
|
|
3191
|
+
up.on('click', '.google-map', function(event, $element, pins) {
|
3192
|
+
console.log("There are %d pins on the clicked map", pins.length);
|
3193
|
+
});
|
3194
|
+
|
3120
3195
|
@selector [up-data]
|
3121
3196
|
@param {JSON} up-data
|
3122
3197
|
A serialized JSON string
|
@@ -3334,6 +3409,7 @@ We need to work on this page:
|
|
3334
3409
|
popSelector = config.popTargets.join(', ');
|
3335
3410
|
return up.replace(popSelector, url, {
|
3336
3411
|
history: false,
|
3412
|
+
title: true,
|
3337
3413
|
reveal: false,
|
3338
3414
|
transition: 'none',
|
3339
3415
|
saveScroll: false,
|
@@ -3424,7 +3500,19 @@ We need to work on this page:
|
|
3424
3500
|
Application layout
|
3425
3501
|
==================
|
3426
3502
|
|
3427
|
-
|
3503
|
+
You can [make Unpoly aware](/up.layout.config) of fixed elements in your
|
3504
|
+
layout, such as navigation bars or headers. Unpoly will respect these sticky
|
3505
|
+
elements when [revealing elements](/up.reveal) or [opening a modal dialog](/up-modal).
|
3506
|
+
|
3507
|
+
This modules also contains functions to programmatically [scroll a viewport](/up.scroll)
|
3508
|
+
or [reveal an element within its viewport](/up.reveal).
|
3509
|
+
|
3510
|
+
Bootstrap integration
|
3511
|
+
---------------------
|
3512
|
+
|
3513
|
+
When using Bootstrap integration (`unpoly-bootstrap3.js` and `unpoly-bootstrap3.css`)
|
3514
|
+
Unpoly will automatically be aware of sticky Bootstrap components such as
|
3515
|
+
[fixed navbar](https://getbootstrap.com/examples/navbar-fixed-top/).
|
3428
3516
|
|
3429
3517
|
@class up.layout
|
3430
3518
|
*/
|
@@ -3452,17 +3540,17 @@ This modules contains functions to scroll the viewport and reveal contained elem
|
|
3452
3540
|
@param {Array} [config.anchoredRight]
|
3453
3541
|
An array of CSS selectors that find elements anchored to the
|
3454
3542
|
right edge of the screen (using `position: fixed` or `position: absolute`).
|
3455
|
-
@param {Number} [config.duration]
|
3543
|
+
@param {Number} [config.duration=0]
|
3456
3544
|
The duration of the scrolling animation in milliseconds.
|
3457
3545
|
Setting this to `0` will disable scrolling animations.
|
3458
|
-
@param {String} [config.easing]
|
3546
|
+
@param {String} [config.easing='swing']
|
3459
3547
|
The timing function that controls the animation's acceleration.
|
3460
3548
|
See [W3C documentation](http://www.w3.org/TR/css3-transitions/#transition-timing-function)
|
3461
3549
|
for a list of pre-defined timing functions.
|
3462
|
-
@param {Number} [config.snap]
|
3550
|
+
@param {Number} [config.snap=50]
|
3463
3551
|
When [revealing](/up.reveal) elements, Unpoly will scroll an viewport
|
3464
3552
|
to the top when the revealed element is closer to the top than `config.snap`.
|
3465
|
-
@param {Number} [config.substance]
|
3553
|
+
@param {Number} [config.substance=150]
|
3466
3554
|
A number indicating how many top pixel rows of an element to [reveal](/up.reveal).
|
3467
3555
|
@stable
|
3468
3556
|
*/
|
@@ -4034,8 +4122,8 @@ This modules contains functions to scroll the viewport and reveal contained elem
|
|
4034
4122
|
Changing page fragments programmatically
|
4035
4123
|
========================================
|
4036
4124
|
|
4037
|
-
This module contains Unpoly's core functions to [change](/up.replace) or
|
4038
|
-
|
4125
|
+
This module contains Unpoly's core functions to [change](/up.replace) or
|
4126
|
+
[destroy](/up.destroy) page fragments via Javascript.
|
4039
4127
|
|
4040
4128
|
All the other Unpoly modules (like [`up.link`](/up.link) or [`up.modal`](/up.modal))
|
4041
4129
|
are based on this module.
|
@@ -4167,7 +4255,7 @@ are based on this module.
|
|
4167
4255
|
the CSS selector for the updating fragment.
|
4168
4256
|
|
4169
4257
|
If you are using the `unpoly-rails` gem you can also access the selector via
|
4170
|
-
`up.
|
4258
|
+
`up.target` in all controllers, views and helpers.
|
4171
4259
|
|
4172
4260
|
\#\#\#\# Events
|
4173
4261
|
|
@@ -4262,6 +4350,9 @@ are based on this module.
|
|
4262
4350
|
var isReloadable, newRequest, query, urlFromServer;
|
4263
4351
|
options.method = u.normalizeMethod(u.option(u.methodFromXhr(xhr), options.method));
|
4264
4352
|
options.title = u.option(u.titleFromXhr(xhr), options.title);
|
4353
|
+
if (!(options.title === false || u.isString(options.title) || (options.history === false && options.title !== true))) {
|
4354
|
+
options.title = u.titleFromXhr(xhr);
|
4355
|
+
}
|
4265
4356
|
isReloadable = options.method === 'GET';
|
4266
4357
|
if (urlFromServer = u.locationFromXhr(xhr)) {
|
4267
4358
|
url = urlFromServer;
|
@@ -4424,10 +4515,10 @@ are based on this module.
|
|
4424
4515
|
};
|
4425
4516
|
};
|
4426
4517
|
updateHistory = function(options) {
|
4518
|
+
if (options.title) {
|
4519
|
+
document.title = options.title;
|
4520
|
+
}
|
4427
4521
|
if (options.history) {
|
4428
|
-
if (options.title) {
|
4429
|
-
document.title = options.title;
|
4430
|
-
}
|
4431
4522
|
return up.history[options.historyMethod](options.history);
|
4432
4523
|
}
|
4433
4524
|
};
|
@@ -4645,7 +4736,7 @@ are based on this module.
|
|
4645
4736
|
|
4646
4737
|
/**
|
4647
4738
|
Compiles a page fragment that has been inserted into the DOM
|
4648
|
-
|
4739
|
+
by external code.
|
4649
4740
|
|
4650
4741
|
**As long as you manipulate the DOM using Unpoly, you will never
|
4651
4742
|
need to call this method.** You only need to use `up.hello` if the
|
@@ -4938,6 +5029,9 @@ to smoothly fade out the old `.list` while fading in the new `.list`:
|
|
4938
5029
|
|
4939
5030
|
<a href="/users" up-target=".list" up-transition="cross-fade">Show users</a>
|
4940
5031
|
|
5032
|
+
Transitions vs. animations
|
5033
|
+
--------------------------
|
5034
|
+
|
4941
5035
|
When we morph between an old an new element, we call it a *transition*.
|
4942
5036
|
In contrast, when we animate a new element without simultaneously removing an
|
4943
5037
|
old element, we call it an *animation*.
|
@@ -4947,6 +5041,9 @@ using the `up-animation` attribute:
|
|
4947
5041
|
|
4948
5042
|
<a href="/users" up-modal=".list" up-animation="move-from-top">Show users</a>
|
4949
5043
|
|
5044
|
+
Predefined animations and transitions
|
5045
|
+
-------------------------------------
|
5046
|
+
|
4950
5047
|
Unpoly ships with a number of predefined [animations](/up.animate#named-animation)
|
4951
5048
|
and [transitions](/up.morph#named-animation).
|
4952
5049
|
You can also easily [define your own animations](/up.animation)
|
@@ -5391,7 +5488,7 @@ or [transitions](/up.transition) using Javascript or CSS.
|
|
5391
5488
|
If you choose to *not* use `up.animate` and roll your own
|
5392
5489
|
logic instead, your code must honor the following contract:
|
5393
5490
|
|
5394
|
-
1. It must honor the passed options
|
5491
|
+
1. It must honor the passed options `{ delay, duration, easing }` if present
|
5395
5492
|
2. It must *not* remove any of the given elements from the DOM.
|
5396
5493
|
3. It returns a promise that is resolved when the transition ends
|
5397
5494
|
4. The returned promise responds to a `resolve()` function that
|
@@ -5414,8 +5511,8 @@ or [transitions](/up.transition) using Javascript or CSS.
|
|
5414
5511
|
|
5415
5512
|
Here is the definition of the pre-defined `fade-in` animation:
|
5416
5513
|
|
5417
|
-
up.animation('fade-in', function($
|
5418
|
-
$
|
5514
|
+
up.animation('fade-in', function($element, options) {
|
5515
|
+
$element.css(opacity: 0);
|
5419
5516
|
up.animate($ghost, { opacity: 1 }, options);
|
5420
5517
|
})
|
5421
5518
|
|
@@ -5426,7 +5523,7 @@ or [transitions](/up.transition) using Javascript or CSS.
|
|
5426
5523
|
If you choose to *not* use `up.animate` and roll your own
|
5427
5524
|
animation code instead, your code must honor the following contract:
|
5428
5525
|
|
5429
|
-
1. It must honor the passed options
|
5526
|
+
1. It must honor the passed options `{ delay, duration, easing }` if present
|
5430
5527
|
2. It must *not* remove the passed element from the DOM.
|
5431
5528
|
3. It returns a promise that is resolved when the animation ends
|
5432
5529
|
4. The returned promise responds to a `resolve()` function that
|
@@ -5449,15 +5546,20 @@ or [transitions](/up.transition) using Javascript or CSS.
|
|
5449
5546
|
};
|
5450
5547
|
|
5451
5548
|
/**
|
5452
|
-
Returns a new
|
5549
|
+
Returns a new deferred that resolves once all given deferreds have resolved.
|
5453
5550
|
|
5454
5551
|
Other then [`$.when` from jQuery](https://api.jquery.com/jquery.when/),
|
5455
|
-
the combined
|
5456
|
-
will resolve all the wrapped
|
5552
|
+
the combined deferred will have a `resolve` method. This `resolve` method
|
5553
|
+
will resolve all the wrapped deferreds.
|
5554
|
+
|
5555
|
+
This is important when composing multiple existing animations into
|
5556
|
+
a [custom transition](/up.transition), since the transition function
|
5557
|
+
must return a deferred with a `resolve` function that fast-forwards
|
5558
|
+
the animation to its last frame.
|
5457
5559
|
|
5458
5560
|
@function up.motion.when
|
5459
|
-
@param
|
5460
|
-
@return A new
|
5561
|
+
@param {Array<Deferred>} deferreds...
|
5562
|
+
@return {Deferred} A new deferred
|
5461
5563
|
@experimental
|
5462
5564
|
*/
|
5463
5565
|
resolvableWhen = u.resolvableWhen;
|
@@ -5641,7 +5743,7 @@ Caching and preloading
|
|
5641
5743
|
All HTTP requests go through the Unpoly proxy.
|
5642
5744
|
It caches a [limited](/up.proxy.config) number of server responses
|
5643
5745
|
for a [limited](/up.proxy.config) amount of time,
|
5644
|
-
making requests to these URLs return
|
5746
|
+
making requests to these URLs return instantly.
|
5645
5747
|
|
5646
5748
|
The cache is cleared whenever the user makes a non-`GET` request
|
5647
5749
|
(like `POST`, `PUT` or `DELETE`).
|
@@ -5651,42 +5753,6 @@ links when the user hovers over the click area](/up-preload) (or puts the mouse/
|
|
5651
5753
|
down before releasing). This way the response will already be cached when
|
5652
5754
|
the user performs the click.
|
5653
5755
|
|
5654
|
-
Spinners
|
5655
|
-
--------
|
5656
|
-
|
5657
|
-
You can [listen](/up.on) to the [`up:proxy:slow`](/up:proxy:slow)
|
5658
|
-
and [`up:proxy:recover`](/up:proxy:recover) events to implement a spinner
|
5659
|
-
that appears during a long-running request,
|
5660
|
-
and disappears once the response has been received:
|
5661
|
-
|
5662
|
-
<div class="spinner">Please wait!</div>
|
5663
|
-
|
5664
|
-
Here is the Javascript to make it alive:
|
5665
|
-
|
5666
|
-
up.compiler('.spinner', function($element) {
|
5667
|
-
|
5668
|
-
show = function() { $element.show() };
|
5669
|
-
hide = function() { $element.hide() };
|
5670
|
-
|
5671
|
-
showOff = up.on('up:proxy:slow', show);
|
5672
|
-
hideOff = up.on('up:proxy:recover', hide);
|
5673
|
-
|
5674
|
-
hide();
|
5675
|
-
|
5676
|
-
// Clean up when the element is removed from the DOM
|
5677
|
-
return function() {
|
5678
|
-
showOff();
|
5679
|
-
hideOff();
|
5680
|
-
};
|
5681
|
-
|
5682
|
-
});
|
5683
|
-
|
5684
|
-
The `up:proxy:slow` event will be emitted after a delay of 300 ms
|
5685
|
-
to prevent the spinner from flickering on and off.
|
5686
|
-
You can change (or remove) this delay by [configuring `up.proxy`](/up.proxy.config) like this:
|
5687
|
-
|
5688
|
-
up.proxy.config.slowDelay = 150;
|
5689
|
-
|
5690
5756
|
@class up.proxy
|
5691
5757
|
*/
|
5692
5758
|
|
@@ -5987,6 +6053,43 @@ You can change (or remove) this delay by [configuring `up.proxy`](/up.proxy.conf
|
|
5987
6053
|
Note that if additional requests are made while Unpoly is already busy
|
5988
6054
|
waiting, **no** additional `up:proxy:slow` events will be triggered.
|
5989
6055
|
|
6056
|
+
|
6057
|
+
\#\#\#\# Spinners
|
6058
|
+
|
6059
|
+
You can [listen](/up.on) to the `up:proxy:slow`
|
6060
|
+
and [`up:proxy:recover`](/up:proxy:recover) events to implement a spinner
|
6061
|
+
that appears during a long-running request,
|
6062
|
+
and disappears once the response has been received:
|
6063
|
+
|
6064
|
+
<div class="spinner">Please wait!</div>
|
6065
|
+
|
6066
|
+
Here is the Javascript to make it alive:
|
6067
|
+
|
6068
|
+
up.compiler('.spinner', function($element) {
|
6069
|
+
|
6070
|
+
show = function() { $element.show() };
|
6071
|
+
hide = function() { $element.hide() };
|
6072
|
+
|
6073
|
+
showOff = up.on('up:proxy:slow', show);
|
6074
|
+
hideOff = up.on('up:proxy:recover', hide);
|
6075
|
+
|
6076
|
+
hide();
|
6077
|
+
|
6078
|
+
// Clean up when the element is removed from the DOM
|
6079
|
+
return function() {
|
6080
|
+
showOff();
|
6081
|
+
hideOff();
|
6082
|
+
};
|
6083
|
+
|
6084
|
+
});
|
6085
|
+
|
6086
|
+
The `up:proxy:slow` event will be emitted after a delay of 300 ms
|
6087
|
+
to prevent the spinner from flickering on and off.
|
6088
|
+
You can change (or remove) this delay by [configuring `up.proxy`](/up.proxy.config) like this:
|
6089
|
+
|
6090
|
+
up.proxy.config.slowDelay = 150;
|
6091
|
+
|
6092
|
+
|
5990
6093
|
@event up:proxy:slow
|
5991
6094
|
@stable
|
5992
6095
|
*/
|
@@ -6004,6 +6107,10 @@ You can change (or remove) this delay by [configuring `up.proxy`](/up.proxy.conf
|
|
6004
6107
|
This event is [emitted]/(up.emit) when [AJAX requests](/up.ajax)
|
6005
6108
|
have [taken long to finish](/up:proxy:slow), but have finished now.
|
6006
6109
|
|
6110
|
+
See [`up:proxy:slow`](/up:proxy:slow) for more documentation on
|
6111
|
+
how to use this event for implementing a spinner that shows during
|
6112
|
+
long-running requests.
|
6113
|
+
|
6007
6114
|
@event up:proxy:recover
|
6008
6115
|
@stable
|
6009
6116
|
*/
|
@@ -6186,10 +6293,27 @@ You can change (or remove) this delay by [configuring `up.proxy`](/up.proxy.conf
|
|
6186
6293
|
Linking to page fragments
|
6187
6294
|
=========================
|
6188
6295
|
|
6189
|
-
|
6296
|
+
Standard HTML links are a poor fit for modern applications:
|
6297
|
+
|
6298
|
+
- State changes caused by AJAX updates get lost during the page transition.
|
6299
|
+
- Unsaved form changes get lost during the page transition.
|
6300
|
+
- The Javascript VM is reset during the page transition.
|
6301
|
+
- If the page layout is composed from multiple srollable containers
|
6302
|
+
(e.g. a pane view), the scroll positions get lost during the page transition.
|
6303
|
+
- The user sees a "flash" as the browser loads and renders the new page,
|
6304
|
+
even if large portions of the old and new page are the same (navigation, layout, etc.).
|
6305
|
+
|
6306
|
+
Unpoly fixes this by letting you annotate links with an [`up-target`](/up-target)
|
6307
|
+
attribute. The value of this attribute is a CSS selector that indicates which page
|
6308
|
+
fragment to update. The rest of the page will remain unchanged.
|
6309
|
+
|
6310
|
+
|
6311
|
+
Exammple
|
6312
|
+
--------
|
6190
6313
|
|
6191
6314
|
Let's say we are rendering three pages with a tabbed navigation to switch between screens:
|
6192
6315
|
|
6316
|
+
|
6193
6317
|
```
|
6194
6318
|
/pages/a /pages/b /pages/c
|
6195
6319
|
|
@@ -6216,27 +6340,8 @@ Your HTML could look like this:
|
|
6216
6340
|
</article>
|
6217
6341
|
```
|
6218
6342
|
|
6219
|
-
|
6220
|
-
|
6221
|
-
|
6222
|
-
- State changes caused by AJAX updates get lost during the page transition.
|
6223
|
-
- Unsaved form changes get lost during the page transition.
|
6224
|
-
- The Javascript VM is reset during the page transition.
|
6225
|
-
- If the page layout is composed from multiple srollable containers
|
6226
|
-
(e.g. a pane view), the scroll positions get lost during the page transition.
|
6227
|
-
- The user sees a "flash" as the browser loads and renders the new page,
|
6228
|
-
even if large portions of the old and new page are the same (navigation, layout, etc.).
|
6229
|
-
|
6230
|
-
|
6231
|
-
Smoother flow by updating fragments
|
6232
|
-
-----------------------------------
|
6233
|
-
|
6234
|
-
In Unpoly you annotate navigation links with an `up-target` attribute.
|
6235
|
-
The value of this attribute is a CSS selector that indicates which page
|
6236
|
-
fragment to update.
|
6237
|
-
|
6238
|
-
Since we only want to update the `<article>` tag, we will use `up-target="article"`:
|
6239
|
-
|
6343
|
+
Since we only want to update the `<article>` tag, we annotate the links
|
6344
|
+
with an `up-target` attribute:
|
6240
6345
|
|
6241
6346
|
```
|
6242
6347
|
<nav>
|
@@ -6246,10 +6351,11 @@ Since we only want to update the `<article>` tag, we will use `up-target="articl
|
|
6246
6351
|
</nav>
|
6247
6352
|
```
|
6248
6353
|
|
6249
|
-
|
6354
|
+
Note that instead of `article` you can use any other CSS selector like `#main .article`.
|
6250
6355
|
|
6251
|
-
With these `up-target` annotations Unpoly only updates the targeted part of the screen.
|
6252
|
-
Javascript will
|
6356
|
+
With these [`up-target`](/up-target) annotations Unpoly only updates the targeted part of the screen.
|
6357
|
+
The Javascript environment will persist and the user will not see a white flash while the
|
6358
|
+
new page is loading.
|
6253
6359
|
|
6254
6360
|
|
6255
6361
|
Read on
|
@@ -6594,6 +6700,41 @@ Read on
|
|
6594
6700
|
return follow($link);
|
6595
6701
|
});
|
6596
6702
|
|
6703
|
+
/**
|
6704
|
+
Marks up the current link to be followed *as fast as possible*.
|
6705
|
+
This is done by:
|
6706
|
+
|
6707
|
+
- [Following the link through AJAX](/up-target) instead of a full page load
|
6708
|
+
- [Preloading the link's destination URL](/up-preload)
|
6709
|
+
- [Triggering the link on `mousedown`](/up-instant) instead of on `click`
|
6710
|
+
|
6711
|
+
Use `up-dash` like this:
|
6712
|
+
|
6713
|
+
<a href="/users" up-dash=".main">User list</a>
|
6714
|
+
|
6715
|
+
Note that this is shorthand for:
|
6716
|
+
|
6717
|
+
<a href="/users" up-target=".main" up-instant up-preload>User list</a>
|
6718
|
+
|
6719
|
+
@selector [up-dash]
|
6720
|
+
@stable
|
6721
|
+
*/
|
6722
|
+
up.macro('[up-dash]', function($element) {
|
6723
|
+
var newAttrs, target;
|
6724
|
+
target = u.castedAttr($element, 'up-dash');
|
6725
|
+
$element.removeAttr('up-dash');
|
6726
|
+
newAttrs = {
|
6727
|
+
'up-preload': '',
|
6728
|
+
'up-instant': ''
|
6729
|
+
};
|
6730
|
+
if (target === true) {
|
6731
|
+
makeFollowable($element);
|
6732
|
+
} else {
|
6733
|
+
newAttrs['up-target'] = target;
|
6734
|
+
}
|
6735
|
+
return u.setMissingAttrs($element, newAttrs);
|
6736
|
+
});
|
6737
|
+
|
6597
6738
|
/**
|
6598
6739
|
Add an `up-expand` class to any element that contains a link
|
6599
6740
|
in order to enlarge the link's click area.
|
@@ -6654,41 +6795,6 @@ Read on
|
|
6654
6795
|
return makeFollowable($area);
|
6655
6796
|
}
|
6656
6797
|
});
|
6657
|
-
|
6658
|
-
/**
|
6659
|
-
Marks up the current link to be followed *as fast as possible*.
|
6660
|
-
This is done by:
|
6661
|
-
|
6662
|
-
- [Following the link through AJAX](/up-target) instead of a full page load
|
6663
|
-
- [Preloading the link's destination URL](/up-preload)
|
6664
|
-
- [Triggering the link on `mousedown`](/up-instant) instead of on `click`
|
6665
|
-
|
6666
|
-
Use `up-dash` like this:
|
6667
|
-
|
6668
|
-
<a href="/users" up-dash=".main">User list</a>
|
6669
|
-
|
6670
|
-
Note that this is shorthand for:
|
6671
|
-
|
6672
|
-
<a href="/users" up-target=".main" up-instant up-preload>User list</a>
|
6673
|
-
|
6674
|
-
@selector [up-dash]
|
6675
|
-
@stable
|
6676
|
-
*/
|
6677
|
-
up.macro('[up-dash]', function($element) {
|
6678
|
-
var newAttrs, target;
|
6679
|
-
target = u.castedAttr($element, 'up-dash');
|
6680
|
-
newAttrs = {
|
6681
|
-
'up-preload': 'true',
|
6682
|
-
'up-instant': 'true'
|
6683
|
-
};
|
6684
|
-
if (target === true) {
|
6685
|
-
newAttrs['up-follow'] = '';
|
6686
|
-
} else {
|
6687
|
-
newAttrs['up-target'] = target;
|
6688
|
-
}
|
6689
|
-
u.setMissingAttrs($element, newAttrs);
|
6690
|
-
return $element.removeAttr('up-dash');
|
6691
|
-
});
|
6692
6798
|
return {
|
6693
6799
|
knife: eval(typeof Knife !== "undefined" && Knife !== null ? Knife.point : void 0),
|
6694
6800
|
visit: visit,
|
@@ -7028,7 +7134,7 @@ open dialogs with sub-forms, etc. all without losing form state.
|
|
7028
7134
|
|
7029
7135
|
@function up.autosubmit
|
7030
7136
|
@param {String|Element|jQuery} selectorOrElement
|
7031
|
-
The form
|
7137
|
+
The field or form to observe.
|
7032
7138
|
@param {Object} [options]
|
7033
7139
|
See options for [`up.observe`](/up.observe)
|
7034
7140
|
@return {Function}
|
@@ -7579,7 +7685,15 @@ open dialogs with sub-forms, etc. all without losing form state.
|
|
7579
7685
|
text field value changes:
|
7580
7686
|
|
7581
7687
|
<form method="GET" action="/search" up-autosubmit>
|
7582
|
-
<input type="query">
|
7688
|
+
<input type="search" name="query">
|
7689
|
+
</form>
|
7690
|
+
|
7691
|
+
The following would submit the form only if the query was changed,
|
7692
|
+
but not if the checkbox was changed:
|
7693
|
+
|
7694
|
+
<form method="GET" action="/search">
|
7695
|
+
<input type="search" name="query" autosubmit>
|
7696
|
+
<input type="checkbox"> Include archive
|
7583
7697
|
</form>
|
7584
7698
|
|
7585
7699
|
@selector [up-autosubmit]
|