@turnkey/react-wallet-kit
Version:
The easiest and most powerful way to integrate Turnkey's Embedded Wallets into your React applications.
252 lines (249 loc) • 11.3 kB
JavaScript
import { slicedToArray as _slicedToArray, asyncToGenerator as _asyncToGenerator, regenerator as _regenerator } from '../../../_virtual/_rollupPluginBabelHelpers.mjs';
import { jsx, jsxs } from 'react/jsx-runtime';
import { ActionButton } from '../../design/Buttons.mjs';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import { faQrcode, faArrowUpRightFromSquare } from '@fortawesome/free-solid-svg-icons';
import { useRef, useState, useEffect } from 'react';
import clsx from 'clsx';
import { SuccessPage } from '../../design/Success.mjs';
import { useModal } from '../../../providers/modal/Hook.mjs';
import { useTurnkey } from '../../../providers/client/Hook.mjs';
import { findWalletConnectProvider, useDebouncedCallback } from '../../../utils/utils.mjs';
import { ActionPage } from '../Action.mjs';
function MobileWalletConnectScreen(props) {
var _targetApp$info$name, _targetApp$info$name2;
var targetApp = props.provider,
onConnect = props.onConnect,
onSign = props.onSign,
onSelectQRCode = props.onSelectQRCode,
successPageDuration = props.successPageDuration;
var _useModal = useModal(),
pushPage = _useModal.pushPage,
popPages = _useModal.popPages,
closeModal = _useModal.closeModal,
isMobile = _useModal.isMobile;
var _useTurnkey = useTurnkey(),
walletProviders = _useTurnkey.walletProviders;
var latestProviderRef = useRef(null);
var _useState = useState(false),
_useState2 = _slicedToArray(_useState, 2),
isConnecting = _useState2[0],
setIsConnecting = _useState2[1];
var _useState3 = useState(false),
_useState4 = _slicedToArray(_useState3, 2),
canSign = _useState4[0],
setCanSign = _useState4[1];
var _useState5 = useState(false),
_useState6 = _slicedToArray(_useState5, 2),
completed = _useState6[0],
setCompleted = _useState6[1];
var _useState7 = useState(isMobile),
_useState8 = _slicedToArray(_useState7, 2),
shouldStartConnecting = _useState8[0],
setShouldStartConnecting = _useState8[1];
// Find the current WalletConnect provider state
var walletConnectProvider = findWalletConnectProvider(walletProviders, targetApp.chainInfo.namespace);
// if provider is not found then that means that the user entered this screen
// while WalletConnect was still initializing, and then it failed to initialize
useEffect(function () {
if (!walletConnectProvider) {
// we have to go back two pages here since thats the screen
// we get wallet providers from state
popPages(2);
}
}, [walletConnectProvider, popPages]);
// Initial connection effect
useEffect(function () {
if (!shouldStartConnecting) return;
if (walletConnectProvider) {
latestProviderRef.current = walletConnectProvider;
// we don't try to connect if WalletConnect is still initializing or we are already connecting
if (!isConnecting && !walletConnectProvider.isLoading) {
if (walletConnectProvider.connectedAddresses.length > 0) {
// Connection already established. Try to connect if possible
if (onSign) {
setCanSign(true);
} else {
setCompleted(true);
}
} else {
var _latestProviderRef$cu, _latestProviderRef$cu2;
// Start connection flow
setCanSign(false);
handleOpenApp("wc?uri=".concat(encodeURIComponent((_latestProviderRef$cu = latestProviderRef === null || latestProviderRef === void 0 ? void 0 : (_latestProviderRef$cu2 = latestProviderRef.current) === null || _latestProviderRef$cu2 === void 0 ? void 0 : _latestProviderRef$cu2.uri) !== null && _latestProviderRef$cu !== void 0 ? _latestProviderRef$cu : "")));
runConnectAction(walletConnectProvider);
}
}
}
}, [walletConnectProvider, shouldStartConnecting]);
// Handle the connection action - uses the ref to get latest provider
var runConnectAction = useDebouncedCallback(/*#__PURE__*/function () {
var _ref = _asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee(targetProvider) {
return _regenerator().w(function (_context) {
while (1) switch (_context.p = _context.n) {
case 0:
setIsConnecting(true);
_context.p = 1;
_context.n = 2;
return onConnect(targetProvider);
case 2:
if (onSign) {
setCanSign(true);
} else {
// Skip signing step if no signature is required (Connect only, not signup/login)
setCompleted(true);
}
_context.n = 4;
break;
case 3:
_context.p = 3;
_context.v;
case 4:
_context.p = 4;
setIsConnecting(false);
return _context.f(4);
case 5:
return _context.a(2);
}
}, _callee, null, [[1, 3, 4, 5]]);
}));
return function (_x) {
return _ref.apply(this, arguments);
};
}(), 100);
// Handle the sign action - uses the ref to get latest provider
var runSignAction = useDebouncedCallback(/*#__PURE__*/function () {
var _ref2 = _asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee2(targetProvider) {
return _regenerator().w(function (_context2) {
while (1) switch (_context2.p = _context2.n) {
case 0:
setIsConnecting(true);
_context2.p = 1;
_context2.n = 2;
return onSign(targetProvider);
case 2:
setCompleted(true);
_context2.n = 4;
break;
case 3:
_context2.p = 3;
_context2.v;
case 4:
_context2.p = 4;
setIsConnecting(false);
return _context2.f(4);
case 5:
return _context2.a(2);
}
}, _callee2, null, [[1, 3, 4, 5]]);
}));
return function (_x2) {
return _ref2.apply(this, arguments);
};
}(), 100);
var handleOpenApp = function handleOpenApp(linkParams) {
var link = "".concat(targetApp.uri).concat(linkParams ? "".concat(linkParams) : "");
window.location.href = link;
};
useEffect(function () {
if (completed) {
pushPage({
key: "Connect Success",
content: jsx(SuccessPage, {
text: "Successfully connected to WalletConnect!",
onComplete: closeModal,
duration: successPageDuration
}),
preventBack: true,
showTitle: false
});
}
}, [completed]);
return jsx("div", {
className: clsx("flex flex-col items-center justify-center py-5 text-center", isMobile ? "w-full" : "w-auto"),
children: !shouldStartConnecting ? jsxs("div", {
className: clsx("flex flex-col gap-4 mt-6 items-center justify-center", isMobile ? "w-full" : "w-96"),
children: [jsx("img", {
src: targetApp.info.icon,
className: "size-14 rounded-full"
}), jsxs("span", {
className: "text-sm text-center text-icon-text-light dark:text-icon-text-dark",
children: ["You can connect", " ", (_targetApp$info$name = targetApp.info.name) !== null && _targetApp$info$name !== void 0 ? _targetApp$info$name : "this wallet provider", " using your mobile device. Open this page on your mobile device to continue or scan the QR code with your wallet app."]
}), jsxs("span", {
className: "text-sm text-center text-icon-text-light dark:text-icon-text-dark",
children: ["Already on mobile?", " ", jsxs("span", {
className: "text-primary-light dark:text-primary-dark cursor-pointer underline",
onClick: function onClick() {
return setShouldStartConnecting(true);
},
children: ["Try opening ", targetApp.info.name, " anyways."]
})]
}), jsx(ActionButton, {
onClick: function onClick() {
return (
// At this point, the user already selected the chian. So we can pass it in to redirect directly to the QR code for that chain
onSelectQRCode(targetApp.chainInfo.namespace)
);
},
className: "w-full text-inherit bg-button-light dark:bg-button-dark",
children: jsxs("div", {
className: "flex flex-row w-full justify-center items-center gap-2",
children: ["Scan QR code", jsx(FontAwesomeIcon, {
icon: faQrcode,
size: "lg",
className: "text-icon-text-light dark:text-icon-text-dark"
})]
})
})]
}) : canSign ? jsxs("div", {
className: clsx("flex flex-col gap-4 mt-6 items-center justify-center", isMobile ? "w-full" : "w-72"),
children: [jsx("img", {
src: targetApp.info.icon,
className: "size-14 rounded-full"
}), jsxs("span", {
className: "text-sm text-center text-icon-text-light dark:text-icon-text-dark",
children: [(_targetApp$info$name2 = targetApp.info.name) !== null && _targetApp$info$name2 !== void 0 ? _targetApp$info$name2 : "This wallet provider", " is connected! Please sign the login request using the app to continue."]
}), jsx(ActionButton, {
onClick: function onClick() {
handleOpenApp();
runSignAction(latestProviderRef.current);
},
loading: isConnecting,
loadingText: "Check the app...",
className: "w-full text-inherit bg-button-light dark:bg-button-dark",
children: jsxs("div", {
className: "flex flex-row w-full justify-center items-center gap-1.5",
children: ["Sign login request", jsx(FontAwesomeIcon, {
icon: faArrowUpRightFromSquare,
size: "sm",
className: "text-icon-text-light dark:text-icon-text-dark"
})]
})
})]
}) : jsxs("div", {
className: "flex flex-col",
children: [jsx(ActionPage
// Run the action from a separate useEffect. No need to pass it here
, {
// Run the action from a separate useEffect. No need to pass it here
title: "Connecting to ".concat(targetApp.info.name),
icon: jsx("img", {
className: "size-11 rounded-full",
src: targetApp.info.icon || ""
})
}), jsxs("div", {
className: "text-icon-text-light text-sm dark:text-icon-text-dark text-center !p-0",
children: ["App not opening? Please ensure you have ", targetApp.info.name, " ", "installed or", " ", jsxs("span", {
className: "text-primary-light dark:text-primary-dark cursor-pointer underline",
onClick: function onClick() {
var _latestProviderRef$cu3, _latestProviderRef$cu4;
handleOpenApp("wc?uri=".concat(encodeURIComponent((_latestProviderRef$cu3 = latestProviderRef === null || latestProviderRef === void 0 ? void 0 : (_latestProviderRef$cu4 = latestProviderRef.current) === null || _latestProviderRef$cu4 === void 0 ? void 0 : _latestProviderRef$cu4.uri) !== null && _latestProviderRef$cu3 !== void 0 ? _latestProviderRef$cu3 : "")));
},
children: ["try opening ", targetApp.info.name, " again."]
})]
})]
})
});
}
export { MobileWalletConnectScreen };
//# sourceMappingURL=MobileWalletConnectScreen.mjs.map