diff options
Diffstat (limited to 'src')
31 files changed, 617 insertions, 351 deletions
diff --git a/src/lib/build-flags.ts b/src/lib/build-flags.ts index 28b650b6f..faefdd6ab 100644 --- a/src/lib/build-flags.ts +++ b/src/lib/build-flags.ts @@ -1 +1,2 @@ export const LOGIN_INCLUDE_DEV_SERVERS = true +export const PWI_ENABLED = false diff --git a/src/lib/moderation.ts b/src/lib/moderation.ts index 6c08606ee..8ba99128b 100644 --- a/src/lib/moderation.ts +++ b/src/lib/moderation.ts @@ -1,4 +1,4 @@ -import {ModerationCause, ProfileModeration} from '@atproto/api' +import {ModerationCause, ProfileModeration, PostModeration} from '@atproto/api' export interface ModerationCauseDescription { name: string @@ -92,6 +92,25 @@ export function getProfileModerationCauses( }) as ModerationCause[] } +export function isPostMediaBlurred( + decisions: PostModeration['decisions'], +): boolean { + return decisions.post.blurMedia +} + +export function isQuoteBlurred( + decisions: PostModeration['decisions'], +): boolean { + return ( + decisions.quote?.blur || + decisions.quote?.blurMedia || + decisions.quote?.filter || + decisions.quotedAccount?.blur || + decisions.quotedAccount?.filter || + false + ) +} + export function isCauseALabelOnUri( cause: ModerationCause | undefined, uri: string, diff --git a/src/locale/locales/cs/messages.po b/src/locale/locales/cs/messages.po index 6cd60a889..c84625c25 100644 --- a/src/locale/locales/cs/messages.po +++ b/src/locale/locales/cs/messages.po @@ -83,7 +83,7 @@ msgstr "" #: src/view/com/modals/ListAddRemoveUsers.tsx:264 #: src/view/com/modals/UserAddRemoveLists.tsx:187 -#: src/view/screens/ProfileList.tsx:675 +#: src/view/screens/ProfileList.tsx:684 msgid "Add" msgstr "" @@ -91,7 +91,7 @@ msgstr "" msgid "Add a content warning" msgstr "" -#: src/view/screens/ProfileList.tsx:665 +#: src/view/screens/ProfileList.tsx:674 msgid "Add a user to this list" msgstr "" @@ -199,7 +199,7 @@ msgstr "" msgid "Are you sure you'd like to discard this draft?" msgstr "" -#: src/view/screens/ProfileList.tsx:345 +#: src/view/screens/ProfileList.tsx:352 msgid "Are you sure?" msgstr "" @@ -242,11 +242,11 @@ msgstr "" msgid "Block Account" msgstr "" -#: src/view/screens/ProfileList.tsx:446 +#: src/view/screens/ProfileList.tsx:453 msgid "Block accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:302 +#: src/view/screens/ProfileList.tsx:309 msgid "Block these accounts?" msgstr "" @@ -270,7 +270,7 @@ msgstr "" msgid "Blocked post." msgstr "" -#: src/view/screens/ProfileList.tsx:304 +#: src/view/screens/ProfileList.tsx:311 msgid "Blocking is public. Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you." msgstr "" @@ -531,7 +531,7 @@ msgstr "" msgid "Copy" msgstr "" -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Copy link to list" msgstr "" @@ -555,7 +555,7 @@ msgstr "" msgid "Could not load feed" msgstr "" -#: src/view/screens/ProfileList.tsx:752 +#: src/view/screens/ProfileList.tsx:761 msgid "Could not load list" msgstr "" @@ -601,8 +601,8 @@ msgstr "" msgid "Delete app password" msgstr "" -#: src/view/screens/ProfileList.tsx:344 -#: src/view/screens/ProfileList.tsx:402 +#: src/view/screens/ProfileList.tsx:351 +#: src/view/screens/ProfileList.tsx:409 msgid "Delete List" msgstr "" @@ -691,7 +691,7 @@ msgstr "" msgid "Edit image" msgstr "" -#: src/view/screens/ProfileList.tsx:390 +#: src/view/screens/ProfileList.tsx:397 msgid "Edit list details" msgstr "" @@ -739,6 +739,10 @@ msgstr "" msgid "Enable this setting to only see replies between people you follow." msgstr "" +#: src/view/screens/Profile.tsx:454 +msgid "End of feed" +msgstr "" + #: src/view/com/auth/create/Step1.tsx:71 msgid "Enter the address of your provider:" msgstr "" @@ -888,8 +892,8 @@ msgstr "" #: src/view/screens/ProfileFeed.tsx:111 #: src/view/screens/ProfileFeed.tsx:116 -#: src/view/screens/ProfileList.tsx:761 -#: src/view/screens/ProfileList.tsx:766 +#: src/view/screens/ProfileList.tsx:770 +#: src/view/screens/ProfileList.tsx:775 msgid "Go Back" msgstr "" @@ -920,23 +924,23 @@ msgstr "" msgid "Hide user list" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:101 +#: src/view/com/posts/FeedErrorMessage.tsx:102 msgid "Hmm, some kind of issue occured when contacting the feed server. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:89 +#: src/view/com/posts/FeedErrorMessage.tsx:90 msgid "Hmm, the feed server appears to be misconfigured. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:95 +#: src/view/com/posts/FeedErrorMessage.tsx:96 msgid "Hmm, the feed server appears to be offline. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:92 +#: src/view/com/posts/FeedErrorMessage.tsx:93 msgid "Hmm, the feed server gave a bad response. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:86 +#: src/view/com/posts/FeedErrorMessage.tsx:87 msgid "Hmmm, we're having trouble finding this feed. It may have been deleted." msgstr "" @@ -1074,7 +1078,7 @@ msgstr "" #~ msgid "Light" #~ msgstr "" -#: src/view/screens/ProfileFeed.tsx:627 +#: src/view/screens/ProfileFeed.tsx:630 msgid "Like this feed" msgstr "" @@ -1122,7 +1126,7 @@ msgstr "" msgid "Login to account that is not listed" msgstr "" -#: src/view/screens/ProfileFeed.tsx:479 +#: src/view/screens/ProfileFeed.tsx:480 msgid "Looks like this feed is only available to users with a Bluesky account. Please sign up or sign in to view this feed!" msgstr "" @@ -1152,7 +1156,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:520 #: src/view/screens/ProfileFeed.tsx:369 -#: src/view/screens/ProfileList.tsx:506 +#: src/view/screens/ProfileList.tsx:513 msgid "More options" msgstr "" @@ -1164,11 +1168,11 @@ msgstr "" msgid "Mute Account" msgstr "" -#: src/view/screens/ProfileList.tsx:434 +#: src/view/screens/ProfileList.tsx:441 msgid "Mute accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:267 +#: src/view/screens/ProfileList.tsx:274 msgid "Mute these accounts?" msgstr "" @@ -1188,7 +1192,7 @@ msgstr "" msgid "Muted accounts have their posts removed from your feed and from your notifications. Mutes are completely private." msgstr "" -#: src/view/screens/ProfileList.tsx:269 +#: src/view/screens/ProfileList.tsx:276 msgid "Muting is private. Muted accounts can interact with you, but you will not see their posts or receive notifications from them." msgstr "" @@ -1223,10 +1227,10 @@ msgstr "" #: src/view/com/feeds/FeedPage.tsx:188 #: src/view/screens/Feeds.tsx:510 -#: src/view/screens/Profile.tsx:382 -#: src/view/screens/ProfileFeed.tsx:449 -#: src/view/screens/ProfileList.tsx:199 -#: src/view/screens/ProfileList.tsx:231 +#: src/view/screens/Profile.tsx:384 +#: src/view/screens/ProfileFeed.tsx:450 +#: src/view/screens/ProfileList.tsx:206 +#: src/view/screens/ProfileList.tsx:238 #: src/view/shell/desktop/LeftNav.tsx:254 msgid "New post" msgstr "" @@ -1255,8 +1259,8 @@ msgstr "" msgid "No" msgstr "" -#: src/view/screens/ProfileFeed.tsx:620 -#: src/view/screens/ProfileList.tsx:632 +#: src/view/screens/ProfileFeed.tsx:623 +#: src/view/screens/ProfileList.tsx:641 msgid "No description" msgstr "" @@ -1527,7 +1531,7 @@ msgstr "" msgid "Remove account" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:118 +#: src/view/com/posts/FeedErrorMessage.tsx:122 msgid "Remove feed" msgstr "" @@ -1544,7 +1548,7 @@ msgstr "" msgid "Remove image preview" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:119 +#: src/view/com/posts/FeedErrorMessage.tsx:123 msgid "Remove this feed from your saved feeds?" msgstr "" @@ -1569,7 +1573,7 @@ msgstr "" msgid "Report feed" msgstr "" -#: src/view/screens/ProfileList.tsx:416 +#: src/view/screens/ProfileList.tsx:423 msgid "Report List" msgstr "" @@ -1782,7 +1786,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:312 #: src/view/com/util/forms/PostDropdownBtn.tsx:126 -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Share" msgstr "" @@ -1899,11 +1903,11 @@ msgstr "" msgid "Storybook" msgstr "" -#: src/view/screens/ProfileList.tsx:497 +#: src/view/screens/ProfileList.tsx:504 msgid "Subscribe" msgstr "" -#: src/view/screens/ProfileList.tsx:493 +#: src/view/screens/ProfileList.tsx:500 msgid "Subscribe to this list" msgstr "" @@ -2108,7 +2112,7 @@ msgstr "" msgid "Username or email address" msgstr "" -#: src/view/screens/ProfileList.tsx:659 +#: src/view/screens/ProfileList.tsx:668 msgid "Users" msgstr "" @@ -2145,10 +2149,14 @@ msgstr "" msgid "We're so excited to have you join us!" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:98 +#: src/view/com/posts/FeedErrorMessage.tsx:99 msgid "We're sorry, but this content is not viewable without a Bluesky account." msgstr "" +#: src/view/com/posts/FeedErrorMessage.tsx:105 +msgid "We're sorry, but this feed is currently receiving high traffic and is temporarily unavailable. Please try again later." +msgstr "" + #: src/view/screens/Search/Search.tsx:236 msgid "We're sorry, but your search could not be completed. Please try again in a few minutes." msgstr "" diff --git a/src/locale/locales/en/messages.po b/src/locale/locales/en/messages.po index 5e0aec468..330bec614 100644 --- a/src/locale/locales/en/messages.po +++ b/src/locale/locales/en/messages.po @@ -83,7 +83,7 @@ msgstr "" #: src/view/com/modals/ListAddRemoveUsers.tsx:264 #: src/view/com/modals/UserAddRemoveLists.tsx:187 -#: src/view/screens/ProfileList.tsx:675 +#: src/view/screens/ProfileList.tsx:684 msgid "Add" msgstr "" @@ -91,7 +91,7 @@ msgstr "" msgid "Add a content warning" msgstr "" -#: src/view/screens/ProfileList.tsx:665 +#: src/view/screens/ProfileList.tsx:674 msgid "Add a user to this list" msgstr "" @@ -199,7 +199,7 @@ msgstr "" msgid "Are you sure you'd like to discard this draft?" msgstr "" -#: src/view/screens/ProfileList.tsx:345 +#: src/view/screens/ProfileList.tsx:352 msgid "Are you sure?" msgstr "" @@ -242,11 +242,11 @@ msgstr "" msgid "Block Account" msgstr "" -#: src/view/screens/ProfileList.tsx:446 +#: src/view/screens/ProfileList.tsx:453 msgid "Block accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:302 +#: src/view/screens/ProfileList.tsx:309 msgid "Block these accounts?" msgstr "" @@ -270,7 +270,7 @@ msgstr "" msgid "Blocked post." msgstr "" -#: src/view/screens/ProfileList.tsx:304 +#: src/view/screens/ProfileList.tsx:311 msgid "Blocking is public. Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you." msgstr "" @@ -531,7 +531,7 @@ msgstr "" msgid "Copy" msgstr "" -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Copy link to list" msgstr "" @@ -555,7 +555,7 @@ msgstr "" msgid "Could not load feed" msgstr "" -#: src/view/screens/ProfileList.tsx:752 +#: src/view/screens/ProfileList.tsx:761 msgid "Could not load list" msgstr "" @@ -601,8 +601,8 @@ msgstr "" msgid "Delete app password" msgstr "" -#: src/view/screens/ProfileList.tsx:344 -#: src/view/screens/ProfileList.tsx:402 +#: src/view/screens/ProfileList.tsx:351 +#: src/view/screens/ProfileList.tsx:409 msgid "Delete List" msgstr "" @@ -691,7 +691,7 @@ msgstr "" msgid "Edit image" msgstr "" -#: src/view/screens/ProfileList.tsx:390 +#: src/view/screens/ProfileList.tsx:397 msgid "Edit list details" msgstr "" @@ -739,6 +739,10 @@ msgstr "" msgid "Enable this setting to only see replies between people you follow." msgstr "" +#: src/view/screens/Profile.tsx:454 +msgid "End of feed" +msgstr "" + #: src/view/com/auth/create/Step1.tsx:71 msgid "Enter the address of your provider:" msgstr "" @@ -888,8 +892,8 @@ msgstr "" #: src/view/screens/ProfileFeed.tsx:111 #: src/view/screens/ProfileFeed.tsx:116 -#: src/view/screens/ProfileList.tsx:761 -#: src/view/screens/ProfileList.tsx:766 +#: src/view/screens/ProfileList.tsx:770 +#: src/view/screens/ProfileList.tsx:775 msgid "Go Back" msgstr "" @@ -920,23 +924,23 @@ msgstr "" msgid "Hide user list" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:101 +#: src/view/com/posts/FeedErrorMessage.tsx:102 msgid "Hmm, some kind of issue occured when contacting the feed server. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:89 +#: src/view/com/posts/FeedErrorMessage.tsx:90 msgid "Hmm, the feed server appears to be misconfigured. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:95 +#: src/view/com/posts/FeedErrorMessage.tsx:96 msgid "Hmm, the feed server appears to be offline. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:92 +#: src/view/com/posts/FeedErrorMessage.tsx:93 msgid "Hmm, the feed server gave a bad response. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:86 +#: src/view/com/posts/FeedErrorMessage.tsx:87 msgid "Hmmm, we're having trouble finding this feed. It may have been deleted." msgstr "" @@ -1074,7 +1078,7 @@ msgstr "" #~ msgid "Light" #~ msgstr "" -#: src/view/screens/ProfileFeed.tsx:627 +#: src/view/screens/ProfileFeed.tsx:630 msgid "Like this feed" msgstr "" @@ -1122,7 +1126,7 @@ msgstr "" msgid "Login to account that is not listed" msgstr "" -#: src/view/screens/ProfileFeed.tsx:479 +#: src/view/screens/ProfileFeed.tsx:480 msgid "Looks like this feed is only available to users with a Bluesky account. Please sign up or sign in to view this feed!" msgstr "" @@ -1152,7 +1156,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:520 #: src/view/screens/ProfileFeed.tsx:369 -#: src/view/screens/ProfileList.tsx:506 +#: src/view/screens/ProfileList.tsx:513 msgid "More options" msgstr "" @@ -1164,11 +1168,11 @@ msgstr "" msgid "Mute Account" msgstr "" -#: src/view/screens/ProfileList.tsx:434 +#: src/view/screens/ProfileList.tsx:441 msgid "Mute accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:267 +#: src/view/screens/ProfileList.tsx:274 msgid "Mute these accounts?" msgstr "" @@ -1188,7 +1192,7 @@ msgstr "" msgid "Muted accounts have their posts removed from your feed and from your notifications. Mutes are completely private." msgstr "" -#: src/view/screens/ProfileList.tsx:269 +#: src/view/screens/ProfileList.tsx:276 msgid "Muting is private. Muted accounts can interact with you, but you will not see their posts or receive notifications from them." msgstr "" @@ -1223,10 +1227,10 @@ msgstr "" #: src/view/com/feeds/FeedPage.tsx:188 #: src/view/screens/Feeds.tsx:510 -#: src/view/screens/Profile.tsx:382 -#: src/view/screens/ProfileFeed.tsx:449 -#: src/view/screens/ProfileList.tsx:199 -#: src/view/screens/ProfileList.tsx:231 +#: src/view/screens/Profile.tsx:384 +#: src/view/screens/ProfileFeed.tsx:450 +#: src/view/screens/ProfileList.tsx:206 +#: src/view/screens/ProfileList.tsx:238 #: src/view/shell/desktop/LeftNav.tsx:254 msgid "New post" msgstr "" @@ -1255,8 +1259,8 @@ msgstr "" msgid "No" msgstr "" -#: src/view/screens/ProfileFeed.tsx:620 -#: src/view/screens/ProfileList.tsx:632 +#: src/view/screens/ProfileFeed.tsx:623 +#: src/view/screens/ProfileList.tsx:641 msgid "No description" msgstr "" @@ -1527,7 +1531,7 @@ msgstr "" msgid "Remove account" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:118 +#: src/view/com/posts/FeedErrorMessage.tsx:122 msgid "Remove feed" msgstr "" @@ -1544,7 +1548,7 @@ msgstr "" msgid "Remove image preview" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:119 +#: src/view/com/posts/FeedErrorMessage.tsx:123 msgid "Remove this feed from your saved feeds?" msgstr "" @@ -1569,7 +1573,7 @@ msgstr "" msgid "Report feed" msgstr "" -#: src/view/screens/ProfileList.tsx:416 +#: src/view/screens/ProfileList.tsx:423 msgid "Report List" msgstr "" @@ -1782,7 +1786,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:312 #: src/view/com/util/forms/PostDropdownBtn.tsx:126 -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Share" msgstr "" @@ -1899,11 +1903,11 @@ msgstr "" msgid "Storybook" msgstr "" -#: src/view/screens/ProfileList.tsx:497 +#: src/view/screens/ProfileList.tsx:504 msgid "Subscribe" msgstr "" -#: src/view/screens/ProfileList.tsx:493 +#: src/view/screens/ProfileList.tsx:500 msgid "Subscribe to this list" msgstr "" @@ -2108,7 +2112,7 @@ msgstr "" msgid "Username or email address" msgstr "" -#: src/view/screens/ProfileList.tsx:659 +#: src/view/screens/ProfileList.tsx:668 msgid "Users" msgstr "" @@ -2145,10 +2149,14 @@ msgstr "" msgid "We're so excited to have you join us!" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:98 +#: src/view/com/posts/FeedErrorMessage.tsx:99 msgid "We're sorry, but this content is not viewable without a Bluesky account." msgstr "" +#: src/view/com/posts/FeedErrorMessage.tsx:105 +msgid "We're sorry, but this feed is currently receiving high traffic and is temporarily unavailable. Please try again later." +msgstr "" + #: src/view/screens/Search/Search.tsx:236 msgid "We're sorry, but your search could not be completed. Please try again in a few minutes." msgstr "" diff --git a/src/locale/locales/es/messages.po b/src/locale/locales/es/messages.po index baab22c72..ae43a7323 100644 --- a/src/locale/locales/es/messages.po +++ b/src/locale/locales/es/messages.po @@ -83,7 +83,7 @@ msgstr "" #: src/view/com/modals/ListAddRemoveUsers.tsx:264 #: src/view/com/modals/UserAddRemoveLists.tsx:187 -#: src/view/screens/ProfileList.tsx:675 +#: src/view/screens/ProfileList.tsx:684 msgid "Add" msgstr "" @@ -91,7 +91,7 @@ msgstr "" msgid "Add a content warning" msgstr "" -#: src/view/screens/ProfileList.tsx:665 +#: src/view/screens/ProfileList.tsx:674 msgid "Add a user to this list" msgstr "" @@ -199,7 +199,7 @@ msgstr "" msgid "Are you sure you'd like to discard this draft?" msgstr "" -#: src/view/screens/ProfileList.tsx:345 +#: src/view/screens/ProfileList.tsx:352 msgid "Are you sure?" msgstr "" @@ -242,11 +242,11 @@ msgstr "" msgid "Block Account" msgstr "" -#: src/view/screens/ProfileList.tsx:446 +#: src/view/screens/ProfileList.tsx:453 msgid "Block accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:302 +#: src/view/screens/ProfileList.tsx:309 msgid "Block these accounts?" msgstr "" @@ -270,7 +270,7 @@ msgstr "" msgid "Blocked post." msgstr "" -#: src/view/screens/ProfileList.tsx:304 +#: src/view/screens/ProfileList.tsx:311 msgid "Blocking is public. Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you." msgstr "" @@ -531,7 +531,7 @@ msgstr "" msgid "Copy" msgstr "" -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Copy link to list" msgstr "" @@ -555,7 +555,7 @@ msgstr "" msgid "Could not load feed" msgstr "" -#: src/view/screens/ProfileList.tsx:752 +#: src/view/screens/ProfileList.tsx:761 msgid "Could not load list" msgstr "" @@ -601,8 +601,8 @@ msgstr "" msgid "Delete app password" msgstr "" -#: src/view/screens/ProfileList.tsx:344 -#: src/view/screens/ProfileList.tsx:402 +#: src/view/screens/ProfileList.tsx:351 +#: src/view/screens/ProfileList.tsx:409 msgid "Delete List" msgstr "" @@ -691,7 +691,7 @@ msgstr "" msgid "Edit image" msgstr "" -#: src/view/screens/ProfileList.tsx:390 +#: src/view/screens/ProfileList.tsx:397 msgid "Edit list details" msgstr "" @@ -739,6 +739,10 @@ msgstr "" msgid "Enable this setting to only see replies between people you follow." msgstr "" +#: src/view/screens/Profile.tsx:454 +msgid "End of feed" +msgstr "" + #: src/view/com/auth/create/Step1.tsx:71 msgid "Enter the address of your provider:" msgstr "" @@ -888,8 +892,8 @@ msgstr "" #: src/view/screens/ProfileFeed.tsx:111 #: src/view/screens/ProfileFeed.tsx:116 -#: src/view/screens/ProfileList.tsx:761 -#: src/view/screens/ProfileList.tsx:766 +#: src/view/screens/ProfileList.tsx:770 +#: src/view/screens/ProfileList.tsx:775 msgid "Go Back" msgstr "" @@ -920,23 +924,23 @@ msgstr "" msgid "Hide user list" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:101 +#: src/view/com/posts/FeedErrorMessage.tsx:102 msgid "Hmm, some kind of issue occured when contacting the feed server. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:89 +#: src/view/com/posts/FeedErrorMessage.tsx:90 msgid "Hmm, the feed server appears to be misconfigured. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:95 +#: src/view/com/posts/FeedErrorMessage.tsx:96 msgid "Hmm, the feed server appears to be offline. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:92 +#: src/view/com/posts/FeedErrorMessage.tsx:93 msgid "Hmm, the feed server gave a bad response. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:86 +#: src/view/com/posts/FeedErrorMessage.tsx:87 msgid "Hmmm, we're having trouble finding this feed. It may have been deleted." msgstr "" @@ -1074,7 +1078,7 @@ msgstr "" #~ msgid "Light" #~ msgstr "" -#: src/view/screens/ProfileFeed.tsx:627 +#: src/view/screens/ProfileFeed.tsx:630 msgid "Like this feed" msgstr "" @@ -1122,7 +1126,7 @@ msgstr "" msgid "Login to account that is not listed" msgstr "" -#: src/view/screens/ProfileFeed.tsx:479 +#: src/view/screens/ProfileFeed.tsx:480 msgid "Looks like this feed is only available to users with a Bluesky account. Please sign up or sign in to view this feed!" msgstr "" @@ -1152,7 +1156,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:520 #: src/view/screens/ProfileFeed.tsx:369 -#: src/view/screens/ProfileList.tsx:506 +#: src/view/screens/ProfileList.tsx:513 msgid "More options" msgstr "" @@ -1164,11 +1168,11 @@ msgstr "" msgid "Mute Account" msgstr "" -#: src/view/screens/ProfileList.tsx:434 +#: src/view/screens/ProfileList.tsx:441 msgid "Mute accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:267 +#: src/view/screens/ProfileList.tsx:274 msgid "Mute these accounts?" msgstr "" @@ -1188,7 +1192,7 @@ msgstr "" msgid "Muted accounts have their posts removed from your feed and from your notifications. Mutes are completely private." msgstr "" -#: src/view/screens/ProfileList.tsx:269 +#: src/view/screens/ProfileList.tsx:276 msgid "Muting is private. Muted accounts can interact with you, but you will not see their posts or receive notifications from them." msgstr "" @@ -1223,10 +1227,10 @@ msgstr "" #: src/view/com/feeds/FeedPage.tsx:188 #: src/view/screens/Feeds.tsx:510 -#: src/view/screens/Profile.tsx:382 -#: src/view/screens/ProfileFeed.tsx:449 -#: src/view/screens/ProfileList.tsx:199 -#: src/view/screens/ProfileList.tsx:231 +#: src/view/screens/Profile.tsx:384 +#: src/view/screens/ProfileFeed.tsx:450 +#: src/view/screens/ProfileList.tsx:206 +#: src/view/screens/ProfileList.tsx:238 #: src/view/shell/desktop/LeftNav.tsx:254 msgid "New post" msgstr "" @@ -1255,8 +1259,8 @@ msgstr "" msgid "No" msgstr "" -#: src/view/screens/ProfileFeed.tsx:620 -#: src/view/screens/ProfileList.tsx:632 +#: src/view/screens/ProfileFeed.tsx:623 +#: src/view/screens/ProfileList.tsx:641 msgid "No description" msgstr "" @@ -1527,7 +1531,7 @@ msgstr "" msgid "Remove account" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:118 +#: src/view/com/posts/FeedErrorMessage.tsx:122 msgid "Remove feed" msgstr "" @@ -1544,7 +1548,7 @@ msgstr "" msgid "Remove image preview" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:119 +#: src/view/com/posts/FeedErrorMessage.tsx:123 msgid "Remove this feed from your saved feeds?" msgstr "" @@ -1569,7 +1573,7 @@ msgstr "" msgid "Report feed" msgstr "" -#: src/view/screens/ProfileList.tsx:416 +#: src/view/screens/ProfileList.tsx:423 msgid "Report List" msgstr "" @@ -1782,7 +1786,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:312 #: src/view/com/util/forms/PostDropdownBtn.tsx:126 -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Share" msgstr "" @@ -1899,11 +1903,11 @@ msgstr "" msgid "Storybook" msgstr "" -#: src/view/screens/ProfileList.tsx:497 +#: src/view/screens/ProfileList.tsx:504 msgid "Subscribe" msgstr "" -#: src/view/screens/ProfileList.tsx:493 +#: src/view/screens/ProfileList.tsx:500 msgid "Subscribe to this list" msgstr "" @@ -2108,7 +2112,7 @@ msgstr "" msgid "Username or email address" msgstr "" -#: src/view/screens/ProfileList.tsx:659 +#: src/view/screens/ProfileList.tsx:668 msgid "Users" msgstr "" @@ -2145,10 +2149,14 @@ msgstr "" msgid "We're so excited to have you join us!" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:98 +#: src/view/com/posts/FeedErrorMessage.tsx:99 msgid "We're sorry, but this content is not viewable without a Bluesky account." msgstr "" +#: src/view/com/posts/FeedErrorMessage.tsx:105 +msgid "We're sorry, but this feed is currently receiving high traffic and is temporarily unavailable. Please try again later." +msgstr "" + #: src/view/screens/Search/Search.tsx:236 msgid "We're sorry, but your search could not be completed. Please try again in a few minutes." msgstr "" diff --git a/src/locale/locales/fr/messages.po b/src/locale/locales/fr/messages.po index 95b10a094..4c5351c89 100644 --- a/src/locale/locales/fr/messages.po +++ b/src/locale/locales/fr/messages.po @@ -83,7 +83,7 @@ msgstr "" #: src/view/com/modals/ListAddRemoveUsers.tsx:264 #: src/view/com/modals/UserAddRemoveLists.tsx:187 -#: src/view/screens/ProfileList.tsx:675 +#: src/view/screens/ProfileList.tsx:684 msgid "Add" msgstr "" @@ -91,7 +91,7 @@ msgstr "" msgid "Add a content warning" msgstr "" -#: src/view/screens/ProfileList.tsx:665 +#: src/view/screens/ProfileList.tsx:674 msgid "Add a user to this list" msgstr "" @@ -199,7 +199,7 @@ msgstr "" msgid "Are you sure you'd like to discard this draft?" msgstr "" -#: src/view/screens/ProfileList.tsx:345 +#: src/view/screens/ProfileList.tsx:352 msgid "Are you sure?" msgstr "" @@ -242,11 +242,11 @@ msgstr "" msgid "Block Account" msgstr "" -#: src/view/screens/ProfileList.tsx:446 +#: src/view/screens/ProfileList.tsx:453 msgid "Block accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:302 +#: src/view/screens/ProfileList.tsx:309 msgid "Block these accounts?" msgstr "" @@ -270,7 +270,7 @@ msgstr "" msgid "Blocked post." msgstr "" -#: src/view/screens/ProfileList.tsx:304 +#: src/view/screens/ProfileList.tsx:311 msgid "Blocking is public. Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you." msgstr "" @@ -531,7 +531,7 @@ msgstr "" msgid "Copy" msgstr "" -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Copy link to list" msgstr "" @@ -555,7 +555,7 @@ msgstr "" msgid "Could not load feed" msgstr "" -#: src/view/screens/ProfileList.tsx:752 +#: src/view/screens/ProfileList.tsx:761 msgid "Could not load list" msgstr "" @@ -601,8 +601,8 @@ msgstr "" msgid "Delete app password" msgstr "" -#: src/view/screens/ProfileList.tsx:344 -#: src/view/screens/ProfileList.tsx:402 +#: src/view/screens/ProfileList.tsx:351 +#: src/view/screens/ProfileList.tsx:409 msgid "Delete List" msgstr "" @@ -691,7 +691,7 @@ msgstr "" msgid "Edit image" msgstr "" -#: src/view/screens/ProfileList.tsx:390 +#: src/view/screens/ProfileList.tsx:397 msgid "Edit list details" msgstr "" @@ -739,6 +739,10 @@ msgstr "" msgid "Enable this setting to only see replies between people you follow." msgstr "" +#: src/view/screens/Profile.tsx:454 +msgid "End of feed" +msgstr "" + #: src/view/com/auth/create/Step1.tsx:71 msgid "Enter the address of your provider:" msgstr "" @@ -888,8 +892,8 @@ msgstr "" #: src/view/screens/ProfileFeed.tsx:111 #: src/view/screens/ProfileFeed.tsx:116 -#: src/view/screens/ProfileList.tsx:761 -#: src/view/screens/ProfileList.tsx:766 +#: src/view/screens/ProfileList.tsx:770 +#: src/view/screens/ProfileList.tsx:775 msgid "Go Back" msgstr "" @@ -920,23 +924,23 @@ msgstr "" msgid "Hide user list" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:101 +#: src/view/com/posts/FeedErrorMessage.tsx:102 msgid "Hmm, some kind of issue occured when contacting the feed server. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:89 +#: src/view/com/posts/FeedErrorMessage.tsx:90 msgid "Hmm, the feed server appears to be misconfigured. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:95 +#: src/view/com/posts/FeedErrorMessage.tsx:96 msgid "Hmm, the feed server appears to be offline. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:92 +#: src/view/com/posts/FeedErrorMessage.tsx:93 msgid "Hmm, the feed server gave a bad response. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:86 +#: src/view/com/posts/FeedErrorMessage.tsx:87 msgid "Hmmm, we're having trouble finding this feed. It may have been deleted." msgstr "" @@ -1074,7 +1078,7 @@ msgstr "" #~ msgid "Light" #~ msgstr "" -#: src/view/screens/ProfileFeed.tsx:627 +#: src/view/screens/ProfileFeed.tsx:630 msgid "Like this feed" msgstr "" @@ -1122,7 +1126,7 @@ msgstr "" msgid "Login to account that is not listed" msgstr "" -#: src/view/screens/ProfileFeed.tsx:479 +#: src/view/screens/ProfileFeed.tsx:480 msgid "Looks like this feed is only available to users with a Bluesky account. Please sign up or sign in to view this feed!" msgstr "" @@ -1152,7 +1156,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:520 #: src/view/screens/ProfileFeed.tsx:369 -#: src/view/screens/ProfileList.tsx:506 +#: src/view/screens/ProfileList.tsx:513 msgid "More options" msgstr "" @@ -1164,11 +1168,11 @@ msgstr "" msgid "Mute Account" msgstr "" -#: src/view/screens/ProfileList.tsx:434 +#: src/view/screens/ProfileList.tsx:441 msgid "Mute accounts" msgstr "" -#: src/view/screens/ProfileList.tsx:267 +#: src/view/screens/ProfileList.tsx:274 msgid "Mute these accounts?" msgstr "" @@ -1188,7 +1192,7 @@ msgstr "" msgid "Muted accounts have their posts removed from your feed and from your notifications. Mutes are completely private." msgstr "" -#: src/view/screens/ProfileList.tsx:269 +#: src/view/screens/ProfileList.tsx:276 msgid "Muting is private. Muted accounts can interact with you, but you will not see their posts or receive notifications from them." msgstr "" @@ -1223,10 +1227,10 @@ msgstr "" #: src/view/com/feeds/FeedPage.tsx:188 #: src/view/screens/Feeds.tsx:510 -#: src/view/screens/Profile.tsx:382 -#: src/view/screens/ProfileFeed.tsx:449 -#: src/view/screens/ProfileList.tsx:199 -#: src/view/screens/ProfileList.tsx:231 +#: src/view/screens/Profile.tsx:384 +#: src/view/screens/ProfileFeed.tsx:450 +#: src/view/screens/ProfileList.tsx:206 +#: src/view/screens/ProfileList.tsx:238 #: src/view/shell/desktop/LeftNav.tsx:254 msgid "New post" msgstr "" @@ -1255,8 +1259,8 @@ msgstr "" msgid "No" msgstr "" -#: src/view/screens/ProfileFeed.tsx:620 -#: src/view/screens/ProfileList.tsx:632 +#: src/view/screens/ProfileFeed.tsx:623 +#: src/view/screens/ProfileList.tsx:641 msgid "No description" msgstr "" @@ -1527,7 +1531,7 @@ msgstr "" msgid "Remove account" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:118 +#: src/view/com/posts/FeedErrorMessage.tsx:122 msgid "Remove feed" msgstr "" @@ -1544,7 +1548,7 @@ msgstr "" msgid "Remove image preview" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:119 +#: src/view/com/posts/FeedErrorMessage.tsx:123 msgid "Remove this feed from your saved feeds?" msgstr "" @@ -1569,7 +1573,7 @@ msgstr "" msgid "Report feed" msgstr "" -#: src/view/screens/ProfileList.tsx:416 +#: src/view/screens/ProfileList.tsx:423 msgid "Report List" msgstr "" @@ -1782,7 +1786,7 @@ msgstr "" #: src/view/com/profile/ProfileHeader.tsx:312 #: src/view/com/util/forms/PostDropdownBtn.tsx:126 -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Share" msgstr "" @@ -1899,11 +1903,11 @@ msgstr "" msgid "Storybook" msgstr "" -#: src/view/screens/ProfileList.tsx:497 +#: src/view/screens/ProfileList.tsx:504 msgid "Subscribe" msgstr "" -#: src/view/screens/ProfileList.tsx:493 +#: src/view/screens/ProfileList.tsx:500 msgid "Subscribe to this list" msgstr "" @@ -2108,7 +2112,7 @@ msgstr "" msgid "Username or email address" msgstr "" -#: src/view/screens/ProfileList.tsx:659 +#: src/view/screens/ProfileList.tsx:668 msgid "Users" msgstr "" @@ -2145,10 +2149,14 @@ msgstr "" msgid "We're so excited to have you join us!" msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:98 +#: src/view/com/posts/FeedErrorMessage.tsx:99 msgid "We're sorry, but this content is not viewable without a Bluesky account." msgstr "" +#: src/view/com/posts/FeedErrorMessage.tsx:105 +msgid "We're sorry, but this feed is currently receiving high traffic and is temporarily unavailable. Please try again later." +msgstr "" + #: src/view/screens/Search/Search.tsx:236 msgid "We're sorry, but your search could not be completed. Please try again in a few minutes." msgstr "" diff --git a/src/locale/locales/hi/messages.po b/src/locale/locales/hi/messages.po index e442483db..9e85e0a5c 100644 --- a/src/locale/locales/hi/messages.po +++ b/src/locale/locales/hi/messages.po @@ -83,7 +83,7 @@ msgstr "अकाउंट के विकलà¥à¤ª" #: src/view/com/modals/ListAddRemoveUsers.tsx:264 #: src/view/com/modals/UserAddRemoveLists.tsx:187 -#: src/view/screens/ProfileList.tsx:675 +#: src/view/screens/ProfileList.tsx:684 msgid "Add" msgstr "à¤à¤¡ करो" @@ -91,7 +91,7 @@ msgstr "à¤à¤¡ करो" msgid "Add a content warning" msgstr "सामगà¥à¤°à¥€ चेतावनी जोड़ें" -#: src/view/screens/ProfileList.tsx:665 +#: src/view/screens/ProfileList.tsx:674 msgid "Add a user to this list" msgstr "इस सूची में किसी को जोड़ें" @@ -199,7 +199,7 @@ msgstr "कà¥à¤¯à¤¾ आप वाकई à¤à¤ª पासवरà¥à¤¡ \"{name}\" msgid "Are you sure you'd like to discard this draft?" msgstr "कà¥à¤¯à¤¾ आप वाकई इस डà¥à¤°à¤¾à¤«à¥à¤Ÿ को हटाना करना चाहेंगे?" -#: src/view/screens/ProfileList.tsx:345 +#: src/view/screens/ProfileList.tsx:352 msgid "Are you sure?" msgstr "कà¥à¤¯à¤¾ आप वासà¥à¤¤à¤µ में इसे करना चाहते हैं?" @@ -242,11 +242,11 @@ msgstr "जनà¥à¤®à¤¦à¤¿à¤¨:" msgid "Block Account" msgstr "खाता बà¥à¤²à¥‰à¤• करें" -#: src/view/screens/ProfileList.tsx:446 +#: src/view/screens/ProfileList.tsx:453 msgid "Block accounts" msgstr "खाता बà¥à¤²à¥‰à¤• करें" -#: src/view/screens/ProfileList.tsx:302 +#: src/view/screens/ProfileList.tsx:309 msgid "Block these accounts?" msgstr "खाता बà¥à¤²à¥‰à¤• करें?" @@ -270,7 +270,7 @@ msgstr "अवरà¥à¤¦à¥à¤§ खाते आपके थà¥à¤°à¥‡à¤¡à¥à¤¸ ठmsgid "Blocked post." msgstr "बà¥à¤²à¥‰à¤• पोसà¥à¤Ÿà¥¤" -#: src/view/screens/ProfileList.tsx:304 +#: src/view/screens/ProfileList.tsx:311 msgid "Blocking is public. Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you." msgstr "अवरोधन सारà¥à¤µà¤œà¤¨à¤¿à¤• है. अवरà¥à¤¦à¥à¤§ खाते आपके थà¥à¤°à¥‡à¤¡à¥à¤¸ में उतà¥à¤¤à¤° नहीं दे सकते, आपका उलà¥à¤²à¥‡à¤– नहीं कर सकते, या अनà¥à¤¯à¤¥à¤¾ आपके साथ बातचीत नहीं कर सकते।" @@ -527,7 +527,7 @@ msgstr "कॉपी कर ली" msgid "Copy" msgstr "कॉपी" -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Copy link to list" msgstr "" @@ -551,7 +551,7 @@ msgstr "कॉपीराइट नीति" msgid "Could not load feed" msgstr "फ़ीड लोड नहीं कर सकता" -#: src/view/screens/ProfileList.tsx:752 +#: src/view/screens/ProfileList.tsx:761 msgid "Could not load list" msgstr "सूची लोड नहीं कर सकता" @@ -597,8 +597,8 @@ msgstr "खाता हटाà¤à¤‚" msgid "Delete app password" msgstr "अपà¥à¤ª पासवरà¥à¤¡ हटाà¤à¤‚" -#: src/view/screens/ProfileList.tsx:344 -#: src/view/screens/ProfileList.tsx:402 +#: src/view/screens/ProfileList.tsx:351 +#: src/view/screens/ProfileList.tsx:409 msgid "Delete List" msgstr "सूची हटाà¤à¤" @@ -687,7 +687,7 @@ msgstr "पà¥à¤°à¤¤à¥à¤¯à¥‡à¤• कोड à¤à¤• बार काम करतà msgid "Edit image" msgstr "छवि संपादित करें" -#: src/view/screens/ProfileList.tsx:390 +#: src/view/screens/ProfileList.tsx:397 msgid "Edit list details" msgstr "सूची विवरण संपादित करें" @@ -735,6 +735,10 @@ msgstr "ईमेल:" msgid "Enable this setting to only see replies between people you follow." msgstr "इस सेटिंग को केवल उन लोगों के बीच जवाब देखने में सकà¥à¤·à¤® करें जिनà¥à¤¹à¥‡à¤‚ आप फॉलो करते हैं।।" +#: src/view/screens/Profile.tsx:454 +msgid "End of feed" +msgstr "" + #: src/view/com/auth/create/Step1.tsx:71 msgid "Enter the address of your provider:" msgstr "अपने पà¥à¤°à¤¦à¤¾à¤¤à¤¾ का पता दरà¥à¤œ करें:" @@ -880,8 +884,8 @@ msgstr "वापस जाओ" #: src/view/screens/ProfileFeed.tsx:111 #: src/view/screens/ProfileFeed.tsx:116 -#: src/view/screens/ProfileList.tsx:761 -#: src/view/screens/ProfileList.tsx:766 +#: src/view/screens/ProfileList.tsx:770 +#: src/view/screens/ProfileList.tsx:775 msgid "Go Back" msgstr "वापस जाओ" @@ -912,23 +916,23 @@ msgstr "इसे छिपाà¤à¤‚" msgid "Hide user list" msgstr "उपयोगकरà¥à¤¤à¤¾ सूची छà¥à¤ªà¤¾à¤à¤" -#: src/view/com/posts/FeedErrorMessage.tsx:101 +#: src/view/com/posts/FeedErrorMessage.tsx:102 msgid "Hmm, some kind of issue occured when contacting the feed server. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:89 +#: src/view/com/posts/FeedErrorMessage.tsx:90 msgid "Hmm, the feed server appears to be misconfigured. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:95 +#: src/view/com/posts/FeedErrorMessage.tsx:96 msgid "Hmm, the feed server appears to be offline. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:92 +#: src/view/com/posts/FeedErrorMessage.tsx:93 msgid "Hmm, the feed server gave a bad response. Please let the feed owner know about this issue." msgstr "" -#: src/view/com/posts/FeedErrorMessage.tsx:86 +#: src/view/com/posts/FeedErrorMessage.tsx:87 msgid "Hmmm, we're having trouble finding this feed. It may have been deleted." msgstr "" @@ -1066,7 +1070,7 @@ msgstr "चितà¥à¤° पà¥à¤¸à¥à¤¤à¤•ालय" #~ msgid "Light" #~ msgstr "लाइट मोड" -#: src/view/screens/ProfileFeed.tsx:627 +#: src/view/screens/ProfileFeed.tsx:630 msgid "Like this feed" msgstr "इस फ़ीड को लाइक करो" @@ -1114,7 +1118,7 @@ msgstr "सà¥à¤¥à¤¾à¤¨à¥€à¤¯ देव सरà¥à¤µà¤°" msgid "Login to account that is not listed" msgstr "उस खाते में लॉग इन करें जो सूचीबदà¥à¤§ नहीं है" -#: src/view/screens/ProfileFeed.tsx:479 +#: src/view/screens/ProfileFeed.tsx:480 msgid "Looks like this feed is only available to users with a Bluesky account. Please sign up or sign in to view this feed!" msgstr "" @@ -1144,7 +1148,7 @@ msgstr "अधिक फ़ीड" #: src/view/com/profile/ProfileHeader.tsx:520 #: src/view/screens/ProfileFeed.tsx:369 -#: src/view/screens/ProfileList.tsx:506 +#: src/view/screens/ProfileList.tsx:513 msgid "More options" msgstr "अधिक विकलà¥à¤ª" @@ -1156,11 +1160,11 @@ msgstr "अधिक विकलà¥à¤ª" msgid "Mute Account" msgstr "खाता मà¥à¤¯à¥‚ट करें" -#: src/view/screens/ProfileList.tsx:434 +#: src/view/screens/ProfileList.tsx:441 msgid "Mute accounts" msgstr "खातों को मà¥à¤¯à¥‚ट करें" -#: src/view/screens/ProfileList.tsx:267 +#: src/view/screens/ProfileList.tsx:274 msgid "Mute these accounts?" msgstr "इन खातों को मà¥à¤¯à¥‚ट करें?" @@ -1180,7 +1184,7 @@ msgstr "मà¥à¤¯à¥‚ट किठगठखाते" msgid "Muted accounts have their posts removed from your feed and from your notifications. Mutes are completely private." msgstr "मà¥à¤¯à¥‚ट किठगठखातों की पोसà¥à¤Ÿ आपके फ़ीड और आपकी सूचनाओं से हटा दी जाती हैं। मà¥à¤¯à¥‚ट पूरी तरह से निजी हैं." -#: src/view/screens/ProfileList.tsx:269 +#: src/view/screens/ProfileList.tsx:276 msgid "Muting is private. Muted accounts can interact with you, but you will not see their posts or receive notifications from them." msgstr "मà¥à¤¯à¥‚ट करना निजी है. मà¥à¤¯à¥‚ट किठगठखाते आपके साथ इंटरैकà¥à¤Ÿ कर सकते हैं, लेकिन आप उनकी पोसà¥à¤Ÿ नहीं देखेंगे या उनसे सूचनाà¤à¤‚ पà¥à¤°à¤¾à¤ªà¥à¤¤ नहीं करेंगे।" @@ -1215,10 +1219,10 @@ msgstr "नया" #: src/view/com/feeds/FeedPage.tsx:188 #: src/view/screens/Feeds.tsx:510 -#: src/view/screens/Profile.tsx:382 -#: src/view/screens/ProfileFeed.tsx:449 -#: src/view/screens/ProfileList.tsx:199 -#: src/view/screens/ProfileList.tsx:231 +#: src/view/screens/Profile.tsx:384 +#: src/view/screens/ProfileFeed.tsx:450 +#: src/view/screens/ProfileList.tsx:206 +#: src/view/screens/ProfileList.tsx:238 #: src/view/shell/desktop/LeftNav.tsx:254 msgid "New post" msgstr "नई पोसà¥à¤Ÿ" @@ -1247,8 +1251,8 @@ msgstr "अगली फोटो" msgid "No" msgstr "नहीं" -#: src/view/screens/ProfileFeed.tsx:620 -#: src/view/screens/ProfileList.tsx:632 +#: src/view/screens/ProfileFeed.tsx:623 +#: src/view/screens/ProfileList.tsx:641 msgid "No description" msgstr "कोई विवरण नहीं" @@ -1519,7 +1523,7 @@ msgstr "मेरे फ़ीड से {0} हटाà¤à¤‚?" msgid "Remove account" msgstr "खाता हटाà¤à¤‚" -#: src/view/com/posts/FeedErrorMessage.tsx:118 +#: src/view/com/posts/FeedErrorMessage.tsx:122 msgid "Remove feed" msgstr "फ़ीड हटाà¤à¤" @@ -1536,7 +1540,7 @@ msgstr "छवि निकालें" msgid "Remove image preview" msgstr "छवि पूरà¥à¤µà¤¾à¤µà¤²à¥‹à¤•न निकालें" -#: src/view/com/posts/FeedErrorMessage.tsx:119 +#: src/view/com/posts/FeedErrorMessage.tsx:123 msgid "Remove this feed from your saved feeds?" msgstr "इस फ़ीड को सहेजे गठफ़ीड से हटा दें?" @@ -1561,7 +1565,7 @@ msgstr "रिपोरà¥à¤Ÿ" msgid "Report feed" msgstr "रिपोरà¥à¤Ÿ फ़ीड" -#: src/view/screens/ProfileList.tsx:416 +#: src/view/screens/ProfileList.tsx:423 msgid "Report List" msgstr "रिपोरà¥à¤Ÿ सूची" @@ -1774,7 +1778,7 @@ msgstr "यौन गतिविधि या कामà¥à¤• नगà¥à¤¨à¤¤à¤ #: src/view/com/profile/ProfileHeader.tsx:312 #: src/view/com/util/forms/PostDropdownBtn.tsx:126 -#: src/view/screens/ProfileList.tsx:375 +#: src/view/screens/ProfileList.tsx:382 msgid "Share" msgstr "शेयर" @@ -1891,11 +1895,11 @@ msgstr "सà¥à¤¥à¤¿à¤¤à¤¿ पृषà¥à¤ " msgid "Storybook" msgstr "Storybook" -#: src/view/screens/ProfileList.tsx:497 +#: src/view/screens/ProfileList.tsx:504 msgid "Subscribe" msgstr "सबà¥à¤¸à¤•à¥à¤°à¤¾à¤‡à¤¬" -#: src/view/screens/ProfileList.tsx:493 +#: src/view/screens/ProfileList.tsx:500 msgid "Subscribe to this list" msgstr "इस सूची को सबà¥à¤¸à¤•à¥à¤°à¤¾à¤‡à¤¬ करें" @@ -2100,7 +2104,7 @@ msgstr "लोग सूचियाà¤" msgid "Username or email address" msgstr "यूजर नाम या ईमेल पता" -#: src/view/screens/ProfileList.tsx:659 +#: src/view/screens/ProfileList.tsx:668 msgid "Users" msgstr "यूजर लोग" @@ -2137,10 +2141,14 @@ msgstr "साइट पर जाà¤à¤‚" msgid "We're so excited to have you join us!" msgstr "हम आपके हमारी सेवा में शामिल होने को लेकर बहà¥à¤¤ उतà¥à¤¸à¤¾à¤¹à¤¿à¤¤ हैं!" -#: src/view/com/posts/FeedErrorMessage.tsx:98 +#: src/view/com/posts/FeedErrorMessage.tsx:99 msgid "We're sorry, but this content is not viewable without a Bluesky account." msgstr "" +#: src/view/com/posts/FeedErrorMessage.tsx:105 +msgid "We're sorry, but this feed is currently receiving high traffic and is temporarily unavailable. Please try again later." +msgstr "" + #: src/view/screens/Search/Search.tsx:236 msgid "We're sorry, but your search could not be completed. Please try again in a few minutes." msgstr "" diff --git a/src/view/com/composer/Composer.tsx b/src/view/com/composer/Composer.tsx index 6f058d39e..7336f3b95 100644 --- a/src/view/com/composer/Composer.tsx +++ b/src/view/com/composer/Composer.tsx @@ -201,7 +201,7 @@ export const ComposePost = observer(function ComposePost({ setError('') - if (richtext.text.trim().length === 0 && gallery.isEmpty) { + if (richtext.text.trim().length === 0 && gallery.isEmpty && !extLink) { setError('Did you want to say anything?') return } diff --git a/src/view/com/composer/text-input/TextInput.web.tsx b/src/view/com/composer/text-input/TextInput.web.tsx index 4c31da338..206a3205b 100644 --- a/src/view/com/composer/text-input/TextInput.web.tsx +++ b/src/view/com/composer/text-input/TextInput.web.tsx @@ -116,6 +116,16 @@ export const TextInput = React.forwardRef(function TextInputImpl( autofocus: 'end', editable: true, injectCSS: true, + onCreate({editor: editorProp}) { + // HACK + // the 'enter' animation sometimes causes autofocus to fail + // (see Composer.web.tsx in shell) + // so we wait 200ms (the anim is 150ms) and then focus manually + // -prf + setTimeout(() => { + editorProp.chain().focus('end').run() + }, 200) + }, onUpdate({editor: editorProp}) { const json = editorProp.getJSON() diff --git a/src/view/com/feeds/FeedPage.tsx b/src/view/com/feeds/FeedPage.tsx index f06716fb0..f3f07a8bd 100644 --- a/src/view/com/feeds/FeedPage.tsx +++ b/src/view/com/feeds/FeedPage.tsx @@ -158,9 +158,9 @@ export function FeedPage({ <View testID={testID} style={s.h100pct}> <Feed testID={testID ? `${testID}-feed` : undefined} + enabled={isPageFocused} feed={feed} feedParams={feedParams} - enabled={isPageFocused} pollInterval={POLL_FREQ} scrollElRef={scrollElRef} onScroll={onMainScroll} diff --git a/src/view/com/pager/Pager.tsx b/src/view/com/pager/Pager.tsx index d70087504..61c3609f2 100644 --- a/src/view/com/pager/Pager.tsx +++ b/src/view/com/pager/Pager.tsx @@ -81,12 +81,14 @@ export const Pager = forwardRef<PagerRef, React.PropsWithChildren<Props>>( if (scrollState.current === 'settling') { if (lastDirection.current === -1 && offset < lastOffset.current) { onPageSelecting?.(position) + setSelectedPage(position) lastDirection.current = 0 } else if ( lastDirection.current === 1 && offset > lastOffset.current ) { onPageSelecting?.(position + 1) + setSelectedPage(position + 1) lastDirection.current = 0 } } else { diff --git a/src/view/com/pager/PagerWithHeader.tsx b/src/view/com/pager/PagerWithHeader.tsx index 487c589e3..dcfc1eebb 100644 --- a/src/view/com/pager/PagerWithHeader.tsx +++ b/src/view/com/pager/PagerWithHeader.tsx @@ -69,13 +69,19 @@ export const PagerWithHeader = React.forwardRef<PagerRef, PagerWithHeaderProps>( // capture the header bar sizing const onTabBarLayout = React.useCallback( (evt: LayoutChangeEvent) => { - setTabBarHeight(evt.nativeEvent.layout.height) + const height = evt.nativeEvent.layout.height + if (height > 0) { + setTabBarHeight(height) + } }, [setTabBarHeight], ) const onHeaderOnlyLayout = React.useCallback( (evt: LayoutChangeEvent) => { - setHeaderOnlyHeight(evt.nativeEvent.layout.height) + const height = evt.nativeEvent.layout.height + if (height > 0) { + setHeaderOnlyHeight(height) + } }, [setHeaderOnlyHeight], ) @@ -248,11 +254,14 @@ let PagerTabBar = ({ })) return ( <Animated.View + pointerEvents="box-none" style={[ isMobile ? styles.tabBarMobile : styles.tabBarDesktop, headerTransform, ]}> - <View onLayout={onHeaderOnlyLayout}>{renderHeader?.()}</View> + <View onLayout={onHeaderOnlyLayout} pointerEvents="box-none"> + {renderHeader?.()} + </View> <View onLayout={onTabBarLayout} style={{ diff --git a/src/view/com/post-thread/PostThreadItem.tsx b/src/view/com/post-thread/PostThreadItem.tsx index a4b7a4a9c..86ea4eb39 100644 --- a/src/view/com/post-thread/PostThreadItem.tsx +++ b/src/view/com/post-thread/PostThreadItem.tsx @@ -351,11 +351,14 @@ let PostThreadItemLoaded = ({ {post.embed && ( <ContentHider moderation={moderation.embed} + moderationDecisions={moderation.decisions} ignoreMute={isEmbedByEmbedder(post.embed, post.author.did)} + ignoreQuoteDecisions style={s.mb10}> <PostEmbeds embed={post.embed} moderation={moderation.embed} + moderationDecisions={moderation.decisions} /> </ContentHider> )} @@ -414,7 +417,7 @@ let PostThreadItemLoaded = ({ </> ) } else { - const isThreadedChild = treeView && depth > 1 + const isThreadedChild = treeView && depth > 0 return ( <PostOuterWrapper post={post} @@ -426,7 +429,11 @@ let PostThreadItemLoaded = ({ testID={`postThreadItem-by-${post.author.handle}`} href={postHref} style={[pal.view]} - moderation={moderation.content}> + moderation={moderation.content} + iconSize={isThreadedChild ? 26 : 38} + iconStyles={ + isThreadedChild ? {marginRight: 4} : {marginLeft: 2, marginRight: 2} + }> <PostSandboxWarning /> <View @@ -491,10 +498,10 @@ let PostThreadItemLoaded = ({ timestamp={post.indexedAt} postHref={postHref} showAvatar={isThreadedChild} - avatarSize={26} + avatarSize={20} displayNameType="md-bold" displayNameStyle={isThreadedChild && s.ml2} - style={isThreadedChild && s.mb5} + style={isThreadedChild && s.mb2} /> <PostAlerts moderation={moderation.content} @@ -522,10 +529,14 @@ let PostThreadItemLoaded = ({ {post.embed && ( <ContentHider style={styles.contentHider} - moderation={moderation.embed}> + moderation={moderation.embed} + moderationDecisions={moderation.decisions} + ignoreMute={isEmbedByEmbedder(post.embed, post.author.did)} + ignoreQuoteDecisions> <PostEmbeds embed={post.embed} moderation={moderation.embed} + moderationDecisions={moderation.decisions} /> </ContentHider> )} @@ -583,7 +594,7 @@ function PostOuterWrapper({ const {isMobile} = useWebMediaQueries() const pal = usePalette('default') const styles = useStyles() - if (treeView && depth > 1) { + if (treeView && depth > 0) { return ( <View style={[ @@ -592,9 +603,9 @@ function PostOuterWrapper({ styles.cursor, { flexDirection: 'row', - paddingLeft: 20, + paddingLeft: depth === 1 ? 10 : 20, borderTopWidth: depth === 1 ? 1 : 0, - paddingTop: depth === 1 ? 8 : 0, + paddingTop: depth === 1 ? 6 : 0, }, ]}> {Array.from(Array(depth - 1)).map((_, n: number) => ( @@ -603,8 +614,8 @@ function PostOuterWrapper({ style={{ borderLeftWidth: 2, borderLeftColor: pal.colors.border, - marginLeft: n === 0 ? 14 : isMobile ? 6 : 14, - paddingLeft: n === 0 ? 18 : isMobile ? 6 : 12, + marginLeft: isMobile ? 6 : 14, + paddingLeft: isMobile ? 6 : 12, }} /> ))} diff --git a/src/view/com/post/Post.tsx b/src/view/com/post/Post.tsx index 2e8019e71..9b1bf7a49 100644 --- a/src/view/com/post/Post.tsx +++ b/src/view/com/post/Post.tsx @@ -196,8 +196,14 @@ function PostInner({ {post.embed ? ( <ContentHider moderation={moderation.embed} + moderationDecisions={moderation.decisions} + ignoreQuoteDecisions style={styles.contentHider}> - <PostEmbeds embed={post.embed} moderation={moderation.embed} /> + <PostEmbeds + embed={post.embed} + moderation={moderation.embed} + moderationDecisions={moderation.decisions} + /> </ContentHider> ) : null} </ContentHider> diff --git a/src/view/com/posts/Feed.tsx b/src/view/com/posts/Feed.tsx index 393c1bc91..b9ca9abdc 100644 --- a/src/view/com/posts/Feed.tsx +++ b/src/view/com/posts/Feed.tsx @@ -26,6 +26,7 @@ import { pollLatest, } from '#/state/queries/post-feed' import {useModerationOpts} from '#/state/queries/preferences' +import {isWeb} from '#/platform/detection' const LOADING_ITEM = {_reactKey: '__loading__'} const EMPTY_FEED_ITEM = {_reactKey: '__empty__'} @@ -89,7 +90,7 @@ let Feed = ({ const isEmpty = !isFetching && !data?.pages[0]?.slices.length const checkForNew = React.useCallback(async () => { - if (!data?.pages[0] || isFetching || !onHasNew) { + if (!data?.pages[0] || isFetching || !onHasNew || !enabled) { return } try { @@ -99,7 +100,7 @@ let Feed = ({ } catch (e) { logger.error('Poll latest failed', {feed, error: String(e)}) } - }, [feed, data, isFetching, onHasNew]) + }, [feed, data, isFetching, onHasNew, enabled]) React.useEffect(() => { // we store the interval handler in a ref to avoid needless @@ -216,19 +217,25 @@ let Feed = ({ const shouldRenderEndOfFeed = !hasNextPage && !isEmpty && !isFetching && !isError && !!renderEndOfFeed - const FeedFooter = React.useCallback( - () => - isFetchingNextPage ? ( - <View style={styles.feedFooter}> - <ActivityIndicator /> - </View> - ) : shouldRenderEndOfFeed ? ( - renderEndOfFeed() - ) : ( - <View /> - ), - [isFetchingNextPage, shouldRenderEndOfFeed, renderEndOfFeed], - ) + const FeedFooter = React.useCallback(() => { + /** + * A bit of padding at the bottom of the feed as you scroll and when you + * reach the end, so that content isn't cut off by the bottom of the + * screen. + */ + const offset = Math.max(headerOffset, 32) * (isWeb ? 1 : 2) + + return isFetchingNextPage ? ( + <View style={[styles.feedFooter]}> + <ActivityIndicator /> + <View style={{height: offset}} /> + </View> + ) : shouldRenderEndOfFeed ? ( + <View style={{minHeight: offset}}>{renderEndOfFeed()}</View> + ) : ( + <View style={{height: offset}} /> + ) + }, [isFetchingNextPage, shouldRenderEndOfFeed, renderEndOfFeed, headerOffset]) const scrollHandler = useAnimatedScrollHandler(onScroll || {}) return ( diff --git a/src/view/com/posts/FeedErrorMessage.tsx b/src/view/com/posts/FeedErrorMessage.tsx index 63d9d5956..f63bc1a88 100644 --- a/src/view/com/posts/FeedErrorMessage.tsx +++ b/src/view/com/posts/FeedErrorMessage.tsx @@ -25,6 +25,7 @@ export enum KnownError { FeedgenOffline = 'FeedgenOffline', FeedgenUnknown = 'FeedgenUnknown', FeedNSFPublic = 'FeedNSFPublic', + FeedTooManyRequests = 'FeedTooManyRequests', Unknown = 'Unknown', } @@ -100,6 +101,9 @@ function FeedgenErrorMessage({ [KnownError.FeedgenUnknown]: _l( msgLingui`Hmm, some kind of issue occured when contacting the feed server. Please let the feed owner know about this issue.`, ), + [KnownError.FeedTooManyRequests]: _l( + msgLingui`We're sorry, but this feed is currently receiving high traffic and is temporarily unavailable. Please try again later.`, + ), }[knownError]), [_l, knownError], ) @@ -203,6 +207,13 @@ function detectKnownError( ) { return KnownError.Block } + + // check status codes + if (error?.status === 429) { + return KnownError.FeedTooManyRequests + } + + // convert error to string and continue if (typeof error !== 'string') { error = error.toString() } diff --git a/src/view/com/posts/FeedItem.tsx b/src/view/com/posts/FeedItem.tsx index dfb0cfcf6..b6c509e92 100644 --- a/src/view/com/posts/FeedItem.tsx +++ b/src/view/com/posts/FeedItem.tsx @@ -320,9 +320,15 @@ let FeedItemInner = ({ <ContentHider testID="contentHider-embed" moderation={moderation.embed} + moderationDecisions={moderation.decisions} ignoreMute={isEmbedByEmbedder(post.embed, post.author.did)} + ignoreQuoteDecisions style={styles.embed}> - <PostEmbeds embed={post.embed} moderation={moderation.embed} /> + <PostEmbeds + embed={post.embed} + moderation={moderation.embed} + moderationDecisions={moderation.decisions} + /> </ContentHider> ) : null} </ContentHider> diff --git a/src/view/com/posts/FollowingEndOfFeed.tsx b/src/view/com/posts/FollowingEndOfFeed.tsx index 48724d8b3..6630b9a83 100644 --- a/src/view/com/posts/FollowingEndOfFeed.tsx +++ b/src/view/com/posts/FollowingEndOfFeed.tsx @@ -1,5 +1,5 @@ import React from 'react' -import {StyleSheet, View} from 'react-native' +import {StyleSheet, View, Dimensions} from 'react-native' import {useNavigation} from '@react-navigation/native' import { FontAwesomeIcon, @@ -36,7 +36,12 @@ export function FollowingEndOfFeed() { }, [navigation]) return ( - <View style={[styles.container, pal.border]}> + <View + style={[ + styles.container, + pal.border, + {minHeight: Dimensions.get('window').height * 0.75}, + ]}> <View style={styles.inner}> <Text type="xl-medium" style={[s.textCenter, pal.text]}> You've reached the end of your feed! Find some more accounts to diff --git a/src/view/com/profile/ProfileCard.tsx b/src/view/com/profile/ProfileCard.tsx index 279e00d75..21972f274 100644 --- a/src/view/com/profile/ProfileCard.tsx +++ b/src/view/com/profile/ProfileCard.tsx @@ -228,6 +228,7 @@ const styles = StyleSheet.create({ outer: { borderTopWidth: 1, paddingHorizontal: 6, + paddingVertical: 4, }, outerNoBorder: { borderTopWidth: 0, @@ -237,7 +238,7 @@ const styles = StyleSheet.create({ alignItems: 'center', }, layoutAvi: { - alignSelf: 'baseline', + alignSelf: 'flex-start', width: 54, paddingLeft: 4, paddingTop: 10, diff --git a/src/view/com/profile/ProfileHeader.tsx b/src/view/com/profile/ProfileHeader.tsx index c1de10aa5..16e98ddf2 100644 --- a/src/view/com/profile/ProfileHeader.tsx +++ b/src/view/com/profile/ProfileHeader.tsx @@ -412,10 +412,12 @@ let ProfileHeaderLoaded = ({ const pluralizedFollowers = pluralize(profile.followersCount || 0, 'follower') return ( - <View style={pal.view}> - <UserBanner banner={profile.banner} moderation={moderation.avatar} /> - <View style={styles.content}> - <View style={[styles.buttonsLine]}> + <View style={pal.view} pointerEvents="box-none"> + <View pointerEvents="none"> + <UserBanner banner={profile.banner} moderation={moderation.avatar} /> + </View> + <View style={styles.content} pointerEvents="box-none"> + <View style={[styles.buttonsLine]} pointerEvents="box-none"> {isMe ? ( <TouchableOpacity testID="profileHeaderEditProfileButton" @@ -468,7 +470,7 @@ let ProfileHeaderLoaded = ({ pal.text, { color: showSuggestedFollows - ? colors.white + ? pal.textInverted.color : pal.text.color, }, ]} @@ -525,7 +527,7 @@ let ProfileHeaderLoaded = ({ </NativeDropdown> ) : undefined} </View> - <View> + <View pointerEvents="none"> <Text testID="profileHeaderDisplayName" type="title-2xl" @@ -536,7 +538,7 @@ let ProfileHeaderLoaded = ({ )} </Text> </View> - <View style={styles.handleLine}> + <View style={styles.handleLine} pointerEvents="none"> {profile.viewer?.followedBy && !blockHide ? ( <View style={[styles.pill, pal.btn, s.mr5]}> <Text type="xs" style={[pal.text]}> @@ -557,7 +559,7 @@ let ProfileHeaderLoaded = ({ </View> {!blockHide && ( <> - <View style={styles.metricsLine}> + <View style={styles.metricsLine} pointerEvents="box-none"> <Link testID="profileHeaderFollowersButton" style={[s.flexRow, s.mr10]} @@ -604,12 +606,14 @@ let ProfileHeaderLoaded = ({ </Text> </View> {descriptionRT && !moderation.profile.blur ? ( - <RichText - testID="profileHeaderDescription" - style={[styles.description, pal.text]} - numberOfLines={15} - richText={descriptionRT} - /> + <View pointerEvents="none"> + <RichText + testID="profileHeaderDescription" + style={[styles.description, pal.text]} + numberOfLines={15} + richText={descriptionRT} + /> + </View> ) : undefined} </> )} diff --git a/src/view/com/profile/ProfileHeaderSuggestedFollows.tsx b/src/view/com/profile/ProfileHeaderSuggestedFollows.tsx index f648c9801..1d550aa5c 100644 --- a/src/view/com/profile/ProfileHeaderSuggestedFollows.tsx +++ b/src/view/com/profile/ProfileHeaderSuggestedFollows.tsx @@ -70,15 +70,19 @@ export function ProfileHeaderSuggestedFollows({ }) return ( - <Animated.View style={[{overflow: 'hidden', opacity: 0}, animatedStyles]}> - <View style={{paddingVertical: OUTER_PADDING}}> + <Animated.View + pointerEvents="box-none" + style={[{overflow: 'hidden', opacity: 0}, animatedStyles]}> + <View style={{paddingVertical: OUTER_PADDING}} pointerEvents="box-none"> <View + pointerEvents="box-none" style={{ backgroundColor: pal.viewLight.backgroundColor, height: '100%', paddingTop: INNER_PADDING / 2, }}> <View + pointerEvents="box-none" style={{ flexDirection: 'row', justifyContent: 'space-between', diff --git a/src/view/com/util/LoadingPlaceholder.tsx b/src/view/com/util/LoadingPlaceholder.tsx index 74e36ff7b..a07b33325 100644 --- a/src/view/com/util/LoadingPlaceholder.tsx +++ b/src/view/com/util/LoadingPlaceholder.tsx @@ -7,7 +7,7 @@ import { DimensionValue, } from 'react-native' import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome' -import {HeartIcon} from 'lib/icons' +import {HeartIcon, HeartIconSolid} from 'lib/icons' import {s} from 'lib/styles' import {useTheme} from 'lib/ThemeContext' import {usePalette} from 'lib/hooks/usePalette' @@ -46,12 +46,22 @@ export function PostLoadingPlaceholder({ const pal = usePalette('default') return ( <View style={[styles.post, pal.view, style]}> - <LoadingPlaceholder width={52} height={52} style={styles.avatar} /> + <LoadingPlaceholder + width={52} + height={52} + style={[ + styles.avatar, + { + position: 'relative', + top: -6, + }, + ]} + /> <View style={[s.flex1]}> - <LoadingPlaceholder width={100} height={8} style={[s.mb10]} /> - <LoadingPlaceholder width={200} height={8} style={[s.mb5]} /> - <LoadingPlaceholder width={200} height={8} style={[s.mb5]} /> - <LoadingPlaceholder width={120} height={8} style={[s.mb10]} /> + <LoadingPlaceholder width={100} height={6} style={{marginBottom: 10}} /> + <LoadingPlaceholder width="95%" height={6} style={{marginBottom: 8}} /> + <LoadingPlaceholder width="95%" height={6} style={{marginBottom: 8}} /> + <LoadingPlaceholder width="80%" height={6} style={{marginBottom: 15}} /> <View style={s.flexRow}> <View style={s.flex1}> <FontAwesomeIcon @@ -90,6 +100,8 @@ export function PostFeedLoadingPlaceholder() { <PostLoadingPlaceholder /> <PostLoadingPlaceholder /> <PostLoadingPlaceholder /> + <PostLoadingPlaceholder /> + <PostLoadingPlaceholder /> </View> ) } @@ -102,11 +114,23 @@ export function NotificationLoadingPlaceholder({ const pal = usePalette('default') return ( <View style={[styles.notification, pal.view, style]}> - <View style={[s.flexRow, s.mb10]}> - <LoadingPlaceholder width={30} height={30} style={styles.smallAvatar} /> + <View style={{paddingLeft: 30, paddingRight: 10}}> + <HeartIconSolid + style={{color: pal.colors.backgroundLight} as ViewStyle} + size={30} + /> + </View> + <View style={{flex: 1}}> + <View style={[s.flexRow, s.mb10]}> + <LoadingPlaceholder + width={30} + height={30} + style={styles.smallAvatar} + /> + </View> + <LoadingPlaceholder width="90%" height={6} style={[s.mb5]} /> + <LoadingPlaceholder width="70%" height={6} style={[s.mb5]} /> </View> - <LoadingPlaceholder width={200} height={8} style={[s.mb5]} /> - <LoadingPlaceholder width={120} height={8} style={[s.mb5]} /> </View> ) } @@ -239,18 +263,19 @@ const styles = StyleSheet.create({ }, post: { flexDirection: 'row', - padding: 10, - margin: 1, + alignItems: 'flex-start', + paddingHorizontal: 10, + paddingTop: 20, + paddingBottom: 5, }, avatar: { borderRadius: 26, marginRight: 10, - marginLeft: 6, + marginLeft: 8, }, notification: { + flexDirection: 'row', padding: 10, - paddingLeft: 46, - margin: 1, }, profileCard: { flexDirection: 'row', diff --git a/src/view/com/util/moderation/ContentHider.tsx b/src/view/com/util/moderation/ContentHider.tsx index a13aae2b5..b1ea76621 100644 --- a/src/view/com/util/moderation/ContentHider.tsx +++ b/src/view/com/util/moderation/ContentHider.tsx @@ -1,36 +1,44 @@ import React from 'react' import {Pressable, StyleProp, StyleSheet, View, ViewStyle} from 'react-native' +import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome' import {usePalette} from 'lib/hooks/usePalette' -import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' -import {ModerationUI} from '@atproto/api' +import {ModerationUI, PostModeration} from '@atproto/api' import {Text} from '../text/Text' import {ShieldExclamation} from 'lib/icons' import {describeModerationCause} from 'lib/moderation' import {useLingui} from '@lingui/react' import {msg} from '@lingui/macro' import {useModalControls} from '#/state/modals' +import {isPostMediaBlurred} from 'lib/moderation' export function ContentHider({ testID, moderation, + moderationDecisions, ignoreMute, + ignoreQuoteDecisions, style, childContainerStyle, children, }: React.PropsWithChildren<{ testID?: string moderation: ModerationUI + moderationDecisions?: PostModeration['decisions'] ignoreMute?: boolean + ignoreQuoteDecisions?: boolean style?: StyleProp<ViewStyle> childContainerStyle?: StyleProp<ViewStyle> }>) { const pal = usePalette('default') const {_} = useLingui() - const {isMobile} = useWebMediaQueries() const [override, setOverride] = React.useState(false) const {openModal} = useModalControls() - if (!moderation.blur || (ignoreMute && moderation.cause?.type === 'muted')) { + if ( + !moderation.blur || + (ignoreMute && moderation.cause?.type === 'muted') || + shouldIgnoreQuote(moderationDecisions, ignoreQuoteDecisions) + ) { return ( <View testID={testID} style={[styles.outer, style]}> {children} @@ -38,6 +46,7 @@ export function ContentHider({ ) } + const isMute = moderation.cause?.type === 'muted' const desc = describeModerationCause(moderation.cause, 'content') return ( <View testID={testID} style={[styles.outer, style]}> @@ -58,7 +67,6 @@ export function ContentHider({ accessibilityLabel="" style={[ styles.cover, - {paddingRight: isMobile ? 22 : 18}, moderation.noOverride ? {borderWidth: 1, borderColor: pal.colors.borderDark} : pal.viewLight, @@ -74,14 +82,22 @@ export function ContentHider({ accessibilityRole="button" accessibilityLabel={_(msg`Learn more about this warning`)} accessibilityHint=""> - <ShieldExclamation size={18} style={pal.text} /> + {isMute ? ( + <FontAwesomeIcon + icon={['far', 'eye-slash']} + size={18} + color={pal.colors.textLight} + /> + ) : ( + <ShieldExclamation size={18} style={pal.textLight} /> + )} </Pressable> - <Text type="lg" style={pal.text}> + <Text type="md" style={pal.text}> {desc.name} </Text> {!moderation.noOverride && ( <View style={styles.showBtn}> - <Text type="xl" style={pal.link}> + <Text type="lg" style={pal.link}> {override ? 'Hide' : 'Show'} </Text> </View> @@ -92,6 +108,16 @@ export function ContentHider({ ) } +function shouldIgnoreQuote( + decisions: PostModeration['decisions'] | undefined, + ignore: boolean | undefined, +): boolean { + if (!decisions || !ignore) { + return false + } + return !isPostMediaBlurred(decisions) +} + const styles = StyleSheet.create({ outer: { overflow: 'hidden', @@ -104,6 +130,7 @@ const styles = StyleSheet.create({ marginTop: 4, paddingVertical: 14, paddingLeft: 14, + paddingRight: 18, }, showBtn: { marginLeft: 'auto', diff --git a/src/view/com/util/moderation/PostHider.tsx b/src/view/com/util/moderation/PostHider.tsx index c2b857f54..bffb7ea1a 100644 --- a/src/view/com/util/moderation/PostHider.tsx +++ b/src/view/com/util/moderation/PostHider.tsx @@ -1,8 +1,8 @@ import React, {ComponentProps} from 'react' -import {StyleSheet, Pressable, View} from 'react-native' +import {StyleSheet, Pressable, View, ViewStyle, StyleProp} from 'react-native' import {ModerationUI} from '@atproto/api' +import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome' import {usePalette} from 'lib/hooks/usePalette' -import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' import {Link} from '../Link' import {Text} from '../text/Text' import {addStyle} from 'lib/styles' @@ -13,9 +13,8 @@ import {msg} from '@lingui/macro' import {useModalControls} from '#/state/modals' interface Props extends ComponentProps<typeof Link> { - // testID?: string - // href?: string - // style: StyleProp<ViewStyle> + iconSize: number + iconStyles: StyleProp<ViewStyle> moderation: ModerationUI } @@ -25,11 +24,12 @@ export function PostHider({ moderation, style, children, + iconSize, + iconStyles, ...props }: Props) { const pal = usePalette('default') const {_} = useLingui() - const {isMobile} = useWebMediaQueries() const [override, setOverride] = React.useState(false) const {openModal} = useModalControls() @@ -47,57 +47,74 @@ export function PostHider({ ) } + const isMute = moderation.cause?.type === 'muted' const desc = describeModerationCause(moderation.cause, 'content') - return ( - <> + return !override ? ( + <Pressable + onPress={() => { + if (!moderation.noOverride) { + setOverride(v => !v) + } + }} + accessibilityRole="button" + accessibilityHint={override ? 'Hide the content' : 'Show the content'} + accessibilityLabel="" + style={[ + styles.description, + override ? {paddingBottom: 0} : undefined, + pal.view, + ]}> <Pressable onPress={() => { - if (!moderation.noOverride) { - setOverride(v => !v) - } + openModal({ + name: 'moderation-details', + context: 'content', + moderation, + }) }} accessibilityRole="button" - accessibilityHint={override ? 'Hide the content' : 'Show the content'} - accessibilityLabel="" - style={[ - styles.description, - {paddingRight: isMobile ? 22 : 18}, - pal.viewLight, - ]}> - <Pressable - onPress={() => { - openModal({ - name: 'moderation-details', - context: 'content', - moderation, - }) - }} - accessibilityRole="button" - accessibilityLabel={_(msg`Learn more about this warning`)} - accessibilityHint=""> - <ShieldExclamation size={18} style={pal.text} /> - </Pressable> - <Text type="lg" style={[{flex: 1}, pal.text]} numberOfLines={1}> - {desc.name} - </Text> - {!moderation.noOverride && ( - <Text type="xl" style={[styles.showBtn, pal.link]}> - {override ? 'Hide' : 'Show'} - </Text> - )} - </Pressable> - {override && ( - <View style={[styles.childrenContainer, pal.border, pal.viewLight]}> - <Link - testID={testID} - style={addStyle(style, styles.child)} - href={href} - noFeedback> - {children} - </Link> + accessibilityLabel={_(msg`Learn more about this warning`)} + accessibilityHint=""> + <View + style={[ + pal.viewLight, + { + width: iconSize, + height: iconSize, + borderRadius: iconSize, + alignItems: 'center', + justifyContent: 'center', + }, + iconStyles, + ]}> + {isMute ? ( + <FontAwesomeIcon + icon={['far', 'eye-slash']} + size={14} + color={pal.colors.textLight} + /> + ) : ( + <ShieldExclamation size={14} style={pal.textLight} /> + )} </View> + </Pressable> + <Text type="sm" style={[{flex: 1}, pal.textLight]} numberOfLines={1}> + {desc.name} + </Text> + {!moderation.noOverride && ( + <Text type="sm" style={[styles.showBtn, pal.link]}> + {override ? 'Hide' : 'Show'} + </Text> )} - </> + </Pressable> + ) : ( + <Link + testID={testID} + style={addStyle(style, styles.child)} + href={href} + noFeedback> + {children} + </Link> ) } @@ -106,18 +123,15 @@ const styles = StyleSheet.create({ flexDirection: 'row', alignItems: 'center', gap: 4, - paddingVertical: 14, - paddingLeft: 18, + paddingVertical: 10, + paddingLeft: 6, + paddingRight: 18, marginTop: 1, }, showBtn: { marginLeft: 'auto', alignSelf: 'center', }, - childrenContainer: { - paddingHorizontal: 4, - paddingBottom: 6, - }, child: { borderWidth: 0, borderTopWidth: 0, diff --git a/src/view/com/util/moderation/ProfileHeaderAlerts.tsx b/src/view/com/util/moderation/ProfileHeaderAlerts.tsx index d2675ca54..0f07b679b 100644 --- a/src/view/com/util/moderation/ProfileHeaderAlerts.tsx +++ b/src/view/com/util/moderation/ProfileHeaderAlerts.tsx @@ -10,6 +10,7 @@ import { } from 'lib/moderation' import {msg, Trans} from '@lingui/macro' import {useLingui} from '@lingui/react' +import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome' import {useModalControls} from '#/state/modals' export function ProfileHeaderAlerts({ @@ -31,6 +32,7 @@ export function ProfileHeaderAlerts({ return ( <View style={styles.grid}> {causes.map(cause => { + const isMute = cause.type === 'muted' const desc = describeModerationCause(cause, 'account') return ( <Pressable @@ -47,11 +49,19 @@ export function ProfileHeaderAlerts({ accessibilityLabel={_(msg`Learn more about this warning`)} accessibilityHint="" style={[styles.container, pal.viewLight, style]}> - <ShieldExclamation style={pal.text} size={24} /> - <Text type="lg" style={[{flex: 1}, pal.text]}> + {isMute ? ( + <FontAwesomeIcon + icon={['far', 'eye-slash']} + size={14} + color={pal.colors.textLight} + /> + ) : ( + <ShieldExclamation style={pal.text} size={18} /> + )} + <Text type="sm" style={[{flex: 1}, pal.text]}> {desc.name} </Text> - <Text type="lg" style={[pal.link, styles.learnMoreBtn]}> + <Text type="sm" style={[pal.link, styles.learnMoreBtn]}> <Trans>Learn More</Trans> </Text> </Pressable> diff --git a/src/view/com/util/post-embeds/index.tsx b/src/view/com/util/post-embeds/index.tsx index ca3bf1104..5c16a3b3e 100644 --- a/src/view/com/util/post-embeds/index.tsx +++ b/src/view/com/util/post-embeds/index.tsx @@ -16,6 +16,7 @@ import { AppBskyFeedDefs, AppBskyGraphDefs, ModerationUI, + PostModeration, } from '@atproto/api' import {Link} from '../Link' import {ImageLayoutGrid} from '../images/ImageLayoutGrid' @@ -28,8 +29,9 @@ import {getYoutubeVideoId} from 'lib/strings/url-helpers' import {MaybeQuoteEmbed} from './QuoteEmbed' import {AutoSizedImage} from '../images/AutoSizedImage' import {ListEmbed} from './ListEmbed' -import {isCauseALabelOnUri} from 'lib/moderation' +import {isCauseALabelOnUri, isQuoteBlurred} from 'lib/moderation' import {FeedSourceCard} from 'view/com/feeds/FeedSourceCard' +import {ContentHider} from '../moderation/ContentHider' type Embed = | AppBskyEmbedRecord.View @@ -41,10 +43,12 @@ type Embed = export function PostEmbeds({ embed, moderation, + moderationDecisions, style, }: { embed?: Embed moderation: ModerationUI + moderationDecisions?: PostModeration['decisions'] style?: StyleProp<ViewStyle> }) { const pal = usePalette('default') @@ -55,14 +59,17 @@ export function PostEmbeds({ // = if (AppBskyEmbedRecordWithMedia.isView(embed)) { const isModOnQuote = - AppBskyEmbedRecord.isViewRecord(embed.record.record) && - isCauseALabelOnUri(moderation.cause, embed.record.record.uri) + (AppBskyEmbedRecord.isViewRecord(embed.record.record) && + isCauseALabelOnUri(moderation.cause, embed.record.record.uri)) || + (moderationDecisions && isQuoteBlurred(moderationDecisions)) const mediaModeration = isModOnQuote ? {} : moderation const quoteModeration = isModOnQuote ? moderation : {} return ( <View style={[styles.stackContainer, style]}> <PostEmbeds embed={embed.media} moderation={mediaModeration} /> - <MaybeQuoteEmbed embed={embed.record} moderation={quoteModeration} /> + <ContentHider moderation={quoteModeration}> + <MaybeQuoteEmbed embed={embed.record} moderation={quoteModeration} /> + </ContentHider> </View> ) } diff --git a/src/view/screens/Home.tsx b/src/view/screens/Home.tsx index 6100d42db..d07fa0434 100644 --- a/src/view/screens/Home.tsx +++ b/src/view/screens/Home.tsx @@ -1,6 +1,6 @@ import React from 'react' import {View, ActivityIndicator, StyleSheet} from 'react-native' -import {useFocusEffect} from '@react-navigation/native' +import {useFocusEffect, useIsFocused} from '@react-navigation/native' import {NativeStackScreenProps, HomeTabNavigatorParams} from 'lib/routes/types' import {FeedDescriptor, FeedParams} from '#/state/queries/post-feed' import {FollowingEmptyState} from 'view/com/posts/FollowingEmptyState' @@ -65,6 +65,7 @@ function HomeScreenReady({ const {hasSession} = useSession() const setMinimalShellMode = useSetMinimalShellMode() const setDrawerSwipeDisabled = useSetDrawerSwipeDisabled() + const isPageFocused = useIsFocused() const [selectedPage, setSelectedPage] = React.useState<string>(initialPage) /** @@ -174,7 +175,7 @@ function HomeScreenReady({ <FeedPage key="1" testID="followingFeedPage" - isPageFocused={selectedPageIndex === 0} + isPageFocused={selectedPageIndex === 0 && isPageFocused} feed={homeFeedParams.mergeFeedEnabled ? 'home' : 'following'} feedParams={homeFeedParams} renderEmptyState={renderFollowingEmptyState} @@ -185,7 +186,7 @@ function HomeScreenReady({ <FeedPage key={f} testID="customFeedPage" - isPageFocused={selectedPageIndex === 1 + index} + isPageFocused={selectedPageIndex === 1 + index && isPageFocused} feed={f} renderEmptyState={renderCustomFeedEmptyState} /> @@ -201,7 +202,7 @@ function HomeScreenReady({ tabBarPosition="top"> <FeedPage testID="customFeedPage" - isPageFocused + isPageFocused={isPageFocused} feed={`feedgen|at://did:plc:z72i7hdynmk6r22z27h6tvur/app.bsky.feed.generator/whats-hot`} renderEmptyState={renderCustomFeedEmptyState} /> diff --git a/src/view/screens/Profile.tsx b/src/view/screens/Profile.tsx index d5e378ccb..ea19515b5 100644 --- a/src/view/screens/Profile.tsx +++ b/src/view/screens/Profile.tsx @@ -2,7 +2,7 @@ import React, {useMemo} from 'react' import {StyleSheet, View} from 'react-native' import {useFocusEffect} from '@react-navigation/native' import {AppBskyActorDefs, moderateProfile, ModerationOpts} from '@atproto/api' -import {msg} from '@lingui/macro' +import {msg, Trans} from '@lingui/macro' import {useLingui} from '@lingui/react' import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' import {CenteredView, FlatList} from '../com/util/Views' @@ -36,6 +36,8 @@ import {useQueryClient} from '@tanstack/react-query' import {useComposerControls} from '#/state/shell/composer' import {listenSoftReset} from '#/state/events' import {truncateAndInvalidate} from '#/state/queries/util' +import {Text} from '#/view/com/util/text/Text' +import {usePalette} from 'lib/hooks/usePalette' interface SectionRef { scrollToTop: () => void @@ -420,6 +422,7 @@ const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( <View> <Feed testID="postsFeed" + enabled={isFocused} feed={feed} pollInterval={30e3} scrollElRef={scrollElRef} @@ -428,7 +431,7 @@ const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( scrollEventThrottle={1} renderEmptyState={renderPostsEmpty} headerOffset={headerHeight} - enabled={isFocused} + renderEndOfFeed={ProfileEndOfFeed} /> {(isScrolledDown || hasNew) && ( <LoadLatestBtn @@ -442,6 +445,18 @@ const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( }, ) +function ProfileEndOfFeed() { + const pal = usePalette('default') + + return ( + <View style={[pal.border, {paddingTop: 32, borderTopWidth: 1}]}> + <Text style={[pal.textLight, pal.border, {textAlign: 'center'}]}> + <Trans>End of feed</Trans> + </Text> + </View> + ) +} + const styles = StyleSheet.create({ container: { flexDirection: 'column', diff --git a/src/view/screens/ProfileFeed.tsx b/src/view/screens/ProfileFeed.tsx index 659560a25..3a0bdcc0f 100644 --- a/src/view/screens/ProfileFeed.tsx +++ b/src/view/screens/ProfileFeed.tsx @@ -402,7 +402,7 @@ export function ProfileFeedScreenInner({ isHeaderReady={true} renderHeader={renderHeader} onCurrentPageSelected={onCurrentPageSelected}> - {({onScroll, headerHeight, isScrolledDown, scrollElRef}) => + {({onScroll, headerHeight, isScrolledDown, scrollElRef, isFocused}) => isPublic ? ( <FeedSection ref={feedSectionRef} @@ -413,6 +413,7 @@ export function ProfileFeedScreenInner({ scrollElRef={ scrollElRef as React.MutableRefObject<FlatList<any> | null> } + isFocused={isFocused} /> ) : ( <CenteredView sideBorders style={[{paddingTop: headerHeight}]}> @@ -492,10 +493,11 @@ interface FeedSectionProps { headerHeight: number isScrolledDown: boolean scrollElRef: React.MutableRefObject<FlatList<any> | null> + isFocused: boolean } const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( function FeedSectionImpl( - {feed, onScroll, headerHeight, isScrolledDown, scrollElRef}, + {feed, onScroll, headerHeight, isScrolledDown, scrollElRef, isFocused}, ref, ) { const [hasNew, setHasNew] = React.useState(false) @@ -518,6 +520,7 @@ const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( return ( <View> <Feed + enabled={isFocused} feed={feed} pollInterval={30e3} scrollElRef={scrollElRef} diff --git a/src/view/screens/ProfileList.tsx b/src/view/screens/ProfileList.tsx index 1396b8269..3e568c8cc 100644 --- a/src/view/screens/ProfileList.tsx +++ b/src/view/screens/ProfileList.tsx @@ -56,6 +56,12 @@ import {useSession} from '#/state/session' import {useComposerControls} from '#/state/shell/composer' import {isWeb} from '#/platform/detection' import {truncateAndInvalidate} from '#/state/queries/util' +import { + usePreferencesQuery, + usePinFeedMutation, + useUnpinFeedMutation, +} from '#/state/queries/preferences' +import {logger} from '#/logger' const SECTION_TITLES_CURATE = ['Posts', 'About'] const SECTION_TITLES_MOD = ['About'] @@ -129,7 +135,6 @@ function ProfileListScreenLoaded({ list, onChange() { if (isCurateList) { - // TODO(eric) should construct these strings with a fn too truncateAndInvalidate(queryClient, FEED_RQKEY(`list|${list.uri}`)) } }, @@ -159,7 +164,13 @@ function ProfileListScreenLoaded({ isHeaderReady={true} renderHeader={renderHeader} onCurrentPageSelected={onCurrentPageSelected}> - {({onScroll, headerHeight, isScrolledDown, scrollElRef}) => ( + {({ + onScroll, + headerHeight, + isScrolledDown, + scrollElRef, + isFocused, + }) => ( <FeedSection ref={feedSectionRef} feed={`list|${uri}`} @@ -169,6 +180,7 @@ function ProfileListScreenLoaded({ onScroll={onScroll} headerHeight={headerHeight} isScrolledDown={isScrolledDown} + isFocused={isFocused} /> )} {({onScroll, headerHeight, isScrolledDown, scrollElRef}) => ( @@ -247,19 +259,31 @@ function Header({rkey, list}: {rkey: string; list: AppBskyGraphDefs.ListView}) { const listDeleteMutation = useListDeleteMutation() const isCurateList = list.purpose === 'app.bsky.graph.defs#curatelist' const isModList = list.purpose === 'app.bsky.graph.defs#modlist' - const isPinned = false // TODO const isBlocking = !!list.viewer?.blocked const isMuting = !!list.viewer?.muted const isOwner = list.creator.did === currentAccount?.did + const {isPending: isPinPending, mutateAsync: pinFeed} = usePinFeedMutation() + const {isPending: isUnpinPending, mutateAsync: unpinFeed} = + useUnpinFeedMutation() + const isPending = isPinPending || isUnpinPending + const {data: preferences} = usePreferencesQuery() - const onTogglePinned = useCallback(async () => { + const isPinned = preferences?.feeds?.pinned?.includes(list.uri) + + const onTogglePinned = React.useCallback(async () => { Haptics.default() - // TODO - // list.togglePin().catch(e => { - // Toast.show('There was an issue contacting the server') - // logger.error('Failed to toggle pinned list', {error: e}) - // }) - }, []) + + try { + if (isPinned) { + await unpinFeed({uri: list.uri}) + } else { + await pinFeed({uri: list.uri}) + } + } catch (e) { + Toast.show('There was an issue contacting the server') + logger.error('Failed to toggle pinned feed', {error: e}) + } + }, [list.uri, isPinned, pinFeed, unpinFeed]) const onSubscribeMute = useCallback(() => { openModal({ @@ -466,10 +490,11 @@ function Header({rkey, list}: {rkey: string; list: AppBskyGraphDefs.ListView}) { avatarType="list"> {isCurateList || isPinned ? ( <Button - testID={list.isPinned ? 'unpinBtn' : 'pinBtn'} - type={list.isPinned ? 'default' : 'inverted'} - label={list.isPinned ? 'Unpin' : 'Pin to home'} + testID={isPinned ? 'unpinBtn' : 'pinBtn'} + type={isPinned ? 'default' : 'inverted'} + label={isPinned ? 'Unpin' : 'Pin to home'} onPress={onTogglePinned} + disabled={isPending} /> ) : isModList ? ( isBlocking ? ( @@ -519,10 +544,11 @@ interface FeedSectionProps { headerHeight: number isScrolledDown: boolean scrollElRef: React.MutableRefObject<FlatList<any> | null> + isFocused: boolean } const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( function FeedSectionImpl( - {feed, scrollElRef, onScroll, headerHeight, isScrolledDown}, + {feed, scrollElRef, onScroll, headerHeight, isScrolledDown, isFocused}, ref, ) { const queryClient = useQueryClient() @@ -545,6 +571,7 @@ const FeedSection = React.forwardRef<SectionRef, FeedSectionProps>( <View> <Feed testID="listFeed" + enabled={isFocused} feed={feed} pollInterval={30e3} scrollElRef={scrollElRef} diff --git a/src/view/shell/createNativeStackNavigatorWithAuth.tsx b/src/view/shell/createNativeStackNavigatorWithAuth.tsx index c7b5d1d2e..43dc28159 100644 --- a/src/view/shell/createNativeStackNavigatorWithAuth.tsx +++ b/src/view/shell/createNativeStackNavigatorWithAuth.tsx @@ -1,5 +1,6 @@ import * as React from 'react' import {View} from 'react-native' +import {PWI_ENABLED} from '#/lib/build-flags' // Based on @react-navigation/native-stack/src/createNativeStackNavigator.ts // MIT License @@ -99,7 +100,7 @@ function NativeStackNavigator({ const {showLoggedOut} = useLoggedOutView() const {setShowLoggedOut} = useLoggedOutViewControls() const {isMobile} = useWebMediaQueries() - if (activeRouteRequiresAuth && !hasSession) { + if ((!PWI_ENABLED || activeRouteRequiresAuth) && !hasSession) { return <LoggedOut /> } if (showLoggedOut) { |