@jsenv/navi 0.29.388 → 0.29.389
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.
- package/dist/dev/jsenv_navi.js +163 -89
- package/dist/dev/jsenv_navi.js.map +18 -18
- package/dist/dev/jsenv_navi_side_effects.js +87 -78
- package/dist/dev/jsenv_navi_side_effects.js.map +4 -4
- package/dist/jsenv_navi.js +162 -88
- package/dist/jsenv_navi.js.map +18 -18
- package/dist/jsenv_navi_side_effects.js +87 -78
- package/dist/jsenv_navi_side_effects.js.map +4 -4
- package/docs/dialog_shape.md +3 -2
- package/docs/drag_interactions.md +5 -5
- package/docs/drag_to_travel.md +3 -1
- package/docs/error_handling.md +5 -3
- package/docs/i18n.md +16 -7
- package/docs/list_refresh.md +5 -4
- package/docs/network_policy.md +12 -4
- package/docs/pan_zoom.md +14 -7
- package/docs/resource.md +8 -4
- package/docs/safe_area.md +28 -24
- package/package.json +2 -2
package/docs/pan_zoom.md
CHANGED
|
@@ -47,7 +47,9 @@ the release leaves behind. A pointer pans only once it has travelled a few px
|
|
|
47
47
|
`pan` still gets its hold, and a `double_click` still gets its two presses.
|
|
48
48
|
|
|
49
49
|
Declared alone, `zoom` takes two fingers and the wheel and leaves one pointer to
|
|
50
|
-
whatever else reads it
|
|
50
|
+
whatever else reads it: nothing captures it, waits on it or swallows its click
|
|
51
|
+
until a second finger lands, so a `click` or a `longpress` declared beside `zoom`
|
|
52
|
+
answers it as it would anywhere. `pan` alone leaves the wheel to the page.
|
|
51
53
|
|
|
52
54
|
### A surface that scrolls past: `data-pan-after-hold`
|
|
53
55
|
|
|
@@ -76,6 +78,10 @@ say so. It spends the hold, though: a `longpress` declared beside a `pan` that
|
|
|
76
78
|
waits asks one finger to answer two waits, and the surface's — the shorter one
|
|
77
79
|
— is the one answered.
|
|
78
80
|
|
|
81
|
+
On a surface that only zooms there is no pan to wait for: one finger is the
|
|
82
|
+
page's to scroll, two are the surface's, and `"kept"` (below) has nothing to
|
|
83
|
+
keep.
|
|
84
|
+
|
|
79
85
|
The wait is then asked before every pan, which is right while each finger
|
|
80
86
|
landing there is genuinely ambiguous. Once the user has settled into the plan it
|
|
81
87
|
is not, and asking again is asking three times for one sentence:
|
|
@@ -152,11 +158,11 @@ place `data-pan-after-hold` is.
|
|
|
152
158
|
|
|
153
159
|
### When the surface has the hand: `grab`, `release`, `[data-grabbed]`
|
|
154
160
|
|
|
155
|
-
A surface that is asked for — by a hold,
|
|
156
|
-
has an instant where it becomes the hand's, and nothing on
|
|
157
|
-
hand then moves too early and scrolls the page instead, or
|
|
158
|
-
moment out of doubt. So the surface says it, the same two
|
|
159
|
-
says (`grab`, `release`) and the same attribute:
|
|
161
|
+
A surface that is asked for — by a hold, by the first few pixels of travel, or
|
|
162
|
+
by a second finger — has an instant where it becomes the hand's, and nothing on
|
|
163
|
+
screen says it. The hand then moves too early and scrolls the page instead, or
|
|
164
|
+
waits long past the moment out of doubt. So the surface says it, the same two
|
|
165
|
+
words a carried element says (`grab`, `release`) and the same attribute:
|
|
160
166
|
|
|
161
167
|
```jsx
|
|
162
168
|
<Box
|
|
@@ -180,7 +186,8 @@ says (`grab`, `release`) and the same attribute:
|
|
|
180
186
|
}
|
|
181
187
|
```
|
|
182
188
|
|
|
183
|
-
`[data-grabbed]` is on the element for as long as a hand is on the surface
|
|
189
|
+
`[data-grabbed]` is on the element for as long as a hand is on the surface (on
|
|
190
|
+
one that only zooms, from the second finger landing to the last one lifting), so
|
|
184
191
|
a contour, a veil or a raised shadow needs no listener — which is what this is
|
|
185
192
|
usually for. (`[data-hand-kept]` is the other one, and it outlasts the finger:
|
|
186
193
|
see [`data-pan-after-hold`](#a-surface-that-scrolls-past-data-pan-after-hold).) `grab` and `release` are for the rest: a vibration, a state kept
|
package/docs/resource.md
CHANGED
|
@@ -256,7 +256,8 @@ These are not guessable — each relationship method has its own shape.
|
|
|
256
256
|
|
|
257
257
|
### `.one(propertyName, childResource, { GET, PUT, DELETE })`
|
|
258
258
|
|
|
259
|
-
|
|
259
|
+
`GET` and `PUT` return the **parent** object with the child nested inside;
|
|
260
|
+
`DELETE` returns the parent id, or `{ id }`:
|
|
260
261
|
|
|
261
262
|
```js
|
|
262
263
|
const USER_SESSION = USER.one("session", SESSION, {
|
|
@@ -419,7 +420,8 @@ rules, verified by `src/state/rest/tests/resource_graph_parent_rerun.test.js`:
|
|
|
419
420
|
rerun) by its own `DELETE`, as a root `GET` is; a scoped `GET` is not reset —
|
|
420
421
|
its data simply resolves to nothing once the child is dropped. Override per
|
|
421
422
|
relation with `rerunOn`/`dependencies`, which every relationship method
|
|
422
|
-
accepts
|
|
423
|
+
accepts; what a relation leaves out is its parent resource's (`rerunOn` key
|
|
424
|
+
by key).
|
|
423
425
|
|
|
424
426
|
Splitting a sub-resource out of a parent `PATCH` therefore changes the refresh
|
|
425
427
|
graph: a parent field the parent's own response kept fresh is, once the relation
|
|
@@ -460,8 +462,10 @@ membership of each list is a question its own scope answers.
|
|
|
460
462
|
`withParams()` chains, merging the params —
|
|
461
463
|
`USER.withParams({ role: "admin" }).withParams({ gender: "male" })` is
|
|
462
464
|
`USER.withParams({ role: "admin", gender: "male" })`. Its second argument takes
|
|
463
|
-
`rerunOn` and `dependencies` for that scope;
|
|
464
|
-
resource's
|
|
465
|
+
`rerunOn` and `dependencies` for that scope; what it leaves out is the
|
|
466
|
+
resource's — a `rerunOn` key by key, so `{ rerunOn: { GET: ["PATCH"] } }` keeps
|
|
467
|
+
the resource's `GET_MANY` and `GET_RANGE`. Empty params throw: a scope has to be
|
|
468
|
+
about something.
|
|
465
469
|
|
|
466
470
|
It is not the tool for a param the user types. A search word bound with
|
|
467
471
|
`withParams()` would keep its results from refreshing after a write on the
|
package/docs/safe_area.md
CHANGED
|
@@ -75,13 +75,8 @@ So the app states its own screen once, and never names a component:
|
|
|
75
75
|
|
|
76
76
|
The bands fall out of it (centered), `--navi-app-width` follows, and `FixedBar`
|
|
77
77
|
pins itself to the column's edges rather than the glass. An app wanting them
|
|
78
|
-
uneven writes `--navi-app-inset-left` / `-right` directly instead
|
|
79
|
-
|
|
80
|
-
In pixels: popup placement reads this value back from CSS to compute its own
|
|
81
|
-
margins, and a custom property computes to a token stream rather than to a
|
|
82
|
-
length, so `40rem` would arrive there as the string `"40rem"`. A non-px value
|
|
83
|
-
still caps the popup's size (that part is pure CSS) but leaves its margins and
|
|
84
|
-
its placement viewport-sized, and says so in the console.
|
|
78
|
+
uneven writes `--navi-app-inset-left` / `-right` directly instead; everything
|
|
79
|
+
below follows those the same way, popup placement included.
|
|
85
80
|
|
|
86
81
|
Every popup follows: `Dialog`, `Popover`, and everything built on them
|
|
87
82
|
(`Picker`, `Select`…). It is a ceiling and nothing more — on a screen narrower
|
|
@@ -116,15 +111,19 @@ price.
|
|
|
116
111
|
|
|
117
112
|
#### Placement follows the same rectangle
|
|
118
113
|
|
|
119
|
-
|
|
114
|
+
The app's rectangle moves where a popup is placed, not only how big it may
|
|
120
115
|
get. Placement is computed against the visual viewport narrowed to the level-1
|
|
121
|
-
bands: `getAppInsets` (`src/layout/responsive.js`)
|
|
122
|
-
|
|
116
|
+
bands: `getAppInsets` (`src/layout/responsive.js`) reads `--navi-app-inset-*`
|
|
117
|
+
back off the computed style — the bands `--navi-app-max-width` centers and the
|
|
118
|
+
ones an app writes by hand alike, in any length unit — navi hands them to
|
|
119
|
+
`@jsenv/dom` once (`setPlacementViewportInsets`, wired in
|
|
123
120
|
`navi_css_vars.js`), and `pickPositionRelativeTo` reads them on every
|
|
124
|
-
placement.
|
|
125
|
-
`bottom`, `top`, which is what a dialog does nearly
|
|
126
|
-
|
|
127
|
-
|
|
121
|
+
placement. With centered bands it is invisible for anything centered on its
|
|
122
|
+
cross axis — `center`, `bottom`, `top`, which is what a dialog does nearly
|
|
123
|
+
always — and with uneven ones it is what centers that dialog on the app column
|
|
124
|
+
rather than on the window. Either way it is what puts anything anchored to an
|
|
125
|
+
edge (a `positionArea` like `bottom-start`, a `SidePanel`) flush against the
|
|
126
|
+
app column's edge rather than the window's.
|
|
128
127
|
`FixedBar` reads the same description through CSS instead: it is pinned to
|
|
129
128
|
`--navi-app-inset-*`, which says where the app's rectangle is in the window
|
|
130
129
|
rather than how wide it may be.
|
|
@@ -156,20 +155,25 @@ Beware of making that container scrollable by accident — see
|
|
|
156
155
|
`var(--navi-safe-area-inset-bottom)` in any rule. It is always declared, whether
|
|
157
156
|
or not the app ever mounts a bar.
|
|
158
157
|
|
|
159
|
-
From **JS**,
|
|
160
|
-
|
|
158
|
+
From **JS**, both levels are registered as lengths (`@property`, in
|
|
159
|
+
`safe_area.js`), so
|
|
161
160
|
`getComputedStyle(document.documentElement).getPropertyValue("--navi-safe-area-inset-bottom")`
|
|
162
|
-
gives pixels
|
|
163
|
-
`calc()` unresolved there: give a hidden box `height: var(…)` and measure it —
|
|
164
|
-
see `src/layout/demos/fixed_bar/keyboard.html`.
|
|
161
|
+
gives pixels, and so does `--navi-app-inset-*`.
|
|
165
162
|
|
|
166
163
|
### Putting something new into it
|
|
167
164
|
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
165
|
+
Level 2 has one slot per edge, `--navi-fixed-bar-space-*`, and it belongs to
|
|
166
|
+
`FixedBar`: each bar measures its own border box (notch included), and navi
|
|
167
|
+
writes the largest one on that edge inline on `<html>`
|
|
168
|
+
(`src/layout/fixed_bar/fixed_bar_space.js`). The slot is combined with
|
|
169
|
+
`env(safe-area-inset-*)` through `max()`, not added to it, since a bar measured
|
|
170
|
+
with its notch already covers the notch.
|
|
171
|
+
|
|
172
|
+
Something else taking an edge — a native banner, an OS strip — is published by
|
|
173
|
+
being drawn as a `FixedBar`; every component reading the safe area then clears
|
|
174
|
+
it without learning it exists. Writing the slot by hand holds only while no bar
|
|
175
|
+
takes that edge: the first bar mounting there replaces the value rather than
|
|
176
|
+
adding to it.
|
|
173
177
|
|
|
174
178
|
## What already reads it
|
|
175
179
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jsenv/navi",
|
|
3
|
-
"version": "0.29.
|
|
3
|
+
"version": "0.29.389",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Library of components including navigation to create frontend applications",
|
|
6
6
|
"repository": {
|
|
@@ -34,7 +34,7 @@
|
|
|
34
34
|
"preact": "^11.0.0-rc.2"
|
|
35
35
|
},
|
|
36
36
|
"dependencies": {
|
|
37
|
-
"@jsenv/dom": "0.17.
|
|
37
|
+
"@jsenv/dom": "0.17.73",
|
|
38
38
|
"@jsenv/humanize": "1.8.5",
|
|
39
39
|
"@jsenv/validity": "0.4.5"
|
|
40
40
|
},
|