@moonpay/platform-sdk-react-native 1.0.2 → 1.1.0

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.cjs CHANGED
@@ -416,7 +416,7 @@ var connectionResetSpec = {
416
416
  };
417
417
 
418
418
  // src/frame-view.tsx
419
- var import_react3 = require("react");
419
+ var import_react4 = require("react");
420
420
  var import_react_native3 = require("react-native");
421
421
 
422
422
  // src/frame-component.tsx
@@ -492,11 +492,7 @@ var WebViewTransport = class {
492
492
  if (!this.webViewRef?.current) {
493
493
  throw new Error("Cannot send message: WebView not attached");
494
494
  }
495
- const js = `
496
- window.postMessage(${JSON.stringify(JSON.stringify(message))}, '*');
497
- true;
498
- `;
499
- this.webViewRef.current.injectJavaScript(js);
495
+ this.webViewRef.current.postMessage(JSON.stringify(message));
500
496
  }
501
497
  onMessage(handler) {
502
498
  this.handlers.push(handler);
@@ -621,8 +617,7 @@ function createFrameSession(spec, ctx, props, overrides = {}) {
621
617
 
622
618
  // src/provider.tsx
623
619
  var import_platform_sdk_core3 = require("@moonpay/platform-sdk-core");
624
- var import_react2 = require("react");
625
- var import_react_native2 = require("react-native");
620
+ var import_react3 = require("react");
626
621
 
627
622
  // src/methods/add-card.ts
628
623
  var import_result = require("@moonpay/platform-protocol/result");
@@ -911,23 +906,157 @@ function createMountSession(specCtx, host) {
911
906
  };
912
907
  }
913
908
 
914
- // src/provider.tsx
909
+ // src/VisibleFrameSlotSheet.tsx
910
+ var import_react2 = require("react");
911
+ var import_react_native2 = require("react-native");
915
912
  var import_jsx_runtime2 = require("react/jsx-runtime");
916
- var MoonPayContext = (0, import_react2.createContext)(null);
913
+ function animateSheet(value, toValue, onDone) {
914
+ const animation = import_react_native2.Platform.OS === "android" ? import_react_native2.Animated.timing(value, {
915
+ toValue,
916
+ duration: 250,
917
+ easing: import_react_native2.Easing.out(import_react_native2.Easing.exp),
918
+ useNativeDriver: true
919
+ }) : import_react_native2.Animated.spring(value, {
920
+ toValue,
921
+ damping: 500,
922
+ stiffness: 1e3,
923
+ mass: 3,
924
+ overshootClamping: true,
925
+ restDisplacementThreshold: 10,
926
+ restSpeedThreshold: 10,
927
+ useNativeDriver: true
928
+ });
929
+ animation.start(onDone);
930
+ }
931
+ function VisibleFrameSlotSheet({
932
+ slot,
933
+ onClose
934
+ }) {
935
+ const { height } = (0, import_react_native2.useWindowDimensions)();
936
+ const sheetHeight = Math.round(height * 0.9);
937
+ const translateY = (0, import_react2.useRef)(new import_react_native2.Animated.Value(sheetHeight)).current;
938
+ const [frameReady, setFrameReady] = (0, import_react2.useState)(false);
939
+ const onCloseRef = (0, import_react2.useRef)(onClose);
940
+ onCloseRef.current = onClose;
941
+ const closingRef = (0, import_react2.useRef)(false);
942
+ const close = (0, import_react2.useCallback)(() => {
943
+ if (closingRef.current)
944
+ return;
945
+ closingRef.current = true;
946
+ animateSheet(translateY, sheetHeight, ({ finished }) => {
947
+ if (finished)
948
+ onCloseRef.current();
949
+ });
950
+ }, [translateY, sheetHeight]);
951
+ (0, import_react2.useEffect)(() => {
952
+ animateSheet(translateY, 0);
953
+ }, [translateY]);
954
+ (0, import_react2.useEffect)(() => {
955
+ const unsubscribe = slot.transport.onMessage((msg) => {
956
+ if (msg.kind === "ready")
957
+ setFrameReady(true);
958
+ else if (msg.kind === "complete" || msg.kind === "error")
959
+ close();
960
+ });
961
+ return unsubscribe;
962
+ }, [slot.transport, close]);
963
+ const backdropOpacity = translateY.interpolate({
964
+ inputRange: [0, sheetHeight],
965
+ outputRange: [1, 0],
966
+ extrapolate: "clamp"
967
+ });
968
+ return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native2.Modal, { visible: true, transparent: true, animationType: "none", onRequestClose: close, children: /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(import_react_native2.View, { style: styles.root, children: [
969
+ /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native2.Animated.View, { style: [styles.backdrop, { opacity: backdropOpacity }], children: /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
970
+ import_react_native2.Pressable,
971
+ {
972
+ style: import_react_native2.StyleSheet.absoluteFill,
973
+ accessibilityRole: "button",
974
+ accessibilityLabel: "Close",
975
+ onPress: close
976
+ }
977
+ ) }),
978
+ /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(import_react_native2.Animated.View, { style: [styles.sheet, { height: sheetHeight, transform: [{ translateY }] }], children: [
979
+ /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(MoonPayFrame, { transport: slot.transport }),
980
+ !frameReady && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native2.View, { style: styles.loading, children: /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native2.ActivityIndicator, { size: "large", color: "#000" }) }),
981
+ /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
982
+ import_react_native2.Pressable,
983
+ {
984
+ onPress: close,
985
+ accessibilityRole: "button",
986
+ accessibilityLabel: "Close",
987
+ hitSlop: 8,
988
+ style: styles.closeButton,
989
+ children: /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(import_react_native2.Text, { style: styles.closeButtonText, children: "\u2715" })
990
+ }
991
+ )
992
+ ] })
993
+ ] }) });
994
+ }
995
+ var styles = import_react_native2.StyleSheet.create({
996
+ root: {
997
+ flex: 1,
998
+ justifyContent: "flex-end"
999
+ },
1000
+ // Dimmed backdrop covering the whole screen; fades with the sheet position.
1001
+ backdrop: {
1002
+ ...import_react_native2.StyleSheet.absoluteFillObject,
1003
+ backgroundColor: "rgba(0, 0, 0, 0.5)"
1004
+ },
1005
+ // Bottom sheet: ~90% of the screen (height applied inline), rounded top
1006
+ // corners. The 10% gap keeps the frame clear of the status bar / notch
1007
+ // without depending on react-native-safe-area-context.
1008
+ sheet: {
1009
+ backgroundColor: "#fff",
1010
+ borderTopLeftRadius: 24,
1011
+ borderTopRightRadius: 24,
1012
+ overflow: "hidden"
1013
+ },
1014
+ // Opaque cover with a centered spinner, shown until the frame is ready.
1015
+ loading: {
1016
+ ...import_react_native2.StyleSheet.absoluteFillObject,
1017
+ backgroundColor: "#fff",
1018
+ alignItems: "center",
1019
+ justifyContent: "center"
1020
+ },
1021
+ // Floating X in the top-right corner, over the frame.
1022
+ closeButton: {
1023
+ position: "absolute",
1024
+ top: 12,
1025
+ right: 12,
1026
+ width: 32,
1027
+ height: 32,
1028
+ borderRadius: 16,
1029
+ backgroundColor: "rgba(0, 0, 0, 0.06)",
1030
+ alignItems: "center",
1031
+ justifyContent: "center",
1032
+ zIndex: 1,
1033
+ elevation: 2
1034
+ },
1035
+ closeButtonText: {
1036
+ fontSize: 17,
1037
+ lineHeight: 20,
1038
+ color: "#000",
1039
+ fontWeight: "500"
1040
+ }
1041
+ });
1042
+
1043
+ // src/provider.tsx
1044
+ var import_jsx_runtime3 = require("react/jsx-runtime");
1045
+ var MoonPayContext = (0, import_react3.createContext)(null);
917
1046
  function MoonPayProvider({
918
1047
  sessionToken,
919
1048
  apiBaseUrl,
920
1049
  frameBaseUrl,
921
1050
  children
922
1051
  }) {
923
- const [frameSlots, setFrameSlots] = (0, import_react2.useState)([]);
924
- const addSlot = (0, import_react2.useCallback)((slot) => {
1052
+ const [frameSlots, setFrameSlots] = (0, import_react3.useState)([]);
1053
+ const addSlot = (0, import_react3.useCallback)((slot) => {
925
1054
  setFrameSlots((prev) => [...prev, slot]);
926
1055
  }, []);
927
- const removeSlot = (0, import_react2.useCallback)((id) => {
1056
+ const removeSlot = (0, import_react3.useCallback)((id) => {
928
1057
  setFrameSlots((prev) => prev.filter((s) => s.id !== id));
929
1058
  }, []);
930
- const coreRef = (0, import_react2.useRef)(null);
1059
+ const coreRef = (0, import_react3.useRef)(null);
931
1060
  if (!coreRef.current) {
932
1061
  coreRef.current = (0, import_platform_sdk_core3.createClientCore)({
933
1062
  apiBaseUrl,
@@ -936,33 +1065,31 @@ function MoonPayProvider({
936
1065
  });
937
1066
  }
938
1067
  const core = coreRef.current;
939
- const client = (0, import_react2.useMemo)(() => {
1068
+ const client = (0, import_react3.useMemo)(() => {
940
1069
  const specCtx = { sessionToken, core, frameBaseUrl };
941
1070
  return createRNClient({
942
1071
  mountSession: createMountSession(specCtx, { addSlot, removeSlot }),
943
1072
  core
944
1073
  });
945
1074
  }, [sessionToken, frameBaseUrl, core, addSlot, removeSlot]);
946
- return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(MoonPayContext.Provider, { value: { client, sessionToken, core, frameBaseUrl }, children: [
1075
+ return /* @__PURE__ */ (0, import_jsx_runtime3.jsxs)(MoonPayContext.Provider, { value: { client, sessionToken, core, frameBaseUrl }, children: [
947
1076
  children,
948
- frameSlots.filter((slot) => slot.hidden).map((slot) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(MoonPayFrame, { transport: slot.transport, hidden: true }, slot.id)),
949
- frameSlots.filter((slot) => !slot.hidden).map((slot) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
950
- import_react_native2.Modal,
1077
+ frameSlots.filter((slot) => slot.hidden).map((slot) => /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(MoonPayFrame, { transport: slot.transport, hidden: true }, slot.id)),
1078
+ frameSlots.filter((slot) => !slot.hidden).map((slot) => /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
1079
+ VisibleFrameSlotSheet,
951
1080
  {
952
- visible: true,
953
- animationType: "slide",
954
- onRequestClose: () => {
1081
+ slot,
1082
+ onClose: () => {
955
1083
  slot.dispose();
956
1084
  removeSlot(slot.id);
957
- },
958
- children: /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(MoonPayFrame, { transport: slot.transport })
1085
+ }
959
1086
  },
960
1087
  slot.id
961
1088
  ))
962
1089
  ] });
963
1090
  }
964
1091
  function useMoonPayContext() {
965
- const ctx = (0, import_react2.useContext)(MoonPayContext);
1092
+ const ctx = (0, import_react3.useContext)(MoonPayContext);
966
1093
  if (!ctx) {
967
1094
  throw new Error("useMoonPay must be used within a <MoonPayProvider>");
968
1095
  }
@@ -973,7 +1100,7 @@ function useMoonPay() {
973
1100
  }
974
1101
 
975
1102
  // src/frame-view.tsx
976
- var import_jsx_runtime3 = require("react/jsx-runtime");
1103
+ var import_jsx_runtime4 = require("react/jsx-runtime");
977
1104
  function applyReactiveProps(spec, keys, props, applied, handle) {
978
1105
  for (const key of keys) {
979
1106
  const next = props[key];
@@ -991,11 +1118,11 @@ function MoonPayFrameView({
991
1118
  onEvent
992
1119
  }) {
993
1120
  const { sessionToken, core, frameBaseUrl } = useMoonPayContext();
994
- const [transport, setTransport] = (0, import_react3.useState)(null);
995
- const handleRef = (0, import_react3.useRef)(null);
996
- const onEventRef = (0, import_react3.useRef)(onEvent);
1121
+ const [transport, setTransport] = (0, import_react4.useState)(null);
1122
+ const handleRef = (0, import_react4.useRef)(null);
1123
+ const onEventRef = (0, import_react4.useRef)(onEvent);
997
1124
  onEventRef.current = onEvent;
998
- const propsRef = (0, import_react3.useRef)(props);
1125
+ const propsRef = (0, import_react4.useRef)(props);
999
1126
  propsRef.current = props;
1000
1127
  const reactiveKeys = Object.keys(spec.reactiveProps ?? {});
1001
1128
  const mountProps = {};
@@ -1006,8 +1133,8 @@ function MoonPayFrameView({
1006
1133
  }
1007
1134
  const mountKey = JSON.stringify(mountProps);
1008
1135
  const liveKey = JSON.stringify(liveProps);
1009
- const appliedRef = (0, import_react3.useRef)({});
1010
- (0, import_react3.useEffect)(() => {
1136
+ const appliedRef = (0, import_react4.useRef)({});
1137
+ (0, import_react4.useEffect)(() => {
1011
1138
  let disposed = false;
1012
1139
  let session;
1013
1140
  const applied = {};
@@ -1046,23 +1173,23 @@ function MoonPayFrameView({
1046
1173
  setTransport(null);
1047
1174
  };
1048
1175
  }, [mountKey, spec, sessionToken, core, frameBaseUrl]);
1049
- (0, import_react3.useEffect)(() => {
1176
+ (0, import_react4.useEffect)(() => {
1050
1177
  const handle = handleRef.current;
1051
1178
  if (!handle)
1052
1179
  return;
1053
1180
  applyReactiveProps(spec, reactiveKeys, propsRef.current, appliedRef.current, handle);
1054
1181
  }, [liveKey]);
1055
1182
  if (spec.hidden) {
1056
- return transport ? /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(MoonPayFrame, { transport, hidden: true }) : null;
1183
+ return transport ? /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(MoonPayFrame, { transport, hidden: true }) : null;
1057
1184
  }
1058
1185
  const resolvedStyle = { ...defaultStyle, ...style };
1059
- return /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(import_react_native3.View, { style: resolvedStyle, children: transport ? /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(MoonPayFrame, { transport }) : null });
1186
+ return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(import_react_native3.View, { style: resolvedStyle, children: transport ? /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(MoonPayFrame, { transport }) : null });
1060
1187
  }
1061
1188
 
1062
1189
  // src/components/add-card.tsx
1063
- var import_jsx_runtime4 = require("react/jsx-runtime");
1190
+ var import_jsx_runtime5 = require("react/jsx-runtime");
1064
1191
  function MoonPayAddCard({ onEvent, style }) {
1065
- return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
1192
+ return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(
1066
1193
  MoonPayFrameView,
1067
1194
  {
1068
1195
  spec: addCardSpec,
@@ -1075,13 +1202,13 @@ function MoonPayAddCard({ onEvent, style }) {
1075
1202
  }
1076
1203
 
1077
1204
  // src/components/apple-pay-button.tsx
1078
- var import_jsx_runtime5 = require("react/jsx-runtime");
1205
+ var import_jsx_runtime6 = require("react/jsx-runtime");
1079
1206
  function MoonPayApplePayButton({
1080
1207
  quote,
1081
1208
  onEvent,
1082
1209
  style
1083
1210
  }) {
1084
- return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(
1211
+ return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
1085
1212
  MoonPayFrameView,
1086
1213
  {
1087
1214
  spec: applePaySpec,
@@ -1094,9 +1221,9 @@ function MoonPayApplePayButton({
1094
1221
  }
1095
1222
 
1096
1223
  // src/components/auth.tsx
1097
- var import_jsx_runtime6 = require("react/jsx-runtime");
1224
+ var import_jsx_runtime7 = require("react/jsx-runtime");
1098
1225
  function MoonPayAuth({ onEvent, style }) {
1099
- return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
1226
+ return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
1100
1227
  MoonPayFrameView,
1101
1228
  {
1102
1229
  spec: authSpec,
@@ -1109,9 +1236,9 @@ function MoonPayAuth({ onEvent, style }) {
1109
1236
  }
1110
1237
 
1111
1238
  // src/components/buy-button.tsx
1112
- var import_jsx_runtime7 = require("react/jsx-runtime");
1239
+ var import_jsx_runtime8 = require("react/jsx-runtime");
1113
1240
  function MoonPayBuyButton({ quote, onEvent, style }) {
1114
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
1241
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1115
1242
  MoonPayFrameView,
1116
1243
  {
1117
1244
  spec: buyButtonSpec,
@@ -1124,13 +1251,13 @@ function MoonPayBuyButton({ quote, onEvent, style }) {
1124
1251
  }
1125
1252
 
1126
1253
  // src/components/buy-frame.tsx
1127
- var import_jsx_runtime8 = require("react/jsx-runtime");
1254
+ var import_jsx_runtime9 = require("react/jsx-runtime");
1128
1255
  function MoonPayBuyFrame({
1129
1256
  quote,
1130
1257
  externalTransactionId,
1131
1258
  onEvent
1132
1259
  }) {
1133
- return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1260
+ return /* @__PURE__ */ (0, import_jsx_runtime9.jsx)(
1134
1261
  MoonPayFrameView,
1135
1262
  {
1136
1263
  spec: buySpec,
@@ -1142,9 +1269,9 @@ function MoonPayBuyFrame({
1142
1269
  }
1143
1270
 
1144
1271
  // src/components/challenge.tsx
1145
- var import_jsx_runtime9 = require("react/jsx-runtime");
1272
+ var import_jsx_runtime10 = require("react/jsx-runtime");
1146
1273
  function MoonPayChallenge({ url, onEvent, style }) {
1147
- return /* @__PURE__ */ (0, import_jsx_runtime9.jsx)(
1274
+ return /* @__PURE__ */ (0, import_jsx_runtime10.jsx)(
1148
1275
  MoonPayFrameView,
1149
1276
  {
1150
1277
  spec: challengeSpec,
@@ -1157,9 +1284,9 @@ function MoonPayChallenge({ url, onEvent, style }) {
1157
1284
  }
1158
1285
 
1159
1286
  // src/components/connect.tsx
1160
- var import_jsx_runtime10 = require("react/jsx-runtime");
1287
+ var import_jsx_runtime11 = require("react/jsx-runtime");
1161
1288
  function MoonPayConnect({ theme, onEvent, style }) {
1162
- return /* @__PURE__ */ (0, import_jsx_runtime10.jsx)(
1289
+ return /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(
1163
1290
  MoonPayFrameView,
1164
1291
  {
1165
1292
  spec: connectSpec,
@@ -1172,12 +1299,12 @@ function MoonPayConnect({ theme, onEvent, style }) {
1172
1299
  }
1173
1300
 
1174
1301
  // src/components/connection-check.tsx
1175
- var import_jsx_runtime11 = require("react/jsx-runtime");
1302
+ var import_jsx_runtime12 = require("react/jsx-runtime");
1176
1303
  function MoonPayConnectionCheck({
1177
1304
  skipKyc,
1178
1305
  onEvent
1179
1306
  }) {
1180
- return /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(
1307
+ return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
1181
1308
  MoonPayFrameView,
1182
1309
  {
1183
1310
  spec: connectionCheckSpec,
@@ -1189,20 +1316,20 @@ function MoonPayConnectionCheck({
1189
1316
  }
1190
1317
 
1191
1318
  // src/components/connection-reset.tsx
1192
- var import_jsx_runtime12 = require("react/jsx-runtime");
1319
+ var import_jsx_runtime13 = require("react/jsx-runtime");
1193
1320
  function MoonPayConnectionReset({ onEvent }) {
1194
- return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(MoonPayFrameView, { spec: connectionResetSpec, props: {}, defaultStyle: {}, onEvent });
1321
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(MoonPayFrameView, { spec: connectionResetSpec, props: {}, defaultStyle: {}, onEvent });
1195
1322
  }
1196
1323
 
1197
1324
  // src/components/google-pay-button.tsx
1198
- var import_jsx_runtime13 = require("react/jsx-runtime");
1325
+ var import_jsx_runtime14 = require("react/jsx-runtime");
1199
1326
  function MoonPayGooglePayButton({
1200
1327
  quote,
1201
1328
  externalTransactionId,
1202
1329
  onEvent,
1203
1330
  style
1204
1331
  }) {
1205
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
1332
+ return /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1206
1333
  MoonPayFrameView,
1207
1334
  {
1208
1335
  spec: googlePaySpec,
@@ -1215,9 +1342,9 @@ function MoonPayGooglePayButton({
1215
1342
  }
1216
1343
 
1217
1344
  // src/components/widget.tsx
1218
- var import_jsx_runtime14 = require("react/jsx-runtime");
1345
+ var import_jsx_runtime15 = require("react/jsx-runtime");
1219
1346
  function MoonPayWidget({ quote, onEvent, style }) {
1220
- return /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1347
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1221
1348
  MoonPayFrameView,
1222
1349
  {
1223
1350
  spec: widgetSpec,