craft-native 0.0.219 → 0.0.220
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/cli.js +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.js +1 -1
- package/dist/ios/src/index.js +6 -1
- package/dist/ios/src/testing.d.ts +8 -0
- package/dist/ios/templates/CraftApp.swift +13 -6
- package/dist/ios/templates/CraftHybrid.swift +2 -0
- package/dist/ios/templates/CraftNativeScreen.swift +13 -3
- package/dist/ios/templates/testing/DriverTests.swift.template +13 -0
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -3424,7 +3424,7 @@ function pinCraftNativeDependency(packagePath, craftVersion) {
|
|
|
3424
3424
|
`);
|
|
3425
3425
|
}
|
|
3426
3426
|
// package.json
|
|
3427
|
-
var version = "0.0.
|
|
3427
|
+
var version = "0.0.220";
|
|
3428
3428
|
|
|
3429
3429
|
// bin/cli.ts
|
|
3430
3430
|
var spawnedFrom = process6.env[CRAFT_CLI_SPAWN_MARKER];
|
package/dist/index.cjs
CHANGED
package/dist/index.js
CHANGED
package/dist/ios/src/index.js
CHANGED
|
@@ -137,7 +137,12 @@ function serializeSimulatorSteps(steps) {
|
|
|
137
137
|
arg = step.state;
|
|
138
138
|
else if ("direction" in step)
|
|
139
139
|
arg = step.direction;
|
|
140
|
-
else if ("
|
|
140
|
+
else if ("fromX" in step) {
|
|
141
|
+
const coordinates = [step.fromX, step.fromY, step.toX, step.toY];
|
|
142
|
+
if (coordinates.some((value) => number(value) > 1))
|
|
143
|
+
throw new Error("drag coordinates must be between 0 and 1");
|
|
144
|
+
arg = coordinates.join(" ");
|
|
145
|
+
} else if ("x" in step) {
|
|
141
146
|
if (number(step.x) > 1 || number(step.y) > 1)
|
|
142
147
|
throw new Error("tapxy coordinates must be between 0 and 1");
|
|
143
148
|
arg = `${step.x} ${step.y}`;
|
|
@@ -27,6 +27,14 @@ export type SimulatorStep = {
|
|
|
27
27
|
command: 'swipe';
|
|
28
28
|
direction: 'up' | 'down' | 'left' | 'right';
|
|
29
29
|
}
|
|
30
|
+
/** A slow drag in app-relative coordinates, held before release to avoid a flick. */
|
|
31
|
+
| {
|
|
32
|
+
command: 'drag';
|
|
33
|
+
fromX: number;
|
|
34
|
+
fromY: number;
|
|
35
|
+
toX: number;
|
|
36
|
+
toY: number;
|
|
37
|
+
}
|
|
30
38
|
/** The system back-swipe: a drag in from the left edge (or the right). */
|
|
31
39
|
| {
|
|
32
40
|
command: 'edge';
|
|
@@ -691,12 +691,18 @@ final class CraftChrome: ObservableObject {
|
|
|
691
691
|
}
|
|
692
692
|
/// A destination beside the tab pill, outside the tab stacks and swipe order.
|
|
693
693
|
func updateTabAccessory(_ item: [String: Any]?) {
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
698
|
-
|
|
699
|
-
|
|
694
|
+
let next: Tab?
|
|
695
|
+
if let item, let path = item["path"] as? String,
|
|
696
|
+
path.hasPrefix("/"), !path.hasPrefix("//"),
|
|
697
|
+
let title = item["title"] as? String {
|
|
698
|
+
next = Tab(id: path, title: title, symbol: item["symbol"] as? String ?? "message",
|
|
699
|
+
badge: (item["badge"] as? String).flatMap { $0.isEmpty ? nil : String($0.prefix(8)) },
|
|
700
|
+
accessibilityLabel: item["accessibilityLabel"] as? String)
|
|
701
|
+
} else {
|
|
702
|
+
next = nil
|
|
703
|
+
}
|
|
704
|
+
guard tabAccessory != next else { return }
|
|
705
|
+
tabAccessory = next
|
|
700
706
|
}
|
|
701
707
|
|
|
702
708
|
func setHiddenByScreen(_ hidden: Bool) {
|
|
@@ -936,6 +942,7 @@ struct CraftTabBarView: View {
|
|
|
936
942
|
.foregroundStyle(Color.primary)
|
|
937
943
|
.frame(width: 62, height: 62)
|
|
938
944
|
}
|
|
945
|
+
.contentShape(Rectangle())
|
|
939
946
|
.overlay(alignment: .topTrailing) {
|
|
940
947
|
if let badge = accessory.badge {
|
|
941
948
|
Text(badge)
|
|
@@ -1243,6 +1243,7 @@ final class CraftHybridController: UIViewController, UINavigationControllerDeleg
|
|
|
1243
1243
|
target.view.isHidden = true
|
|
1244
1244
|
target.view.frame = self.view.bounds
|
|
1245
1245
|
current.view.frame = self.view.bounds
|
|
1246
|
+
(current.topViewController as? CraftNativeScreenController)?.screenVisibilityChanged(true)
|
|
1246
1247
|
if target.topViewController is CraftHybridWebSlot,
|
|
1247
1248
|
current.topViewController is CraftNativeScreenController {
|
|
1248
1249
|
self.parkWeb()
|
|
@@ -1272,6 +1273,7 @@ final class CraftHybridController: UIViewController, UINavigationControllerDeleg
|
|
|
1272
1273
|
recognizer.isEnabled = true
|
|
1273
1274
|
}
|
|
1274
1275
|
CraftChrome.shared.cancelTabSwipe(restoringSelection: restoringSelection)
|
|
1276
|
+
(visibleStack?.topViewController as? CraftNativeScreenController)?.screenVisibilityChanged(true)
|
|
1275
1277
|
if visibleStack?.topViewController is CraftNativeScreenController { parkWeb() }
|
|
1276
1278
|
}
|
|
1277
1279
|
|
|
@@ -4128,8 +4128,7 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
4128
4128
|
applyNavigationBarAppearance()
|
|
4129
4129
|
// Each screen says whether it wants the tab bar, so one that hid it
|
|
4130
4130
|
// never leaves it hidden for the next.
|
|
4131
|
-
|
|
4132
|
-
CraftChrome.shared.updateTabAccessory(tabAccessory)
|
|
4131
|
+
restoreShellChrome()
|
|
4133
4132
|
refreshTraitDefaults()
|
|
4134
4133
|
}
|
|
4135
4134
|
|
|
@@ -4176,13 +4175,24 @@ final class CraftNativeScreenController: UIViewController, UIScrollViewDelegate,
|
|
|
4176
4175
|
}
|
|
4177
4176
|
}
|
|
4178
4177
|
|
|
4178
|
+
private func restoreShellChrome() {
|
|
4179
|
+
guard !isAppScript else { return }
|
|
4180
|
+
CraftChrome.shared.setHiddenByScreen(tabBarHidden)
|
|
4181
|
+
CraftChrome.shared.updateTabAccessory(tabAccessory)
|
|
4182
|
+
}
|
|
4183
|
+
|
|
4179
4184
|
/// The screen came on screen or went off it: a screen pushed over it was
|
|
4180
4185
|
/// popped, or the hybrid shell switched to or away from its tab (which
|
|
4181
4186
|
/// hides a stack rather than moving it, so UIKit says nothing). The first
|
|
4182
4187
|
/// appearance is the screen's mount, not news; every later one is
|
|
4183
4188
|
/// `SCREEN_FOCUS { focused: true }`, and going away is `focused: false`.
|
|
4184
4189
|
func screenVisibilityChanged(_ visible: Bool) {
|
|
4185
|
-
guard !runtimeDisposed
|
|
4190
|
+
guard !runtimeDisposed else { return }
|
|
4191
|
+
// Hidden tab stacks receive no UIKit appearance callback. A cancelled
|
|
4192
|
+
// preview also restores a screen that never lost focus, so restore its
|
|
4193
|
+
// chrome even when no new SCREEN_FOCUS event is needed.
|
|
4194
|
+
if visible { restoreShellChrome() }
|
|
4195
|
+
guard visible != reportedVisible else { return }
|
|
4186
4196
|
reportedVisible = visible
|
|
4187
4197
|
if visible, !hasAppeared {
|
|
4188
4198
|
hasAppeared = true
|
|
@@ -37,6 +37,7 @@ import XCTest
|
|
|
37
37
|
/// tab <name> tap a tab bar button
|
|
38
38
|
/// scrollto <text> swipes up (at most 8 times) until text is hittable
|
|
39
39
|
/// swipe up|down|left|right
|
|
40
|
+
/// drag x1 y1 x2 y2 slow app-relative drag, held 0.3s before release
|
|
40
41
|
/// audit <name> accessibility audit (element descriptions, Dynamic Type, contrast); logs each issue
|
|
41
42
|
/// unlabelled logs every hittable button without a label (FAIL if any)
|
|
42
43
|
/// dismiss [label] a system prompt's button (default Not Now: "Save Password?")
|
|
@@ -367,6 +368,18 @@ final class DriverTests: XCTestCase {
|
|
|
367
368
|
case "left": app.swipeLeft()
|
|
368
369
|
default: app.swipeRight()
|
|
369
370
|
}
|
|
371
|
+
case "drag":
|
|
372
|
+
let parts = arg.split(separator: " ")
|
|
373
|
+
let coordinates = parts.compactMap { Double($0) }
|
|
374
|
+
guard parts.count == 4, coordinates.count == 4,
|
|
375
|
+
coordinates.allSatisfy({ $0.isFinite && (0...1).contains($0) }) else {
|
|
376
|
+
check(false, "drag needs four coordinates between 0 and 1")
|
|
377
|
+
return
|
|
378
|
+
}
|
|
379
|
+
let start = app.coordinate(withNormalizedOffset: CGVector(dx: CGFloat(coordinates[0]), dy: CGFloat(coordinates[1])))
|
|
380
|
+
let end = app.coordinate(withNormalizedOffset: CGVector(dx: CGFloat(coordinates[2]), dy: CGFloat(coordinates[3])))
|
|
381
|
+
start.press(forDuration: 0.05, thenDragTo: end, withVelocity: .slow, thenHoldForDuration: 0.3)
|
|
382
|
+
note("drag \(arg): ok")
|
|
370
383
|
case "edge":
|
|
371
384
|
// The system back-swipe: a drag in from the left edge (or the
|
|
372
385
|
// right one with `edge right`), which a centred swipe never is.
|