| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
Sorry, something went wrong.
…ange Core enables edge-to-edge once, in onActivityCreated, with the auto system bar style. The activity survives a dark-mode switch (uiMode is a handled configuration change), so the status and navigation bar icons keep the appearance chosen for the previous theme: dark icons over the app's dark canvas after switching to night mode. Add `refreshEdgeToEdge`, which re-applies the activity's styling with any colors or handler registered through the existing setters, and call it from the Android application when the system appearance changes.
Five defects in how androidOverflowEdge distributes window insets, all reproduced on a real Android 16 device (SM-A536E, SDK 36): - `ignore` was missing from the edge map, so a stacked value like `ignore,bottom` silently degraded to plain `bottom`. - parseEdges returned null for any value resolving to none (`none,none`), and null means "leave the view alone" - so the property became a no-op that stranded the view on whatever edges it had before. - A view switched back to `ignore` never gave back the padding it had baked in: the listener stays installed but passes insets straight through from then on, so nothing undid the earlier pass. - setPadding re-added only edgeInsets.bottom, while the inset pass had applied max(navigation bar, ime). Any setPadding while the keyboard was open collapsed the keyboard gap. - Removing one androidOverflowInset subscriber tore down the native listener for all of them, and disposeNativeView left insetListenerIsSet true, so a recycled native view never got the listener back and the event went quiet after navigating away and returning. Also drops the shortcut that returned WindowInsetsCompat.CONSUMED when a pass reported no system bars: it skipped the padding reset and never notified `dont-apply` listeners when the bars went away. parseEdges moves to its own internal module so it can be unit tested without the whole view stack, and org.nativescript.widgets.d.ts picks up OverflowEdgeIgnore, getEdgeInsets, getImeInsets and setInsetListener.
Seven pages under pages/ete, reachable from the ete/hub entry on the main
page. Each one is readable from a screenshot alone: a shared colour legend
means the ring you see around the content IS the padding the view applied,
so a wrong inset shows up as a wrong-sized band rather than a number
someone has to go looking for.
- edges walks every androidOverflowEdge value, including the stacked
`none,none` and `ignore,bottom` regressions
- nested dont-apply parent whose JS handler rewrites and consumes the
insets, with a child that pads by what survived
- ime keyboard insets, and setPadding while the keyboard is open
- lifecycle the ignore reset sequence, and whether the inset event still
fires after the native view has been recycled
- modals fullscreen vs floating modal windows
- bars statusBarStyle, bar colours, and live system theme switches
- scroll the everyday pattern: list scrolling under the navigation bar
Pages that let the probe overflow keep their controls out of the
navigation bar's reach - a bottom-pinned button there is not tappable.
The bar icon appearance is chosen from the theme when the style is applied, and the activity survives a dark mode switch, so without this the bars keep the old theme's icons until the app restarts. Confirmed on an Android 16 device before merging: a live switch to light mode left the navigation bar dark-on-light-icons, while a fresh start in light mode got it right.
Insets came from Type.systemBars() alone, which leaves the display cutout out. In portrait the two coincide and nobody notices, but rotate the device and the camera moves to an edge that has no bar - so `none`, which reads as "keep my content clear of the system UI", let content slide under it. `cutout` appends to any existing value (`none,cutout`, `top,cutout`) and folds displayCutout() into the insets being distributed. It is a modifier rather than an edge: the bit is masked off before anything asks which edges were requested, so it composes with the whole vocabulary instead of multiplying it. Whatever is consumed of the cutout is withheld from children too, so a nested view that also asked for it does not apply it twice. Left opt-in rather than made the default: folding the cutout in everywhere would silently add padding to landscape layouts that have already worked around this. Measured on an Android 16 device in landscape, where systemBars is 0,84,0,42 and the cutout is 88,0,0,0: `none` pads 0,84,0,42 and `none,cutout` pads 88,84,0,42.
…ange refreshEdgeToEdge re-styles the activity's window, but a fullscreen modal has its own dialog window styled separately when it opens. Nothing re-applied that one, so a modal open across a dark-mode switch kept the bar icons of whichever theme was active when it was shown - white icons on a light navigation bar, and the reverse switching back. The dialog fragment now watches its own configuration changes and re-applies when the night mode bit actually moves, so the cost is one comparison per configuration change rather than a restyle on every rotation. Verified on an Android 16 device with a fullscreen modal open across a switch in both directions.
…adding Adds the css env() function with the css-env-1 safe-area-inset-* and safe-area-max-inset-* variables on iOS and Android, resolvable from stylesheets, inline styles and JS/TS writes, and re-evaluated when the insets change. - SafeArea (@nativescript/core/safe-area) owns the window insets. - overflowSafeArea / overflow-safe-area hands edges to the author. - A padding that names its own edge's inset takes that edge over: the framework stops insetting it on the view, and descendants see it as consumed. - env(ns-safe-area-inset-*) and View.getRemainingSafeAreaInsets report the inset still left at a view. - safe-area-padding: padding plus the remaining inset on each edge.
|
View your CI Pipeline Execution ↗ for commit 5e8a564
💡 Verify your cache is correct by running tasks in a sandbox. Read docs ↗ ☁️ Nx Cloud last updated this comment at 2026-09-24 18:27:02 UTC |
Sorry, something went wrong.
npm i https://pkg.pr.new/@nativescript/core@11449 npm i https://pkg.pr.new/@nativescript/vite@11449 npm i https://pkg.pr.new/@nativescript/webpack@11449 commit: 5e8a564 |
Sorry, something went wrong.
|
I will say I dont think this is the right implémentation for safe area. |
Sorry, something went wrong.
|
There is a JS API you can use import { SafeArea } from '@nativescript/core';
console.log(SafeArea.insets.bottom); // e.g. 34 (dip)
SafeArea.on('insetsChanged', ({ insets }) => {
// push into a store, recompute, etc.
}); |
Sorry, something went wrong.
|
@triniwiz did not see it, missed it! |
Sorry, something went wrong.
| view._batchUpdate(() => { | ||
| for (const [p, v] of converter(value)) { | ||
| this[p.name] = v; | ||
| // Invalid at computed-value time unsets every longhand. |
There was a problem hiding this comment.
@triniwiz I'm worried with this hardcoded padding handling.
I'd rather for ShorthandProperty class not to be tied to padding or any other property like this and have a general api that "also" let us handle padding instead.
Sorry, something went wrong.
There was a problem hiding this comment.
I only added this for sugar it can be removed
Sorry, something went wrong.
| Back | FazBrowse Home | New Git URL |
PR Checklist
Stacked on #11434 (Android edge-to-edge stabilization), which this builds on. The base is that branch so the diff shows only this change; retarget to main once #11434 lands.
What is the current behavior?
env() is not understood anywhere. padding-bottom: env(safe-area-inset-bottom), the most common line of safe-area CSS on the web, reaches Length.parse and the declaration is dropped. Safe-area layout is done with iosOverflowSafeArea / iosIgnoreSafeArea on iOS, androidOverflowEdge on Android, or computed in an androidOverflowInset handler. None of these are in the cascade, and when the framework's inset and the author's padding both apply, the edge is padded twice. calc() and var() written from JS/TS (view.style.width = 'calc(50% - 10dip)') also reach the converter unevaluated.
What is the new behavior?
Implements NativeScript/rfcs#55.
env() follows css-env-1: name, indices, fallback, invalid at computed-value time, and substitution before var() so an unread fallback cannot invalidate a declaration. It works in stylesheets, inline styles, shorthands and JS/TS writes, and values re-evaluate when the insets change.
Variables:
SafeArea (@nativescript/core/safe-area) owns the window insets in dip, with an insetsChanged event. iOS reads the key window and refreshes from viewSafeAreaInsetsDidChange; Android reads the root WindowInsetsCompat (system bars and cutout, no IME) through a non-consuming listener on the decor view.
overflowSafeArea / overflow-safe-area (auto | none | all | <edge>+) is the cross-platform switch that hands edges to the author, the NativeScript form of viewport-fit=cover. auto, the default, keeps each platform's current behavior. androidOverflowEdge wins where both are set, with a trace warning.
Smart padding: a padding-* whose value names its own edge's inset takes that edge over. The framework stops insetting it on that view (iOS zeroes it in getSafeAreaInsets; Android consumes it in the LayoutBase flags without padding), and descendants see it as consumed. The footer above needs no overflow-safe-area. Only the edge's own variable counts, and a local write overrides the cascade per edge.
safe-area-padding takes the same 1 to 4 values as padding and adds the remaining inset to each edge:
Opt-in consumption tracking (SafeArea.trackConsumption, off by default) lets ns-safe-area-inset-* also use UIKit's own per-view propagation on iOS, which sees the layouts that inset without declaring it.
Verification
Behavior changes
No existing layout moves unless it opts in: env() was a dropped declaration, and overflowSafeArea defaults to auto. The one change on an existing path is that a JS/TS style write containing calc(, var( or env( is now evaluated instead of reaching the converter as raw text.