@craft-native/ios 0.0.502 → 0.0.504
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/package.json
CHANGED
|
@@ -4232,6 +4232,14 @@ private class CraftNativeFlowView: UIStackView {
|
|
|
4232
4232
|
private final class CraftNativeSafeAreaView: CraftNativeFlowView {
|
|
4233
4233
|
private var edges: Set<String> = ["top", "right", "bottom", "left"]
|
|
4234
4234
|
|
|
4235
|
+
/// The screen's leading scroll view owns the status bar's inset, and this
|
|
4236
|
+
/// view sits empty above it (trackContentScrollView). It takes no top
|
|
4237
|
+
/// inset then: taking it would make it as tall as the status bar, and the
|
|
4238
|
+
/// scroll view would no longer be the first thing on the screen.
|
|
4239
|
+
var yieldsTopInset = false {
|
|
4240
|
+
didSet { if yieldsTopInset != oldValue { updateSafeAreaPadding() } }
|
|
4241
|
+
}
|
|
4242
|
+
|
|
4235
4243
|
func setSafeAreaEdges(_ raw: Any?) {
|
|
4236
4244
|
guard let values = raw as? [Any] else {
|
|
4237
4245
|
edges = ["top", "right", "bottom", "left"]
|
|
@@ -4253,7 +4261,7 @@ private final class CraftNativeSafeAreaView: CraftNativeFlowView {
|
|
|
4253
4261
|
private func updateSafeAreaPadding() {
|
|
4254
4262
|
let insets = safeAreaInsets
|
|
4255
4263
|
safeAreaPadding = UIEdgeInsets(
|
|
4256
|
-
top: edges.contains("top") ? insets.top : 0,
|
|
4264
|
+
top: edges.contains("top") && !yieldsTopInset ? insets.top : 0,
|
|
4257
4265
|
left: edges.contains("left") ? insets.left : 0,
|
|
4258
4266
|
bottom: edges.contains("bottom") ? insets.bottom : 0,
|
|
4259
4267
|
right: edges.contains("right") ? insets.right : 0
|
|
@@ -8425,6 +8433,8 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
8425
8433
|
return titleFromOptions || prefersLargeTitle == true || !(navigationItem.rightBarButtonItems ?? []).isEmpty
|
|
8426
8434
|
}
|
|
8427
8435
|
private weak var trackedScrollView: UIScrollView?
|
|
8436
|
+
/// Empty SafeAreaViews above the leading scroll view, which owns their top inset.
|
|
8437
|
+
private let yieldedSafeAreas = NSHashTable<CraftNativeSafeAreaView>.weakObjects()
|
|
8428
8438
|
|
|
8429
8439
|
/// `craft.navigation.setOptions`: this screen's bar. Every key is
|
|
8430
8440
|
/// optional and only the keys given change.
|
|
@@ -8839,17 +8849,39 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
8839
8849
|
}
|
|
8840
8850
|
/// The scroll view the screen starts with, when nothing sits above it:
|
|
8841
8851
|
/// the root's first child, its first, and so on, none padded on top.
|
|
8852
|
+
/// Empty siblings above it do not count. An empty SafeAreaView among
|
|
8853
|
+
/// them is remembered: once the root runs under the status bar it
|
|
8854
|
+
/// would take that inset and stop being empty, the scroll view would
|
|
8855
|
+
/// stop leading, the root would return inside the safe area and the
|
|
8856
|
+
/// view would be empty again. A screen with an empty header above its
|
|
8857
|
+
/// scroll view flipped between the two layouts and stopped in either.
|
|
8858
|
+
var emptySafeAreasAbove: [CraftNativeSafeAreaView] = []
|
|
8842
8859
|
func leading(_ node: RenderedNode) -> RenderedNode? {
|
|
8843
8860
|
if let scroll = node.view as? CraftNativeScrollView { return scroll.isVertical && scroll.isScrollEnabled ? node : nil }
|
|
8844
8861
|
if let list = node.view as? CraftNativeFlatList {
|
|
8845
8862
|
return list.isScrollEnabled && (list.collectionViewLayout as? UICollectionViewFlowLayout)?.scrollDirection != .horizontal ? node : nil
|
|
8846
8863
|
}
|
|
8847
8864
|
guard paddingInsets(node.style).top == 0,
|
|
8848
|
-
let
|
|
8849
|
-
|
|
8865
|
+
let index = node.children.firstIndex(where: { $0.type != "Modal" && !$0.view.isHidden && $0.view.bounds.height > 0 }) else { return nil }
|
|
8866
|
+
for skipped in node.children[..<index] where skipped.type != "Modal" && !skipped.view.isHidden {
|
|
8867
|
+
if let safeArea = skipped.view as? CraftNativeSafeAreaView { emptySafeAreasAbove.append(safeArea) }
|
|
8868
|
+
}
|
|
8869
|
+
return leading(node.children[index])
|
|
8850
8870
|
}
|
|
8851
8871
|
let scroll = find(renderedRoot)
|
|
8852
8872
|
let leadingScroll = leading(renderedRoot)
|
|
8873
|
+
// The leading scroll view owns the top inset; the empty SafeAreaViews
|
|
8874
|
+
// it passed give theirs up, and get it back when it no longer leads
|
|
8875
|
+
// (the header gained content, or the scroll view left the screen).
|
|
8876
|
+
let yielding = leadingScroll == nil ? [] : emptySafeAreasAbove
|
|
8877
|
+
for view in yieldedSafeAreas.allObjects where !yielding.contains(where: { $0 === view }) {
|
|
8878
|
+
view.yieldsTopInset = false
|
|
8879
|
+
yieldedSafeAreas.remove(view)
|
|
8880
|
+
}
|
|
8881
|
+
for view in yielding where !view.yieldsTopInset {
|
|
8882
|
+
view.yieldsTopInset = true
|
|
8883
|
+
yieldedSafeAreas.add(view)
|
|
8884
|
+
}
|
|
8853
8885
|
// The leading scroller may overflow beneath navigation chrome.
|
|
8854
8886
|
// A bounded list inside a form must clip its rows to its viewport.
|
|
8855
8887
|
if let leadingScroll, leadingScroll.style["overflow"] as? String != "hidden" {
|
|
@@ -11632,10 +11664,14 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
11632
11664
|
if let spacing = styleNumber(style["letterSpacing"]) { attributes[.kern] = spacing }
|
|
11633
11665
|
addTextDecorationAttributes(style, to: &attributes)
|
|
11634
11666
|
if let shadow = textShadow(style) { attributes[.shadow] = shadow }
|
|
11667
|
+
// A CSS line box may be shorter than its font while glyphs paint outside
|
|
11668
|
+
// it. UIKit clips that same paragraph inside a UILabel. Preserve the
|
|
11669
|
+
// resolved font metrics for layout and drawing, including custom faces
|
|
11670
|
+
// whose ascenders exceed their point size and Dynamic Type scaling.
|
|
11635
11671
|
if let lineHeight = styleNumber(style["lineHeight"]) {
|
|
11636
11672
|
let paragraph = NSMutableParagraphStyle()
|
|
11637
|
-
paragraph.minimumLineHeight = lineHeight
|
|
11638
|
-
paragraph.maximumLineHeight = lineHeight
|
|
11673
|
+
paragraph.minimumLineHeight = max(lineHeight, label.font.lineHeight)
|
|
11674
|
+
paragraph.maximumLineHeight = max(lineHeight, label.font.lineHeight)
|
|
11639
11675
|
paragraph.alignment = label.textAlignment
|
|
11640
11676
|
attributes[.paragraphStyle] = paragraph
|
|
11641
11677
|
}
|
|
@@ -11689,8 +11725,8 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
11689
11725
|
if let spacing = styleNumber(style["letterSpacing"]) { attributes[.kern] = spacing }
|
|
11690
11726
|
if let lineHeight = styleNumber(style["lineHeight"]) {
|
|
11691
11727
|
let paragraph = NSMutableParagraphStyle()
|
|
11692
|
-
paragraph.minimumLineHeight = lineHeight
|
|
11693
|
-
paragraph.maximumLineHeight = lineHeight
|
|
11728
|
+
paragraph.minimumLineHeight = max(lineHeight, font.lineHeight)
|
|
11729
|
+
paragraph.maximumLineHeight = max(lineHeight, font.lineHeight)
|
|
11694
11730
|
attributes[.paragraphStyle] = paragraph
|
|
11695
11731
|
}
|
|
11696
11732
|
addTextDecorationAttributes(style, to: &attributes)
|
|
@@ -11717,8 +11753,8 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
11717
11753
|
// then paints a second line outside the field instead of scrolling.
|
|
11718
11754
|
if singleLine { paragraph.lineBreakMode = .byClipping }
|
|
11719
11755
|
if let lineHeight = styleNumber(style["lineHeight"]) {
|
|
11720
|
-
paragraph.minimumLineHeight = lineHeight
|
|
11721
|
-
paragraph.maximumLineHeight = lineHeight
|
|
11756
|
+
paragraph.minimumLineHeight = max(lineHeight, font.lineHeight)
|
|
11757
|
+
paragraph.maximumLineHeight = max(lineHeight, font.lineHeight)
|
|
11722
11758
|
}
|
|
11723
11759
|
attributes[.paragraphStyle] = paragraph
|
|
11724
11760
|
addTextDecorationAttributes(style, to: &attributes)
|