feat: update app download tracking for Android launch (#7542)
* feat: change UniwalletModal android text * very wip android WC * adding android/ios disambiguated event names * put analytics events in todos * use analytics package * use isAndroidGALaunched * fix ternary * add navbar menu element * broken onelink changes * replace utm with onelinks * use microsite link in address redirect * fix unit tests, no longer discriminate between platforms expected behavior * nit lint
This commit is contained in:
parent
aa056adaf9
commit
46c8caa09c
@ -197,7 +197,7 @@
|
||||
"@types/react-helmet": "^6.1.7",
|
||||
"@types/react-window-infinite-loader": "^1.0.6",
|
||||
"@uniswap/analytics": "1.5.0",
|
||||
"@uniswap/analytics-events": "^2.25.0",
|
||||
"@uniswap/analytics-events": "^2.28.0",
|
||||
"@uniswap/governance": "^1.0.2",
|
||||
"@uniswap/liquidity-staker": "^1.0.2",
|
||||
"@uniswap/merkle-distributor": "^1.0.1",
|
||||
|
@ -1,4 +1,5 @@
|
||||
import { InterfaceElementName } from '@uniswap/analytics-events'
|
||||
import { useAndroidGALaunchFlagEnabled } from 'featureFlags/flags/androidGALaunch'
|
||||
import { PropsWithChildren, useCallback } from 'react'
|
||||
import styled from 'styled-components'
|
||||
import { ClickableStyle } from 'theme/components'
|
||||
@ -31,7 +32,7 @@ function BaseButton({ onClick, branded, children }: PropsWithChildren<{ onClick?
|
||||
)
|
||||
}
|
||||
|
||||
// Launches App Store if on an iOS device, else navigates to Uniswap Wallet microsite
|
||||
// Launches App/Play Store if on an iOS/Android device, else navigates to Uniswap Wallet microsite
|
||||
export function DownloadButton({
|
||||
onClick,
|
||||
text = 'Download',
|
||||
@ -41,11 +42,12 @@ export function DownloadButton({
|
||||
text?: string
|
||||
element: InterfaceElementName
|
||||
}) {
|
||||
const isAndroidGALaunched = useAndroidGALaunchFlagEnabled()
|
||||
const onButtonClick = useCallback(() => {
|
||||
// handles any actions required by the parent, i.e. cancelling wallet connection attempt or dismissing an ad
|
||||
onClick?.()
|
||||
openDownloadApp({ element })
|
||||
}, [element, onClick])
|
||||
openDownloadApp({ element, isAndroidGALaunched })
|
||||
}, [element, isAndroidGALaunched, onClick])
|
||||
|
||||
return (
|
||||
<BaseButton branded onClick={onButtonClick}>
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { Trans } from '@lingui/macro'
|
||||
import { InterfaceElementName } from '@uniswap/analytics-events'
|
||||
import { InterfaceElementName, InterfaceEventName } from '@uniswap/analytics-events'
|
||||
import { WalletConnect as WalletConnectv2 } from '@web3-react/walletconnect-v2'
|
||||
import { sendAnalyticsEvent } from 'analytics'
|
||||
import Column, { AutoColumn } from 'components/Column'
|
||||
@ -9,11 +9,12 @@ import { uniwalletWCV2ConnectConnection } from 'connection'
|
||||
import { ActivationStatus, useActivationState } from 'connection/activate'
|
||||
import { ConnectionType } from 'connection/types'
|
||||
import { UniwalletConnect as UniwalletConnectV2 } from 'connection/WalletConnectV2'
|
||||
import { useAndroidGALaunchFlagEnabled } from 'featureFlags/flags/androidGALaunch'
|
||||
import { QRCodeSVG } from 'qrcode.react'
|
||||
import { useEffect, useState } from 'react'
|
||||
import styled, { useTheme } from 'styled-components'
|
||||
import { CloseIcon, ThemedText } from 'theme/components'
|
||||
import { isIOS } from 'utils/userAgent'
|
||||
import { isAndroid, isIOS } from 'utils/userAgent'
|
||||
|
||||
import uniPng from '../../assets/images/uniwallet_modal_icon.png'
|
||||
import { DownloadButton } from './DownloadButton'
|
||||
@ -42,9 +43,11 @@ export default function UniwalletModal() {
|
||||
const { activationState, cancelActivation } = useActivationState()
|
||||
const [uri, setUri] = useState<string>()
|
||||
|
||||
// Displays the modal if not on iOS, a Uniswap Wallet Connection is pending, & qrcode URI is available
|
||||
const isAndroidGALaunched = useAndroidGALaunchFlagEnabled()
|
||||
// Displays the modal if not on iOS/Android, a Uniswap Wallet Connection is pending, & qrcode URI is available
|
||||
const onLaunchedMobilePlatform = isIOS || (isAndroidGALaunched && isAndroid)
|
||||
const open =
|
||||
!isIOS &&
|
||||
!onLaunchedMobilePlatform &&
|
||||
activationState.status === ActivationStatus.PENDING &&
|
||||
activationState.connection.type === ConnectionType.UNISWAP_WALLET_V2 &&
|
||||
!!uri
|
||||
@ -57,7 +60,7 @@ export default function UniwalletModal() {
|
||||
}, [])
|
||||
|
||||
useEffect(() => {
|
||||
if (open) sendAnalyticsEvent('Uniswap wallet modal opened')
|
||||
if (open) sendAnalyticsEvent(InterfaceEventName.UNIWALLET_CONNECT_MODAL_OPENED)
|
||||
}, [open])
|
||||
|
||||
const theme = useTheme()
|
||||
@ -102,6 +105,8 @@ const InfoSectionWrapper = styled(RowBetween)`
|
||||
`
|
||||
|
||||
function InfoSection() {
|
||||
const isAndroidGALaunched = useAndroidGALaunchFlagEnabled()
|
||||
|
||||
return (
|
||||
<InfoSectionWrapper>
|
||||
<AutoColumn gap="4px">
|
||||
@ -109,9 +114,13 @@ function InfoSection() {
|
||||
<Trans>Don't have Uniswap Wallet?</Trans>
|
||||
</ThemedText.SubHeaderSmall>
|
||||
<ThemedText.BodySmall color="neutral2">
|
||||
<Trans>
|
||||
Download in the App Store to safely store your tokens and NFTs, swap tokens, and connect to crypto apps.
|
||||
</Trans>
|
||||
{isAndroidGALaunched ? (
|
||||
<Trans>Get the Uniswap app on iOS and Android to safely store and swap tokens.</Trans>
|
||||
) : (
|
||||
<Trans>
|
||||
Download in the App Store to safely store your tokens and NFTs, swap tokens, and connect to crypto apps.
|
||||
</Trans>
|
||||
)}
|
||||
</ThemedText.BodySmall>
|
||||
</AutoColumn>
|
||||
<Column>
|
||||
|
@ -11,7 +11,7 @@ import { useLocation } from 'react-router-dom'
|
||||
import { useHideBaseWalletBanner } from 'state/user/hooks'
|
||||
import { ThemedText } from 'theme/components'
|
||||
import { openDownloadApp, openWalletMicrosite } from 'utils/openDownloadApp'
|
||||
import { isIOS, isMobileSafari } from 'utils/userAgent'
|
||||
import { isAndroid, isIOS, isMobileSafari } from 'utils/userAgent'
|
||||
|
||||
import { BannerButton, BaseBackgroundImage, ButtonRow, PopupContainer, StyledXButton } from './styled'
|
||||
|
||||
@ -60,14 +60,14 @@ export default function BaseWalletBanner() {
|
||||
</ThemedText.HeadlineMedium>
|
||||
|
||||
<ButtonRow>
|
||||
{isIOS ? (
|
||||
{isIOS || (isAndroidGALaunched && isAndroid) ? (
|
||||
<>
|
||||
<BannerButton
|
||||
backgroundColor="white"
|
||||
onClick={() =>
|
||||
openDownloadApp({
|
||||
element: InterfaceElementName.UNISWAP_WALLET_BANNER_DOWNLOAD_BUTTON,
|
||||
appStoreParams: 'pt=123625782&ct=base-app-banner&mt=8',
|
||||
isAndroidGALaunched,
|
||||
})
|
||||
}
|
||||
>
|
||||
@ -77,14 +77,23 @@ export default function BaseWalletBanner() {
|
||||
</ThemedText.LabelSmall>
|
||||
</BannerButton>
|
||||
|
||||
<BannerButton backgroundColor="black" onClick={() => openWalletMicrosite()}>
|
||||
<BannerButton
|
||||
backgroundColor="black"
|
||||
onClick={() =>
|
||||
openWalletMicrosite({ element: InterfaceElementName.UNISWAP_WALLET_BANNER_DOWNLOAD_BUTTON })
|
||||
}
|
||||
>
|
||||
<ThemedText.LabelSmall color="white">
|
||||
<Trans>Learn more</Trans>
|
||||
</ThemedText.LabelSmall>
|
||||
</BannerButton>
|
||||
</>
|
||||
) : (
|
||||
<BannerButton backgroundColor="white" width="125px" onClick={() => openWalletMicrosite()}>
|
||||
<BannerButton
|
||||
backgroundColor="white"
|
||||
width="125px"
|
||||
onClick={() => openWalletMicrosite({ element: InterfaceElementName.UNISWAP_WALLET_BANNER_DOWNLOAD_BUTTON })}
|
||||
>
|
||||
<ThemedText.LabelSmall color="black">
|
||||
<Trans>Learn more</Trans>
|
||||
</ThemedText.LabelSmall>
|
||||
|
@ -174,7 +174,8 @@ export const MenuDropdown = () => {
|
||||
<Box
|
||||
onClick={() =>
|
||||
openDownloadApp({
|
||||
element: InterfaceElementName.UNISWAP_WALLET_MODAL_DOWNLOAD_BUTTON,
|
||||
element: InterfaceElementName.UNISWAP_WALLET_NAVBAR_MENU_DOWNLOAD_BUTTON,
|
||||
isAndroidGALaunched,
|
||||
})
|
||||
}
|
||||
>
|
||||
|
@ -6,6 +6,7 @@ import { AutoRow } from 'components/Row'
|
||||
import { connections, deprecatedNetworkConnection, networkConnection } from 'connection'
|
||||
import { ActivationStatus, useActivationState } from 'connection/activate'
|
||||
import { isSupportedChain } from 'constants/chains'
|
||||
import { useAndroidGALaunchFlagEnabled } from 'featureFlags/flags/androidGALaunch'
|
||||
import { useFallbackProviderEnabled } from 'featureFlags/flags/fallbackProvider'
|
||||
import { useEffect } from 'react'
|
||||
import styled from 'styled-components'
|
||||
@ -40,6 +41,7 @@ const PrivacyPolicyWrapper = styled.div`
|
||||
|
||||
export default function WalletModal({ openSettings }: { openSettings: () => void }) {
|
||||
const { connector, chainId } = useWeb3React()
|
||||
const isAndroidGALaunched = useAndroidGALaunchFlagEnabled()
|
||||
|
||||
const { activationState } = useActivationState()
|
||||
const fallbackProviderEnabled = useFallbackProviderEnabled()
|
||||
@ -66,7 +68,7 @@ export default function WalletModal({ openSettings }: { openSettings: () => void
|
||||
<AutoColumn gap="16px">
|
||||
<OptionGrid data-testid="option-grid">
|
||||
{connections
|
||||
.filter((connection) => connection.shouldDisplay())
|
||||
.filter((connection) => connection.shouldDisplay(isAndroidGALaunched))
|
||||
.map((connection) => (
|
||||
<Option key={connection.getName()} connection={connection} />
|
||||
))}
|
||||
|
@ -11,7 +11,7 @@ import COINBASE_ICON from 'assets/wallets/coinbase-icon.svg'
|
||||
import UNIWALLET_ICON from 'assets/wallets/uniswap-wallet-icon.png'
|
||||
import WALLET_CONNECT_ICON from 'assets/wallets/walletconnect-icon.svg'
|
||||
import { useSyncExternalStore } from 'react'
|
||||
import { isMobile, isNonIOSPhone } from 'utils/userAgent'
|
||||
import { isMobile, isNonIOSPhone, isNonSupportedPhone } from 'utils/userAgent'
|
||||
|
||||
import { RPC_URLS } from '../constants/networks'
|
||||
import { DEPRECATED_RPC_PROVIDERS, RPC_PROVIDERS } from '../constants/providers'
|
||||
@ -149,7 +149,8 @@ export const uniwalletWCV2ConnectConnection: Connection = {
|
||||
hooks: web3WCV2UniwalletConnectHooks,
|
||||
type: ConnectionType.UNISWAP_WALLET_V2,
|
||||
getIcon: () => UNIWALLET_ICON,
|
||||
shouldDisplay: () => Boolean(!getIsInjectedMobileBrowser() && !isNonIOSPhone),
|
||||
shouldDisplay: (isAndroidGALaunched) =>
|
||||
Boolean(!getIsInjectedMobileBrowser() && (isAndroidGALaunched ? !isNonSupportedPhone : !isNonIOSPhone)),
|
||||
}
|
||||
|
||||
const [web3CoinbaseWallet, web3CoinbaseWalletHooks] = initializeConnector<CoinbaseWallet>(
|
||||
|
@ -26,6 +26,6 @@ export interface Connection {
|
||||
hooks: Web3ReactHooks
|
||||
type: ConnectionType
|
||||
getIcon?(isDarkMode: boolean): string
|
||||
shouldDisplay(): boolean
|
||||
shouldDisplay(isAndroidGALaunched?: boolean): boolean
|
||||
overrideActivate?: (chainId?: ChainId) => boolean
|
||||
}
|
||||
|
@ -25,7 +25,7 @@ import { Z_INDEX } from 'theme/zIndex'
|
||||
import { STATSIG_DUMMY_KEY } from 'tracing'
|
||||
import { isPathBlocked } from 'utils/blockedPaths'
|
||||
import { getEnvName } from 'utils/env'
|
||||
import { getDownloadAppLink } from 'utils/openDownloadApp'
|
||||
import { MICROSITE_LINK } from 'utils/openDownloadApp'
|
||||
import { getCurrentPageFromLocation } from 'utils/urlRoutes'
|
||||
import { getCLS, getFCP, getFID, getLCP, Metric } from 'web-vitals'
|
||||
|
||||
@ -145,7 +145,7 @@ export default function App() {
|
||||
const shouldRedirectToAppInstall = pathname?.startsWith('/address/')
|
||||
useLayoutEffect(() => {
|
||||
if (shouldRedirectToAppInstall) {
|
||||
window.location.href = getDownloadAppLink()
|
||||
window.location.href = MICROSITE_LINK
|
||||
}
|
||||
}, [shouldRedirectToAppInstall])
|
||||
|
||||
|
@ -2114,7 +2114,7 @@ exports[`disable nft on landing page does not render nft information and card 1`
|
||||
</div>
|
||||
<a
|
||||
class="c63"
|
||||
href="https://wallet.uniswap.org/?utm_source=home_page&utm_medium=webapp&utm_campaign=wallet_microsite&utm_id=1"
|
||||
href="https://uniswapwallet.onelink.me/8q3y/79gveilz"
|
||||
>
|
||||
<svg
|
||||
height="20"
|
||||
@ -4727,7 +4727,7 @@ exports[`disable nft on landing page renders nft information and card 1`] = `
|
||||
</div>
|
||||
<a
|
||||
class="c63"
|
||||
href="https://wallet.uniswap.org/?utm_source=home_page&utm_medium=webapp&utm_campaign=wallet_microsite&utm_id=1"
|
||||
href="https://uniswapwallet.onelink.me/8q3y/79gveilz"
|
||||
>
|
||||
<svg
|
||||
height="20"
|
||||
|
@ -1,14 +0,0 @@
|
||||
import { render } from 'test-utils/render'
|
||||
|
||||
import Landing from '.'
|
||||
|
||||
jest.mock('utils/userAgent', () => {
|
||||
return {
|
||||
isIOS: true,
|
||||
}
|
||||
})
|
||||
|
||||
it('renders ios microsite link', () => {
|
||||
const { container } = render(<Landing />)
|
||||
expect(container.innerHTML.includes(`https://apps.apple.com/app/apple-store/id6443944476`)).toBeTruthy()
|
||||
})
|
@ -1,14 +0,0 @@
|
||||
import { render } from 'test-utils/render'
|
||||
|
||||
import Landing from '.'
|
||||
|
||||
jest.mock('utils/userAgent', () => {
|
||||
return {
|
||||
isIOS: false,
|
||||
}
|
||||
})
|
||||
|
||||
it('renders non-ios microsite link', () => {
|
||||
const { container } = render(<Landing />)
|
||||
expect(container.innerHTML.includes(`https://wallet.uniswap.org/?utm_source=home_page`)).toBeTruthy()
|
||||
})
|
@ -34,3 +34,10 @@ describe('disable nft on landing page', () => {
|
||||
)
|
||||
})
|
||||
})
|
||||
|
||||
describe('Uniswap wallet app download link', () => {
|
||||
it('renders onelink app download', () => {
|
||||
const { container } = render(<Landing />)
|
||||
expect(container.innerHTML.includes('https://uniswapwallet.onelink.me/8q3y/79gveilz')).toBeTruthy()
|
||||
})
|
||||
})
|
||||
|
@ -399,9 +399,8 @@ export default function Landing() {
|
||||
|
||||
<DownloadWalletLink
|
||||
{...getDownloadAppLinkProps({
|
||||
// landing page specific tracking params
|
||||
microSiteParams: `utm_source=home_page&utm_medium=webapp&utm_campaign=wallet_microsite&utm_id=1`,
|
||||
appStoreParams: `ct=Uniswap-Home-Page&mt=8`,
|
||||
element: InterfaceElementName.UNISWAP_WALLET_LANDING_PAGE_DOWNLOAD_BUTTON,
|
||||
isAndroidGALaunched,
|
||||
})}
|
||||
>
|
||||
{isAndroidGALaunched ? (
|
||||
|
@ -1,69 +1,68 @@
|
||||
import { InterfaceElementName, InterfaceEventName } from '@uniswap/analytics-events'
|
||||
import { AppDownloadPlatform, InterfaceElementName, InterfaceEventName } from '@uniswap/analytics-events'
|
||||
import { sendAnalyticsEvent } from 'analytics'
|
||||
import { isIOS } from 'utils/userAgent'
|
||||
import { isAndroid, isIOS } from 'utils/userAgent'
|
||||
|
||||
const APP_STORE_LINK = 'https://apps.apple.com/app/apple-store/id6443944476'
|
||||
const MICROSITE_LINK = 'https://wallet.uniswap.org/'
|
||||
|
||||
type OpenDownloadAppOptions = {
|
||||
element?: InterfaceElementName
|
||||
appStoreParams?: string
|
||||
microSiteParams?: string
|
||||
// OneLink will direct to App/Play Store or microsite depending on user agent
|
||||
const APP_DOWNLOAD_LINKS: Partial<{ [key in InterfaceElementName]: string }> = {
|
||||
[InterfaceElementName.UNISWAP_WALLET_MODAL_DOWNLOAD_BUTTON]: 'https://uniswapwallet.onelink.me/8q3y/qfwlncf9',
|
||||
[InterfaceElementName.UNISWAP_WALLET_NAVBAR_MENU_DOWNLOAD_BUTTON]: 'https://uniswapwallet.onelink.me/8q3y/46tvu6pb',
|
||||
[InterfaceElementName.UNISWAP_WALLET_LANDING_PAGE_DOWNLOAD_BUTTON]: 'https://uniswapwallet.onelink.me/8q3y/79gveilz',
|
||||
[InterfaceElementName.UNISWAP_WALLET_BANNER_DOWNLOAD_BUTTON]: 'https://uniswapwallet.onelink.me/8q3y/jh9orof3',
|
||||
}
|
||||
|
||||
const defaultDownloadAppOptions = {
|
||||
appStoreParams: `pt=123625782&ct=In-App-Banners&mt=8`,
|
||||
export const MICROSITE_LINK = 'https://wallet.uniswap.org/'
|
||||
|
||||
type OpenDownloadAppOptions = {
|
||||
element: InterfaceElementName
|
||||
isAndroidGALaunched: boolean
|
||||
}
|
||||
|
||||
/**
|
||||
* Note: openDownloadApp and getDownloadAppLink are equivalent functions, the first just runs imperatively
|
||||
* Note: openDownloadApp is equivalent to APP_DOWNLOAD_LINKS[element], the first just runs imperatively
|
||||
* and adds an analytics event, where the other only returns a link. Typically you'll use both:
|
||||
*
|
||||
* <a href={getDownloadAppLink(options)} onClick={() => openDownloadApp(options)} />
|
||||
* <a href={APP_DOWNLOAD_LINKS[element]} onClick={() => openDownloadApp(element)} />
|
||||
*
|
||||
* This way with JS disabled and when hovering the <a /> you see and nav to the full href properly,
|
||||
* but with JS on it will send the analytics event before navigating to the href.
|
||||
*
|
||||
* I've added a helper `getDownloadAppLinkProps` that unifies this behavior into one thing.
|
||||
*/
|
||||
|
||||
export function openDownloadApp(options: OpenDownloadAppOptions = defaultDownloadAppOptions) {
|
||||
export function openDownloadApp({ element, isAndroidGALaunched }: OpenDownloadAppOptions) {
|
||||
if (isIOS) {
|
||||
openAppStore({ element: options?.element, urlParamString: options?.appStoreParams })
|
||||
openDownloadStore({ element, appPlatform: AppDownloadPlatform.IOS, linkTarget: 'uniswap_wallet_appstore' })
|
||||
} else if (isAndroidGALaunched && isAndroid) {
|
||||
openDownloadStore({ element, appPlatform: AppDownloadPlatform.ANDROID, linkTarget: 'uniswap_wallet_playstore' })
|
||||
} else {
|
||||
openWalletMicrosite({ element: options?.element, urlParamString: options?.microSiteParams })
|
||||
openWalletMicrosite({ element })
|
||||
}
|
||||
}
|
||||
|
||||
// if you need this by itself can add export, not used externally for now
|
||||
export const getDownloadAppLink = (options: OpenDownloadAppOptions = defaultDownloadAppOptions) =>
|
||||
isIOS
|
||||
? linkWithParams(APP_STORE_LINK, options?.appStoreParams)
|
||||
: linkWithParams(MICROSITE_LINK, options?.microSiteParams)
|
||||
|
||||
export const getDownloadAppLinkProps = (options: OpenDownloadAppOptions = defaultDownloadAppOptions) => {
|
||||
export const getDownloadAppLinkProps = ({ element, isAndroidGALaunched }: OpenDownloadAppOptions) => {
|
||||
return {
|
||||
href: getDownloadAppLink(options),
|
||||
href: APP_DOWNLOAD_LINKS[element],
|
||||
onClick(e: { preventDefault: () => void }) {
|
||||
e.preventDefault()
|
||||
openDownloadApp(options)
|
||||
openDownloadApp({ element, isAndroidGALaunched })
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
type AnalyticsLinkOptions = {
|
||||
element?: InterfaceElementName
|
||||
urlParamString?: string
|
||||
element: InterfaceElementName
|
||||
appPlatform?: AppDownloadPlatform
|
||||
linkTarget?: string
|
||||
}
|
||||
|
||||
const openAppStore = (options?: AnalyticsLinkOptions) => {
|
||||
sendAnalyticsEvent(InterfaceEventName.UNISWAP_WALLET_APP_DOWNLOAD_OPENED, { element: options?.element })
|
||||
window.open(linkWithParams(APP_STORE_LINK, options?.urlParamString), /* target = */ 'uniswap_wallet_appstore')
|
||||
const openDownloadStore = (options: AnalyticsLinkOptions) => {
|
||||
sendAnalyticsEvent(InterfaceEventName.UNISWAP_WALLET_APP_DOWNLOAD_OPENED, {
|
||||
element: options.element,
|
||||
appPlatform: options?.appPlatform,
|
||||
})
|
||||
window.open(APP_DOWNLOAD_LINKS[options.element], /* target = */ options.linkTarget)
|
||||
}
|
||||
|
||||
export const openWalletMicrosite = (options?: AnalyticsLinkOptions) => {
|
||||
sendAnalyticsEvent(InterfaceEventName.UNISWAP_WALLET_MICROSITE_OPENED, { element: options?.element })
|
||||
window.open(linkWithParams(MICROSITE_LINK, options?.urlParamString), /* target = */ 'uniswap_wallet_microsite')
|
||||
export const openWalletMicrosite = (options: AnalyticsLinkOptions) => {
|
||||
sendAnalyticsEvent(InterfaceEventName.UNISWAP_WALLET_MICROSITE_OPENED, { element: options.element })
|
||||
window.open(APP_DOWNLOAD_LINKS[options.element], /* target = */ 'uniswap_wallet_microsite')
|
||||
}
|
||||
|
||||
const linkWithParams = (link: string, params?: string) => link + (params ? `?${params}` : '')
|
||||
|
@ -7,6 +7,8 @@ const { name } = parser.getBrowser()
|
||||
export const isMobile = type === 'mobile' || type === 'tablet'
|
||||
const platform = parser.getOS().name
|
||||
export const isIOS = platform === 'iOS'
|
||||
export const isAndroid = platform === 'Android'
|
||||
export const isNonIOSPhone = !isIOS && type === 'mobile'
|
||||
export const isNonSupportedPhone = !isIOS && !isAndroid && type === 'mobile'
|
||||
|
||||
export const isMobileSafari = isMobile && isIOS && name?.toLowerCase().includes('safari')
|
||||
|
@ -6059,10 +6059,10 @@
|
||||
"@typescript-eslint/types" "5.59.1"
|
||||
eslint-visitor-keys "^3.3.0"
|
||||
|
||||
"@uniswap/analytics-events@^2.25.0":
|
||||
version "2.25.0"
|
||||
resolved "https://registry.yarnpkg.com/@uniswap/analytics-events/-/analytics-events-2.25.0.tgz#06f2d81342b2e4dc516bdfa1222ddaa7c274ac04"
|
||||
integrity sha512-0syw7gZtoHXSCVb+zV464L+Zgy1ICnGDOrbK2xoVtpiQ8rBjUXPWvcKuaiNPfTsS9tIZNtqOmEyZEjWwvFSLUw==
|
||||
"@uniswap/analytics-events@^2.28.0":
|
||||
version "2.28.0"
|
||||
resolved "https://registry.yarnpkg.com/@uniswap/analytics-events/-/analytics-events-2.28.0.tgz#344fbbe3e120b7f8100e4d540004847f7147cf6e"
|
||||
integrity sha512-j650l315p9W5dbVPzHRu485omyZw+I6jU/ZGpzuz4OdrJIp8yCl57LTLFfmMsZGwmJYDlOxY2fB6Jrbc2lUvUA==
|
||||
|
||||
"@uniswap/analytics@1.5.0":
|
||||
version "1.5.0"
|
||||
|
Loading…
Reference in New Issue
Block a user