diff --git a/.yarn/patches/react-native-htmlview-npm-0.16.0-501f1b89ba.patch b/.yarn/patches/react-native-htmlview-npm-0.16.0-501f1b89ba.patch
deleted file mode 100644
index f42c82e7..00000000
--- a/.yarn/patches/react-native-htmlview-npm-0.16.0-501f1b89ba.patch
+++ /dev/null
@@ -1,22 +0,0 @@
-diff --git a/HTMLView.js b/HTMLView.js
-index 43f8b7eb552d9a44b5feef74ec2ae7d7ddbc2fca..334d144f1fb96067726bca199ff37267c2fa0fb2 100644
---- a/HTMLView.js
-+++ b/HTMLView.js
-@@ -1,7 +1,7 @@
- import React, {PureComponent} from 'react';
- import PropTypes from 'prop-types';
- import htmlToElement from './htmlToElement';
--import {Linking, Platform, StyleSheet, View, ViewPropTypes} from 'react-native';
-+import {Linking, Platform, StyleSheet, View} from 'react-native';
-
- const boldStyle = {fontWeight: 'bold'};
- const italicStyle = {fontStyle: 'italic'};
-@@ -146,7 +146,7 @@ HtmlView.propTypes = {
- renderNode: PropTypes.func,
- RootComponent: PropTypes.func,
- rootComponentProps: PropTypes.object,
-- style: ViewPropTypes.style,
-+ style: PropTypes.object,
- stylesheet: PropTypes.object,
- TextComponent: PropTypes.func,
- textComponentProps: PropTypes.object,
diff --git a/fastlane/metadata/en-US/release_notes.txt b/fastlane/metadata/en-US/release_notes.txt
index 731c525f..62516967 100644
--- a/fastlane/metadata/en-US/release_notes.txt
+++ b/fastlane/metadata/en-US/release_notes.txt
@@ -1,4 +1,5 @@
Enjoy toooting! This version includes following improvements and fixes:
- Allowing adding more context of reports
- Option to disable autoplay gif
-- Hide boosts from users
\ No newline at end of file
+- Hide boosts from users
+- Followed hashtags are underlined
\ No newline at end of file
diff --git a/fastlane/metadata/zh-Hans/release_notes.txt b/fastlane/metadata/zh-Hans/release_notes.txt
index af941da8..8225007b 100644
--- a/fastlane/metadata/zh-Hans/release_notes.txt
+++ b/fastlane/metadata/zh-Hans/release_notes.txt
@@ -1,4 +1,5 @@
toooting愉快!此版本包括以下改进和修复:
- 可添加举报细节
- 新增暂停自动播放gif动画选项
-- 隐藏用户的转嘟
\ No newline at end of file
+- 隐藏用户的转嘟
+- 下划线高亮正在关注的话题标签
\ No newline at end of file
diff --git a/package.json b/package.json
index aba133e8..ab857b27 100644
--- a/package.json
+++ b/package.json
@@ -60,6 +60,7 @@
"expo-store-review": "^6.0.0",
"expo-video-thumbnails": "^7.0.0",
"expo-web-browser": "~12.0.0",
+ "htmlparser2": "^8.0.1",
"i18next": "^22.4.6",
"linkify-it": "^4.0.1",
"lodash": "^4.17.21",
@@ -75,7 +76,6 @@
"react-native-feather": "^1.1.2",
"react-native-flash-message": "^0.3.1",
"react-native-gesture-handler": "~2.8.0",
- "react-native-htmlview": "^0.16.0",
"react-native-image-picker": "^4.10.3",
"react-native-ios-context-menu": "^1.15.1",
"react-native-language-detection": "^0.2.2",
@@ -120,7 +120,6 @@
"resolutions": {
"react-native-fast-image@^8.6.3": "patch:react-native-fast-image@npm%3A8.6.3#./.yarn/patches/react-native-fast-image-npm-8.6.3-03ee2d23c0.patch",
"expo-av@^13.0.2": "patch:expo-av@npm%3A13.0.2#./.yarn/patches/expo-av-npm-13.0.2-7a651776f1.patch",
- "react-native-htmlview@^0.16.0": "patch:react-native-htmlview@npm%3A0.16.0#./.yarn/patches/react-native-htmlview-npm-0.16.0-501f1b89ba.patch",
"react-native-share-menu@^6.0.0": "patch:react-native-share-menu@npm%3A6.0.0#./.yarn/patches/react-native-share-menu-npm-6.0.0-f1094c3204.patch",
"@types/react-native-share-menu@^5.0.2": "patch:@types/react-native-share-menu@npm%3A5.0.2#./.yarn/patches/@types-react-native-share-menu-npm-5.0.2-373df17ecc.patch"
}
diff --git a/src/@types/untyped.d.ts b/src/@types/untyped.d.ts
index ad27df89..e00bdb1d 100644
--- a/src/@types/untyped.d.ts
+++ b/src/@types/untyped.d.ts
@@ -1,7 +1,5 @@
declare module 'gl-react-blurhash'
-declare module 'htmlparser2-without-node-native'
declare module 'react-native-feather'
-declare module 'react-native-htmlview'
declare module 'react-native-toast-message'
declare module 'rtl-detect'
diff --git a/src/components/Parse/HTML.tsx b/src/components/Parse/HTML.tsx
index 1bb73532..2c5f29a9 100644
--- a/src/components/Parse/HTML.tsx
+++ b/src/components/Parse/HTML.tsx
@@ -1,147 +1,23 @@
import Icon from '@components/Icon'
import openLink from '@components/openLink'
import ParseEmojis from '@components/Parse/Emojis'
-import CustomText from '@components/Text'
-import { getHost } from '@helpers/urlMatcher'
import { useNavigation, useRoute } from '@react-navigation/native'
import { StackNavigationProp } from '@react-navigation/stack'
import { TabLocalStackParamList } from '@utils/navigation/navigators'
+import { useFollowedTagsQuery } from '@utils/queryHooks/tags'
import { getSettingsFontsize } from '@utils/slices/settingsSlice'
import { StyleConstants } from '@utils/styles/constants'
import layoutAnimation from '@utils/styles/layoutAnimation'
import { adaptiveScale } from '@utils/styles/scaling'
import { useTheme } from '@utils/styles/ThemeManager'
+import { ChildNode } from 'domhandler'
+import { ElementType, parseDocument } from 'htmlparser2'
import { isEqual } from 'lodash'
-import React, { useCallback, useState } from 'react'
+import React, { useState } from 'react'
import { useTranslation } from 'react-i18next'
-import { Pressable, TextStyleIOS, View } from 'react-native'
-import HTMLView from 'react-native-htmlview'
+import { Pressable, Text, TextStyleIOS, View } from 'react-native'
import { useSelector } from 'react-redux'
-// Prevent going to the same hashtag multiple times
-const renderNode = ({
- routeParams,
- colors,
- node,
- index,
- adaptedFontsize,
- adaptedLineheight,
- navigation,
- mentions,
- tags,
- showFullLink,
- disableDetails
-}: {
- routeParams?: any
- colors: any
- node: any
- index: number
- adaptedFontsize: number
- adaptedLineheight: number
- navigation: StackNavigationProp
- mentions?: Mastodon.Mention[]
- tags?: Mastodon.Tag[]
- showFullLink: boolean
- disableDetails: boolean
-}) => {
- switch (node.name) {
- case 'a':
- const classes = node.attribs.class
- const href = node.attribs.href
- if (classes) {
- if (classes.includes('hashtag')) {
- const tag = href?.split(new RegExp(/\/tag\/(.*)|\/tags\/(.*)/))
- const differentTag = routeParams?.hashtag
- ? routeParams.hashtag !== tag[1] && routeParams.hashtag !== tag[2]
- : true
- return (
- {
- !disableDetails &&
- differentTag &&
- navigation.push('Tab-Shared-Hashtag', {
- hashtag: tag[1] || tag[2]
- })
- }}
- >
- {node.children[0].data}
- {node.children[1]?.children[0].data}
-
- )
- } else if (classes.includes('mention') && mentions) {
- const accountIndex = mentions.findIndex(mention => mention.url === href)
- const differentAccount = routeParams?.account
- ? routeParams.account.id !== mentions[accountIndex]?.id
- : true
- return (
- {
- accountIndex !== -1 &&
- !disableDetails &&
- differentAccount &&
- navigation.push('Tab-Shared-Account', {
- account: mentions[accountIndex]
- })
- }}
- >
- {node.children[0].data}
- {node.children[1]?.children[0].data}
-
- )
- }
- } else {
- const host = getHost(href)
- // Need example here
- const content = node.children && node.children[0] && node.children[0].data
- const shouldBeTag = tags && tags.filter(tag => `#${tag.name}` === content).length > 0
- return (
- {
- if (!disableDetails) {
- if (shouldBeTag) {
- navigation.push('Tab-Shared-Hashtag', {
- hashtag: content.substring(1)
- })
- } else {
- await openLink(href, navigation)
- }
- }
- }}
- >
- {content && content !== href ? content : showFullLink ? href : host}
- {!shouldBeTag ? '/...' : null}
-
- )
- }
- break
- case 'p':
- if (!node.children.length) {
- return // bug when the tag is empty
- }
- break
- }
-}
-
export interface Props {
content: string
size?: 'S' | 'M' | 'L'
@@ -187,8 +63,8 @@ const ParseHTML = React.memo(
)
const navigation = useNavigation>()
- const route = useRoute()
- const { colors, theme } = useTheme()
+ const { params } = useRoute()
+ const { colors } = useTheme()
const { t } = useTranslation('componentParse')
if (!expandHint) {
expandHint = t('HTML.defaultHint')
@@ -198,116 +74,195 @@ const ParseHTML = React.memo(
numberOfLines = 4
}
- const renderNodeCallback = useCallback(
- (node: any, index: any) =>
- renderNode({
- routeParams: route.params,
- colors,
- node,
- index,
- adaptedFontsize,
- adaptedLineheight,
- navigation,
- mentions,
- tags,
- showFullLink,
- disableDetails
- }),
- []
- )
- const textComponent = useCallback(({ children }: any) => {
- if (children) {
- return (
-
- )
- } else {
- return null
+ const followedTags = useFollowedTagsQuery()
+
+ const [totalLines, setTotalLines] = useState()
+ const [expanded, setExpanded] = useState(highlighted)
+
+ const document = parseDocument(content)
+ const unwrapNode = (node: ChildNode): string => {
+ switch (node.type) {
+ case ElementType.Text:
+ return node.data
+ case ElementType.Tag:
+ if (node.name === 'span') {
+ if (node.attribs.class?.includes('invisible')) return ''
+ if (node.attribs.class?.includes('ellipsis'))
+ return node.children.map(child => unwrapNode(child)).join('') + '...'
+ }
+ return node.children.map(child => unwrapNode(child)).join('')
+ default:
+ return ''
}
- }, [])
- const rootComponent = useCallback(
- ({ children }: any) => {
- const { t } = useTranslation('componentParse')
-
- const [totalLines, setTotalLines] = useState()
- const [expanded, setExpanded] = useState(highlighted)
-
- return (
-
- {(!disableDetails && typeof totalLines === 'number') || numberOfLines === 1 ? (
- {
- layoutAnimation()
- setExpanded(!expanded)
- if (setSpoilerExpanded) {
- setSpoilerExpanded(!expanded)
- }
- }}
- style={{
- flexDirection: 'row',
- justifyContent: 'center',
- alignItems: 'center',
- minHeight: 44,
- backgroundColor: colors.backgroundDefault
- }}
- >
- 1 && typeof totalLines === 'number'
- ? t('HTML.moreLines', { count: totalLines - numberOfLines })
- : ''
- })}
- />
-
-
- ) : null}
- {
- if (numberOfLines === 1 || nativeEvent.lines.length >= numberOfLines + 5) {
- setTotalLines(nativeEvent.lines.length)
- }
- }}
- style={{
- ...textStyles,
- height: numberOfLines === 1 && !expanded ? 0 : undefined
- }}
- numberOfLines={
- typeof totalLines === 'number' ? (expanded ? 999 : numberOfLines) : undefined
- }
- selectable={selectable}
+ }
+ const renderNode = (node: ChildNode, index: number) => {
+ switch (node.type) {
+ case ElementType.Text:
+ return (
+
-
- )
- },
- [theme]
- )
+ )
+ case ElementType.Tag:
+ switch (node.name) {
+ case 'a':
+ const classes = node.attribs.class
+ const href = node.attribs.href
+ if (classes) {
+ if (classes.includes('hashtag')) {
+ const tag = href.match(new RegExp(/\/tags?\/(.*)/, 'i'))?.[1]
+ const paramsHashtag = (params as { hashtag: Mastodon.Tag['name'] } | undefined)
+ ?.hashtag
+ const sameHashtag = paramsHashtag === tag
+ const isFollowing = followedTags.data?.pages[0]?.body.find(t => t.name === tag)
+ return (
+
+ tag?.length &&
+ !disableDetails &&
+ !sameHashtag &&
+ navigation.push('Tab-Shared-Hashtag', { hashtag: tag })
+ }
+ children={node.children.map(unwrapNode).join('')}
+ />
+ )
+ }
+ if (classes.includes('mention') && mentions?.length) {
+ const mentionIndex = mentions.findIndex(mention => mention.url === href)
+ const paramsAccount = (params as { account: Mastodon.Account } | undefined)
+ ?.account
+ const sameAccount = paramsAccount?.id === mentions[mentionIndex]?.id
+ return (
+ -1 ? colors.blue : undefined }}
+ onPress={() =>
+ mentionIndex > -1 &&
+ !disableDetails &&
+ !sameAccount &&
+ navigation.push('Tab-Shared-Account', { account: mentions[mentionIndex] })
+ }
+ children={node.children.map(unwrapNode).join('')}
+ />
+ )
+ }
+ }
+ const content = node.children.map(child => unwrapNode(child)).join('')
+ const shouldBeTag = tags && tags.find(tag => `#${tag.name}` === content)
+ return (
+ {
+ if (!disableDetails) {
+ if (shouldBeTag) {
+ navigation.push('Tab-Shared-Hashtag', {
+ hashtag: content.substring(1)
+ })
+ } else {
+ await openLink(href, navigation)
+ }
+ }
+ }}
+ children={content !== href ? content : showFullLink ? href : content}
+ />
+ )
+ break
+ case 'p':
+ if (index < document.children.length - 1) {
+ return (
+
+ {node.children.map((c, i) => renderNode(c, i))}
+ {'\n\n'}
+
+ )
+ } else {
+ return renderNode(c, i))} />
+ }
+ default:
+ return renderNode(c, i))} />
+ }
+ }
+ return null
+ }
return (
-
+
+ {(!disableDetails && typeof totalLines === 'number') || numberOfLines === 1 ? (
+ {
+ layoutAnimation()
+ setExpanded(!expanded)
+ if (setSpoilerExpanded) {
+ setSpoilerExpanded(!expanded)
+ }
+ }}
+ style={{
+ flexDirection: 'row',
+ justifyContent: 'center',
+ alignItems: 'center',
+ minHeight: 44,
+ backgroundColor: colors.backgroundDefault
+ }}
+ >
+ 1 && typeof totalLines === 'number'
+ ? t('HTML.moreLines', { count: totalLines - numberOfLines })
+ : ''
+ })}
+ />
+
+
+ ) : null}
+ {
+ if (numberOfLines === 1 || nativeEvent.lines.length >= numberOfLines + 5) {
+ setTotalLines(nativeEvent.lines.length)
+ }
+ }}
+ style={{
+ fontSize: adaptedFontsize,
+ lineHeight: adaptedLineheight,
+ ...textStyles,
+ height: numberOfLines === 1 && !expanded ? 0 : undefined
+ }}
+ numberOfLines={
+ typeof totalLines === 'number' ? (expanded ? 999 : numberOfLines) : undefined
+ }
+ selectable={selectable}
+ />
+
)
},
(prev, next) => prev.content === next.content && isEqual(prev.emojis, next.emojis)
diff --git a/src/components/Timeline/Shared/Content.tsx b/src/components/Timeline/Shared/Content.tsx
index b250d56a..ef09c945 100644
--- a/src/components/Timeline/Shared/Content.tsx
+++ b/src/components/Timeline/Shared/Content.tsx
@@ -5,7 +5,7 @@ import { StyleConstants } from '@utils/styles/constants'
import { useTheme } from '@utils/styles/ThemeManager'
import React, { useContext } from 'react'
import { useTranslation } from 'react-i18next'
-import { Platform } from 'react-native'
+import { Platform, View } from 'react-native'
import { useSelector } from 'react-redux'
import { isRtlLang } from 'rtl-detect'
import StatusContext from './Context'
@@ -24,7 +24,7 @@ const TimelineContent: React.FC = ({ notificationOwnToot = false, setSpoi
const instanceAccount = useSelector(getInstanceAccount, () => true)
return (
- <>
+
{status.spoiler_text?.length ? (
<>
= ({ notificationOwnToot = false, setSpoi
}
/>
)}
- >
+
)
}
diff --git a/src/helpers/removeHTML.ts b/src/helpers/removeHTML.ts
index e8a3d4c1..7f1b9832 100644
--- a/src/helpers/removeHTML.ts
+++ b/src/helpers/removeHTML.ts
@@ -1,4 +1,4 @@
-import htmlparser2 from 'htmlparser2-without-node-native'
+import * as htmlparser2 from 'htmlparser2'
const removeHTML = (text: string): string => {
let raw: string = ''
diff --git a/src/helpers/urlMatcher.ts b/src/helpers/urlMatcher.ts
index c08f036e..8c2286d9 100644
--- a/src/helpers/urlMatcher.ts
+++ b/src/helpers/urlMatcher.ts
@@ -1,7 +1,7 @@
import { store } from '@root/store'
import { getInstanceUrl } from '@utils/slices/instancesSlice'
-const getHost = (url: unknown): string | void => {
+const getHost = (url: unknown): string | undefined | null => {
if (typeof url !== 'string') return undefined
const matches = url.match(/^(?:https?:\/\/)?(?:[^@\/\n]+@)?(?:www\.)?([^:\/\n]+)/i)
diff --git a/yarn.lock b/yarn.lock
index f555d518..284740c3 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -5210,16 +5210,6 @@ __metadata:
languageName: node
linkType: hard
-"dom-serializer@npm:0":
- version: 0.2.2
- resolution: "dom-serializer@npm:0.2.2"
- dependencies:
- domelementtype: ^2.0.1
- entities: ^2.0.0
- checksum: 376344893e4feccab649a14ca1a46473e9961f40fe62479ea692d4fee4d9df1c00ca8654811a79c1ca7b020096987e1ca4fb4d7f8bae32c1db800a680a0e5d5e
- languageName: node
- linkType: hard
-
"dom-serializer@npm:^2.0.0":
version: 2.0.0
resolution: "dom-serializer@npm:2.0.0"
@@ -5231,29 +5221,13 @@ __metadata:
languageName: node
linkType: hard
-"domelementtype@npm:1, domelementtype@npm:^1.3.0":
- version: 1.3.1
- resolution: "domelementtype@npm:1.3.1"
- checksum: 7893da40218ae2106ec6ffc146b17f203487a52f5228b032ea7aa470e41dfe03e1bd762d0ee0139e792195efda765434b04b43cddcf63207b098f6ae44b36ad6
- languageName: node
- linkType: hard
-
-"domelementtype@npm:^2.0.1, domelementtype@npm:^2.3.0":
+"domelementtype@npm:^2.3.0":
version: 2.3.0
resolution: "domelementtype@npm:2.3.0"
checksum: ee837a318ff702622f383409d1f5b25dd1024b692ef64d3096ff702e26339f8e345820f29a68bcdcea8cfee3531776b3382651232fbeae95612d6f0a75efb4f6
languageName: node
linkType: hard
-"domhandler@npm:^2.3.0":
- version: 2.4.2
- resolution: "domhandler@npm:2.4.2"
- dependencies:
- domelementtype: 1
- checksum: 49bd70c9c784f845cd047e1dfb3611bd10891c05719acfc93f01fc726a419ed09fbe0b69f9064392d556a63fffc5a02010856cedae9368f4817146d95a97011f
- languageName: node
- linkType: hard
-
"domhandler@npm:^5.0.1, domhandler@npm:^5.0.2":
version: 5.0.3
resolution: "domhandler@npm:5.0.3"
@@ -5263,16 +5237,6 @@ __metadata:
languageName: node
linkType: hard
-"domutils@npm:^1.5.1":
- version: 1.7.0
- resolution: "domutils@npm:1.7.0"
- dependencies:
- dom-serializer: 0
- domelementtype: 1
- checksum: f60a725b1f73c1ae82f4894b691601ecc6ecb68320d87923ac3633137627c7865725af813ae5d188ad3954283853bcf46779eb50304ec5d5354044569fcefd2b
- languageName: node
- linkType: hard
-
"domutils@npm:^3.0.1":
version: 3.0.1
resolution: "domutils@npm:3.0.1"
@@ -5337,21 +5301,7 @@ __metadata:
languageName: node
linkType: hard
-"entities@npm:^1.1.1":
- version: 1.1.2
- resolution: "entities@npm:1.1.2"
- checksum: d537b02799bdd4784ffd714d000597ed168727bddf4885da887c5a491d735739029a00794f1998abbf35f3f6aeda32ef5c15010dca1817d401903a501b6d3e05
- languageName: node
- linkType: hard
-
-"entities@npm:^2.0.0":
- version: 2.2.0
- resolution: "entities@npm:2.2.0"
- checksum: 19010dacaf0912c895ea262b4f6128574f9ccf8d4b3b65c7e8334ad0079b3706376360e28d8843ff50a78aabcb8f08f0a32dbfacdc77e47ed77ca08b713669b3
- languageName: node
- linkType: hard
-
-"entities@npm:^4.2.0":
+"entities@npm:^4.2.0, entities@npm:^4.3.0":
version: 4.4.0
resolution: "entities@npm:4.4.0"
checksum: 84d250329f4b56b40fa93ed067b194db21e8815e4eb9b59f43a086f0ecd342814f6bc483de8a77da5d64e0f626033192b1b4f1792232a7ea6b970ebe0f3187c2
@@ -5489,13 +5439,6 @@ __metadata:
languageName: node
linkType: hard
-"eventemitter2@npm:^1.0.0":
- version: 1.0.5
- resolution: "eventemitter2@npm:1.0.5"
- checksum: f501d8ad439aad85b4d5494d96a83abbb156ed4acf5897fed53a99f4fa427c5a968959276461d8640b613ed16a34995fcd63a13404262e725131a29df9177c96
- languageName: node
- linkType: hard
-
"exec-async@npm:^2.2.0":
version: 2.2.0
resolution: "exec-async@npm:2.2.0"
@@ -6609,18 +6552,15 @@ __metadata:
languageName: node
linkType: hard
-"htmlparser2-without-node-native@npm:^3.9.2":
- version: 3.9.2
- resolution: "htmlparser2-without-node-native@npm:3.9.2"
+"htmlparser2@npm:^8.0.1":
+ version: 8.0.1
+ resolution: "htmlparser2@npm:8.0.1"
dependencies:
- domelementtype: ^1.3.0
- domhandler: ^2.3.0
- domutils: ^1.5.1
- entities: ^1.1.1
- eventemitter2: ^1.0.0
- inherits: ^2.0.1
- readable-stream: ^2.0.2
- checksum: 95754dc0f9ab057b5c072eaf2daed6db7595ec7a51290fde0cde6df803cbe528927764da4acb7bc9e633ff6396b07046eff7edb6f1f619fe665df4eaa8c735ad
+ domelementtype: ^2.3.0
+ domhandler: ^5.0.2
+ domutils: ^3.0.1
+ entities: ^4.3.0
+ checksum: 06d5c71e8313597722bc429ae2a7a8333d77bd3ab07ccb916628384b37332027b047f8619448d8f4a3312b6609c6ea3302a4e77435d859e9e686999e6699ca39
languageName: node
linkType: hard
@@ -6792,7 +6732,7 @@ __metadata:
languageName: node
linkType: hard
-"inherits@npm:2, inherits@npm:2.0.4, inherits@npm:^2.0.1, inherits@npm:^2.0.3, inherits@npm:^2.0.4, inherits@npm:~2.0.3":
+"inherits@npm:2, inherits@npm:2.0.4, inherits@npm:^2.0.3, inherits@npm:^2.0.4, inherits@npm:~2.0.3":
version: 2.0.4
resolution: "inherits@npm:2.0.4"
checksum: 4a48a733847879d6cf6691860a6b1e3f0f4754176e4d71494c41f3475553768b10f84b5ce1d40fbd0e34e6bfbb864ee35858ad4dd2cf31e02fc4a154b724d7f1
@@ -9633,26 +9573,6 @@ __metadata:
languageName: node
linkType: hard
-"react-native-htmlview@npm:0.16.0":
- version: 0.16.0
- resolution: "react-native-htmlview@npm:0.16.0"
- dependencies:
- entities: ^1.1.1
- htmlparser2-without-node-native: ^3.9.2
- checksum: fb46bc162e41ba9c1222f9386215496f9ac7d4f7f3353b2732101abc57f89d570e9e0881c581bec04d77c2aeaac916b4bd157eedc2098ea2e94b7a29c5c739b1
- languageName: node
- linkType: hard
-
-"react-native-htmlview@patch:react-native-htmlview@npm%3A0.16.0#./.yarn/patches/react-native-htmlview-npm-0.16.0-501f1b89ba.patch::locator=tooot%40workspace%3A.":
- version: 0.16.0
- resolution: "react-native-htmlview@patch:react-native-htmlview@npm%3A0.16.0#./.yarn/patches/react-native-htmlview-npm-0.16.0-501f1b89ba.patch::version=0.16.0&hash=aa9ca8&locator=tooot%40workspace%3A."
- dependencies:
- entities: ^1.1.1
- htmlparser2-without-node-native: ^3.9.2
- checksum: 87e79231315bedf821bc30d342d5bc70ae6fe73b34d535051aba3a5142a40675a9687b37333968194aa9e28a5bdc476f6e12ea921f207ac4b80396615696e81c
- languageName: node
- linkType: hard
-
"react-native-image-picker@npm:^4.10.3":
version: 4.10.3
resolution: "react-native-image-picker@npm:4.10.3"
@@ -9974,7 +9894,7 @@ __metadata:
languageName: node
linkType: hard
-"readable-stream@npm:^2.0.2, readable-stream@npm:^2.0.6, readable-stream@npm:~2.3.6":
+"readable-stream@npm:^2.0.6, readable-stream@npm:~2.3.6":
version: 2.3.7
resolution: "readable-stream@npm:2.3.7"
dependencies:
@@ -11397,6 +11317,7 @@ __metadata:
expo-store-review: ^6.0.0
expo-video-thumbnails: ^7.0.0
expo-web-browser: ~12.0.0
+ htmlparser2: ^8.0.1
i18next: ^22.4.6
linkify-it: ^4.0.1
lodash: ^4.17.21
@@ -11413,7 +11334,6 @@ __metadata:
react-native-feather: ^1.1.2
react-native-flash-message: ^0.3.1
react-native-gesture-handler: ~2.8.0
- react-native-htmlview: ^0.16.0
react-native-image-picker: ^4.10.3
react-native-ios-context-menu: ^1.15.1
react-native-language-detection: ^0.2.2