@cloudparse/up-miniapps-sdk 0.6.6 → 0.6.8
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/index.browser.min.js +38 -38
- package/dist/index.browser.min.js.map +1 -1
- package/dist/index.cjs +196 -117
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +260 -181
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -267,11 +267,61 @@ var Bridge = class {
|
|
|
267
267
|
}
|
|
268
268
|
}
|
|
269
269
|
/**
|
|
270
|
-
* Internal handler for mock message processing, overrideable in test environments
|
|
270
|
+
* Internal handler for mock message processing, overrideable in test environments.
|
|
271
|
+
*
|
|
272
|
+
* Every mini-app that calls a bridge method also has to run standalone in a plain
|
|
273
|
+
* browser (dev, and this vault's own Chrome-based verification) with no native shell
|
|
274
|
+
* attached — `isNative()` is false, so `send()` never round-trips through the real
|
|
275
|
+
* host at all. Before this switch existed, EVERY unhandled type here resolved with
|
|
276
|
+
* plain `undefined` (see the `default` branch below), which silently broke any caller
|
|
277
|
+
* checking a result shape like `{success: boolean}` — `undefined?.success` reads as
|
|
278
|
+
* `false`, not "no answer", so e.g. `sdk.media.saveImage()` looked like a real
|
|
279
|
+
* permission-denied rejection in the browser instead of "there's no native shell
|
|
280
|
+
* here to ask." Add a `case` here — instead of leaving every mini-app to
|
|
281
|
+
* individually special-case "what happens when I call this with no shell attached" —
|
|
282
|
+
* whenever a bridge method's mock behavior should be more than a no-op.
|
|
271
283
|
*/
|
|
272
284
|
handleMockMessage(type, payload) {
|
|
273
|
-
|
|
274
|
-
|
|
285
|
+
switch (type) {
|
|
286
|
+
case "SAVE_IMAGE":
|
|
287
|
+
return this.mockSaveImage(
|
|
288
|
+
payload
|
|
289
|
+
);
|
|
290
|
+
default:
|
|
291
|
+
console.warn(
|
|
292
|
+
`[Bridge] Mock mode active: Unhandled message type ${type}`
|
|
293
|
+
);
|
|
294
|
+
return Promise.resolve();
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
/**
|
|
298
|
+
* Standalone-browser stand-in for the native `SAVE_IMAGE` handler: triggers a real
|
|
299
|
+
* browser download (an `<a download>` click) instead of writing to a device photo
|
|
300
|
+
* library, which doesn't exist here. Resolves `{success: true}` on a real trigger so
|
|
301
|
+
* every mini-app's own `result?.success` check gets the same shape/semantics as the
|
|
302
|
+
* real native response — no per-app "am I in mock mode" branching needed. Consumers
|
|
303
|
+
* can still keep their own `catch` fallback for the genuinely different case of a
|
|
304
|
+
* native shell that's missing its WebView bridge (see `sendOnce`'s own rejection
|
|
305
|
+
* path) — that's a real native edge case, not mocking, and this method never runs
|
|
306
|
+
* for it (`send()` only reaches `handleMockMessage` when `!isNative()`).
|
|
307
|
+
*/
|
|
308
|
+
mockSaveImage(payload) {
|
|
309
|
+
if (typeof document === "undefined") {
|
|
310
|
+
return Promise.resolve({ success: false });
|
|
311
|
+
}
|
|
312
|
+
try {
|
|
313
|
+
const href = payload.base64.startsWith("data:") ? payload.base64 : `data:image/png;base64,${payload.base64}`;
|
|
314
|
+
const link = document.createElement("a");
|
|
315
|
+
link.href = href;
|
|
316
|
+
link.download = payload.filename ? `${payload.filename}.png` : "image.png";
|
|
317
|
+
document.body.appendChild(link);
|
|
318
|
+
link.click();
|
|
319
|
+
link.remove();
|
|
320
|
+
return Promise.resolve({ success: true });
|
|
321
|
+
} catch (err) {
|
|
322
|
+
console.warn("[Bridge] Mock SAVE_IMAGE download failed:", err);
|
|
323
|
+
return Promise.resolve({ success: false });
|
|
324
|
+
}
|
|
275
325
|
}
|
|
276
326
|
sendOnce(type, payload, timeoutMs) {
|
|
277
327
|
return new Promise((resolve, reject) => {
|
|
@@ -735,7 +785,7 @@ var MapDrawer = (0, import_react2.forwardRef)(
|
|
|
735
785
|
const dragDelta = touchEndY - dragStartY;
|
|
736
786
|
const drawerHeightFromBottom = dragBaseHeightPxRef.current - dragDelta;
|
|
737
787
|
const distToClosed = Math.abs(drawerHeightFromBottom - closedPx);
|
|
738
|
-
let
|
|
788
|
+
let targetState2;
|
|
739
789
|
if (currentState === "auto") {
|
|
740
790
|
const autoMaxPx2 = resolveHeightToPixels(
|
|
741
791
|
drawerAutoMaxHeight || "100%",
|
|
@@ -743,22 +793,22 @@ var MapDrawer = (0, import_react2.forwardRef)(
|
|
|
743
793
|
);
|
|
744
794
|
const autoPx2 = Math.min(autoMaxPx2, autoContentPx);
|
|
745
795
|
const distToAuto = Math.abs(drawerHeightFromBottom - autoPx2);
|
|
746
|
-
|
|
796
|
+
targetState2 = distToAuto <= distToClosed ? "auto" : "closed";
|
|
747
797
|
} else {
|
|
748
798
|
const distToFull = Math.abs(drawerHeightFromBottom - fullPx2);
|
|
749
799
|
const distToPeek = Math.abs(drawerHeightFromBottom - peekPx2);
|
|
750
800
|
const minDist = Math.min(distToFull, distToPeek, distToClosed);
|
|
751
801
|
if (minDist === distToFull) {
|
|
752
|
-
|
|
802
|
+
targetState2 = "full";
|
|
753
803
|
} else if (minDist === distToPeek) {
|
|
754
|
-
|
|
804
|
+
targetState2 = "peek";
|
|
755
805
|
} else {
|
|
756
|
-
|
|
806
|
+
targetState2 = "closed";
|
|
757
807
|
}
|
|
758
808
|
}
|
|
759
809
|
setTouchStartY(null);
|
|
760
810
|
setCurrentTouchY(null);
|
|
761
|
-
onChangeState(
|
|
811
|
+
onChangeState(targetState2);
|
|
762
812
|
requestAnimationFrame(() => {
|
|
763
813
|
if (parentContainer) {
|
|
764
814
|
parentContainer.style.setProperty("--drag-offset", "0px");
|
|
@@ -2035,115 +2085,142 @@ var GlobalEvent = /* @__PURE__ */ ((GlobalEvent2) => {
|
|
|
2035
2085
|
// src/components/Map/hooks/useUserLocation.ts
|
|
2036
2086
|
var import_react6 = require("react");
|
|
2037
2087
|
var LERP_FACTOR = 0.12;
|
|
2038
|
-
var
|
|
2039
|
-
|
|
2040
|
-
|
|
2041
|
-
|
|
2042
|
-
|
|
2043
|
-
|
|
2044
|
-
const
|
|
2045
|
-
|
|
2046
|
-
|
|
2047
|
-
|
|
2048
|
-
|
|
2049
|
-
|
|
2050
|
-
|
|
2051
|
-
|
|
2052
|
-
|
|
2053
|
-
|
|
2054
|
-
|
|
2055
|
-
|
|
2056
|
-
|
|
2057
|
-
|
|
2058
|
-
|
|
2059
|
-
|
|
2060
|
-
|
|
2061
|
-
|
|
2062
|
-
|
|
2063
|
-
|
|
2064
|
-
|
|
2065
|
-
|
|
2066
|
-
|
|
2067
|
-
|
|
2068
|
-
|
|
2069
|
-
|
|
2070
|
-
|
|
2071
|
-
|
|
2072
|
-
|
|
2073
|
-
|
|
2074
|
-
|
|
2075
|
-
|
|
2076
|
-
|
|
2077
|
-
|
|
2078
|
-
|
|
2079
|
-
|
|
2080
|
-
|
|
2081
|
-
|
|
2082
|
-
|
|
2083
|
-
|
|
2084
|
-
|
|
2085
|
-
|
|
2086
|
-
|
|
2087
|
-
|
|
2088
|
-
|
|
2089
|
-
|
|
2090
|
-
|
|
2091
|
-
if (
|
|
2092
|
-
|
|
2093
|
-
|
|
2094
|
-
changed = true;
|
|
2095
|
-
} else {
|
|
2096
|
-
const target = targetRef.current.heading;
|
|
2097
|
-
const current = currentRef.current.heading;
|
|
2098
|
-
let delta = target - current;
|
|
2099
|
-
if (delta > 180) delta -= 360;
|
|
2100
|
-
if (delta < -180) delta += 360;
|
|
2101
|
-
const nHeading = current + delta * LERP_FACTOR;
|
|
2102
|
-
const normalized = (nHeading % 360 + 360) % 360;
|
|
2103
|
-
if (Math.abs(delta) > 0.1) {
|
|
2104
|
-
currentRef.current.heading = normalized;
|
|
2105
|
-
changed = true;
|
|
2106
|
-
}
|
|
2107
|
-
}
|
|
2108
|
-
}
|
|
2109
|
-
if (changed) {
|
|
2110
|
-
setLocationState({
|
|
2111
|
-
accuracy: targetRef.current.accuracy,
|
|
2112
|
-
coords: currentRef.current.coords ? [...currentRef.current.coords] : null,
|
|
2113
|
-
heading: currentRef.current.heading
|
|
2114
|
-
});
|
|
2115
|
-
}
|
|
2116
|
-
rafId = requestAnimationFrame(animate);
|
|
2117
|
-
};
|
|
2118
|
-
rafId = requestAnimationFrame(animate);
|
|
2119
|
-
sdk.location.getCurrentPosition().then((data) => {
|
|
2120
|
-
const payload = mapPayload(data);
|
|
2121
|
-
targetRef.current = payload;
|
|
2122
|
-
}).catch((e) => console.warn("Initial location fetch failed", e));
|
|
2123
|
-
const unsubscribeStream = sdk.on(
|
|
2124
|
-
"LOCATION_STREAM_UPDATE" /* LOCATION_STREAM_UPDATE */,
|
|
2125
|
-
(payload) => {
|
|
2126
|
-
targetRef.current = mapPayload(payload);
|
|
2088
|
+
var EMPTY_STATE = {
|
|
2089
|
+
accuracy: null,
|
|
2090
|
+
coords: null,
|
|
2091
|
+
heading: null
|
|
2092
|
+
};
|
|
2093
|
+
function mapPayload(payload) {
|
|
2094
|
+
const coords = payload.location?.coords || payload.coords;
|
|
2095
|
+
const headingData = payload.heading;
|
|
2096
|
+
const newCoords = coords ? [coords.longitude, coords.latitude] : null;
|
|
2097
|
+
let heading = null;
|
|
2098
|
+
if (headingData?.trueHeading !== void 0 && headingData.trueHeading >= 0) {
|
|
2099
|
+
heading = headingData.trueHeading;
|
|
2100
|
+
} else if (headingData?.magneticHeading !== void 0 && headingData.magneticHeading >= 0) {
|
|
2101
|
+
heading = headingData.magneticHeading;
|
|
2102
|
+
} else if (headingData?.heading !== null && headingData?.heading >= 0) {
|
|
2103
|
+
heading = headingData.heading;
|
|
2104
|
+
}
|
|
2105
|
+
return {
|
|
2106
|
+
accuracy: coords?.accuracy || null,
|
|
2107
|
+
coords: newCoords,
|
|
2108
|
+
heading
|
|
2109
|
+
};
|
|
2110
|
+
}
|
|
2111
|
+
var refCount = 0;
|
|
2112
|
+
var generation = 0;
|
|
2113
|
+
var subscribers = /* @__PURE__ */ new Set();
|
|
2114
|
+
var targetState = { ...EMPTY_STATE };
|
|
2115
|
+
var currentInterpolated = { coords: null, heading: null };
|
|
2116
|
+
var rafId = null;
|
|
2117
|
+
var unsubscribeStream = null;
|
|
2118
|
+
var unsubscribeLegacy = null;
|
|
2119
|
+
function getSnapshot() {
|
|
2120
|
+
return {
|
|
2121
|
+
accuracy: targetState.accuracy,
|
|
2122
|
+
coords: currentInterpolated.coords ? [...currentInterpolated.coords] : null,
|
|
2123
|
+
heading: currentInterpolated.heading
|
|
2124
|
+
};
|
|
2125
|
+
}
|
|
2126
|
+
function notify() {
|
|
2127
|
+
const snapshot = getSnapshot();
|
|
2128
|
+
for (const callback of subscribers) callback(snapshot);
|
|
2129
|
+
}
|
|
2130
|
+
function animate() {
|
|
2131
|
+
let changed = false;
|
|
2132
|
+
if (targetState.coords) {
|
|
2133
|
+
if (!currentInterpolated.coords) {
|
|
2134
|
+
currentInterpolated.coords = [...targetState.coords];
|
|
2135
|
+
changed = true;
|
|
2136
|
+
} else {
|
|
2137
|
+
const [tLng, tLat] = targetState.coords;
|
|
2138
|
+
const [cLng, cLat] = currentInterpolated.coords;
|
|
2139
|
+
const nLng = cLng + (tLng - cLng) * LERP_FACTOR;
|
|
2140
|
+
const nLat = cLat + (tLat - cLat) * LERP_FACTOR;
|
|
2141
|
+
if (Math.abs(nLng - cLng) > 1e-7 || Math.abs(nLat - cLat) > 1e-7) {
|
|
2142
|
+
currentInterpolated.coords = [nLng, nLat];
|
|
2143
|
+
changed = true;
|
|
2127
2144
|
}
|
|
2128
|
-
|
|
2129
|
-
|
|
2130
|
-
|
|
2131
|
-
|
|
2132
|
-
|
|
2145
|
+
}
|
|
2146
|
+
}
|
|
2147
|
+
if (targetState.heading !== null) {
|
|
2148
|
+
if (currentInterpolated.heading === null) {
|
|
2149
|
+
currentInterpolated.heading = targetState.heading;
|
|
2150
|
+
changed = true;
|
|
2151
|
+
} else {
|
|
2152
|
+
const target = targetState.heading;
|
|
2153
|
+
const current = currentInterpolated.heading;
|
|
2154
|
+
let delta = target - current;
|
|
2155
|
+
if (delta > 180) delta -= 360;
|
|
2156
|
+
if (delta < -180) delta += 360;
|
|
2157
|
+
const nHeading = current + delta * LERP_FACTOR;
|
|
2158
|
+
const normalized = (nHeading % 360 + 360) % 360;
|
|
2159
|
+
if (Math.abs(delta) > 0.1) {
|
|
2160
|
+
currentInterpolated.heading = normalized;
|
|
2161
|
+
changed = true;
|
|
2133
2162
|
}
|
|
2134
|
-
|
|
2135
|
-
|
|
2136
|
-
|
|
2137
|
-
|
|
2138
|
-
|
|
2163
|
+
}
|
|
2164
|
+
}
|
|
2165
|
+
if (changed) notify();
|
|
2166
|
+
rafId = requestAnimationFrame(animate);
|
|
2167
|
+
}
|
|
2168
|
+
function startSharedStream() {
|
|
2169
|
+
rafId = requestAnimationFrame(animate);
|
|
2170
|
+
generation++;
|
|
2171
|
+
const thisGeneration = generation;
|
|
2172
|
+
sdk.location.getCurrentPosition().then((data) => {
|
|
2173
|
+
if (thisGeneration !== generation) return;
|
|
2174
|
+
targetState = mapPayload(data);
|
|
2175
|
+
}).catch((e) => console.warn("Initial location fetch failed", e));
|
|
2176
|
+
unsubscribeStream = sdk.on(
|
|
2177
|
+
"LOCATION_STREAM_UPDATE" /* LOCATION_STREAM_UPDATE */,
|
|
2178
|
+
(payload) => {
|
|
2179
|
+
targetState = mapPayload(payload);
|
|
2180
|
+
}
|
|
2181
|
+
);
|
|
2182
|
+
unsubscribeLegacy = sdk.on(
|
|
2183
|
+
"LOCATION_UPDATE" /* LOCATION_UPDATE */,
|
|
2184
|
+
(payload) => {
|
|
2185
|
+
targetState = mapPayload(payload);
|
|
2186
|
+
}
|
|
2187
|
+
);
|
|
2188
|
+
sdk.location.startStream({
|
|
2189
|
+
distanceFilter: 1,
|
|
2190
|
+
headingThreshold: 2
|
|
2191
|
+
}).catch((e) => console.warn("Failed to start location stream", e));
|
|
2192
|
+
}
|
|
2193
|
+
function stopSharedStream() {
|
|
2194
|
+
generation++;
|
|
2195
|
+
if (rafId !== null) cancelAnimationFrame(rafId);
|
|
2196
|
+
rafId = null;
|
|
2197
|
+
unsubscribeStream?.();
|
|
2198
|
+
unsubscribeLegacy?.();
|
|
2199
|
+
unsubscribeStream = null;
|
|
2200
|
+
unsubscribeLegacy = null;
|
|
2201
|
+
sdk.location.stopStream().catch(() => {
|
|
2202
|
+
});
|
|
2203
|
+
targetState = { ...EMPTY_STATE };
|
|
2204
|
+
currentInterpolated = { coords: null, heading: null };
|
|
2205
|
+
}
|
|
2206
|
+
var useUserLocation = () => {
|
|
2207
|
+
const [locationState, setLocationState] = (0, import_react6.useState)(getSnapshot);
|
|
2208
|
+
(0, import_react6.useEffect)(() => {
|
|
2209
|
+
refCount++;
|
|
2210
|
+
if (refCount === 1) {
|
|
2211
|
+
startSharedStream();
|
|
2212
|
+
} else {
|
|
2213
|
+
setLocationState(getSnapshot());
|
|
2214
|
+
}
|
|
2215
|
+
subscribers.add(setLocationState);
|
|
2139
2216
|
return () => {
|
|
2140
|
-
|
|
2141
|
-
|
|
2142
|
-
|
|
2143
|
-
|
|
2144
|
-
}
|
|
2217
|
+
subscribers.delete(setLocationState);
|
|
2218
|
+
refCount--;
|
|
2219
|
+
if (refCount === 0) {
|
|
2220
|
+
stopSharedStream();
|
|
2221
|
+
}
|
|
2145
2222
|
};
|
|
2146
|
-
}, [
|
|
2223
|
+
}, []);
|
|
2147
2224
|
return locationState;
|
|
2148
2225
|
};
|
|
2149
2226
|
|
|
@@ -3715,7 +3792,7 @@ var RoutingService = {
|
|
|
3715
3792
|
};
|
|
3716
3793
|
|
|
3717
3794
|
// package.json
|
|
3718
|
-
var version = "0.6.
|
|
3795
|
+
var version = "0.6.8";
|
|
3719
3796
|
|
|
3720
3797
|
// src/sdk.ts
|
|
3721
3798
|
function deepFreeze(obj) {
|
|
@@ -4126,7 +4203,6 @@ var import_react14 = require("react");
|
|
|
4126
4203
|
var import_jsx_runtime16 = require("react/jsx-runtime");
|
|
4127
4204
|
var AVATAR_MOUTH_VARIANTS = [
|
|
4128
4205
|
"variant03",
|
|
4129
|
-
"variant06",
|
|
4130
4206
|
"variant07",
|
|
4131
4207
|
"variant08",
|
|
4132
4208
|
"variant09",
|
|
@@ -4870,7 +4946,10 @@ var RESISTANCE = 0.5;
|
|
|
4870
4946
|
var DRAG_DEADZONE = 8;
|
|
4871
4947
|
var FLING_FRICTION = 0.95;
|
|
4872
4948
|
var FLING_MIN_VELOCITY = 0.02;
|
|
4873
|
-
function DefaultIndicator({
|
|
4949
|
+
function DefaultIndicator({
|
|
4950
|
+
progress,
|
|
4951
|
+
isRefreshing
|
|
4952
|
+
}) {
|
|
4874
4953
|
return /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
|
|
4875
4954
|
"div",
|
|
4876
4955
|
{
|