diff --git a/bskyweb/cmd/bskyweb/server.go b/bskyweb/cmd/bskyweb/server.go index b0fde2557f..7a3b8bf16a 100644 --- a/bskyweb/cmd/bskyweb/server.go +++ b/bskyweb/cmd/bskyweb/server.go @@ -336,7 +336,11 @@ func (srv *Server) WebPost(c echo.Context) error { data["postView"] = postView data["requestURI"] = fmt.Sprintf("https://%s%s", req.Host, req.URL.Path) if postView.Embed != nil && postView.Embed.EmbedImages_View != nil { - data["imgThumbUrl"] = postView.Embed.EmbedImages_View.Images[0].Thumb + var thumbUrls []string + for i := range postView.Embed.EmbedImages_View.Images { + thumbUrls = append(thumbUrls, postView.Embed.EmbedImages_View.Images[i].Thumb) + } + data["imgThumbUrls"] = thumbUrls } return c.Render(http.StatusOK, "post.html", data) } diff --git a/bskyweb/templates/post.html b/bskyweb/templates/post.html index 55a0679fbd..307f80bbb4 100644 --- a/bskyweb/templates/post.html +++ b/bskyweb/templates/post.html @@ -25,8 +25,10 @@ {% endif -%} - {%- if imgThumbUrl %} + {%- if imgThumbUrls %} + {% for imgThumbUrl in imgThumbUrls %} + {% endfor %} {%- elif postView.Author.Avatar %} {# Don't use avatar image in cards; usually looks bad #} diff --git a/src/lib/ThemeContext.tsx b/src/lib/ThemeContext.tsx index 483c50c42d..38bd199cbd 100644 --- a/src/lib/ThemeContext.tsx +++ b/src/lib/ThemeContext.tsx @@ -1,9 +1,7 @@ -import {isWeb} from 'platform/detection' import React, {ReactNode, createContext, useContext} from 'react' import { - AppState, TextStyle, - useColorScheme as useColorScheme_BUGGY, + useColorScheme, ViewStyle, ColorSchemeName, } from 'react-native' @@ -97,37 +95,11 @@ function getTheme(theme: ColorSchemeName) { return theme === 'dark' ? darkTheme : defaultTheme } -/** - * With RN iOS, we can only "trust" the color scheme reported while the app is - * active. This is a workaround until the bug is fixed upstream. - * - * @see https://github.com/bluesky-social/social-app/pull/1417#issuecomment-1719868504 - * @see https://github.com/facebook/react-native/pull/39439 - */ -function useColorScheme_FIXED() { - const colorScheme = useColorScheme_BUGGY() - const [currentColorScheme, setCurrentColorScheme] = - React.useState(colorScheme) - - React.useEffect(() => { - // we don't need to be updating state on web - if (isWeb) return - const subscription = AppState.addEventListener('change', state => { - const isActive = state === 'active' - if (!isActive) return - setCurrentColorScheme(colorScheme) - }) - return () => subscription.remove() - }, [colorScheme]) - - return isWeb ? colorScheme : currentColorScheme -} - export const ThemeProvider: React.FC = ({ theme, children, }) => { - const colorScheme = useColorScheme_FIXED() + const colorScheme = useColorScheme() const themeValue = getTheme(theme === 'system' ? colorScheme : theme) return ( diff --git a/src/lib/api/feed-manip.ts b/src/lib/api/feed-manip.ts index 9a050fd3e5..c964693c45 100644 --- a/src/lib/api/feed-manip.ts +++ b/src/lib/api/feed-manip.ts @@ -117,11 +117,7 @@ export class FeedViewPostsSlice { } export class NoopFeedTuner { - private keyCounter = 0 - - reset() { - this.keyCounter = 0 - } + reset() {} tune( feed: FeedViewPost[], _opts?: {dryRun: boolean; maintainOrder: boolean}, @@ -131,13 +127,13 @@ export class NoopFeedTuner { } export class FeedTuner { - private keyCounter = 0 + seenKeys: Set = new Set() seenUris: Set = new Set() constructor(public tunerFns: FeedTunerFn[]) {} reset() { - this.keyCounter = 0 + this.seenKeys.clear() this.seenUris.clear() } @@ -218,11 +214,16 @@ export class FeedTuner { } if (!dryRun) { - for (const slice of slices) { + slices = slices.filter(slice => { + if (this.seenKeys.has(slice._reactKey)) { + return false + } for (const item of slice.items) { this.seenUris.add(item.post.uri) } - } + this.seenKeys.add(slice._reactKey) + return true + }) } return slices diff --git a/src/locale/i18n.ts b/src/locale/i18n.ts index 54762eb81a..6f0a46888e 100644 --- a/src/locale/i18n.ts +++ b/src/locale/i18n.ts @@ -7,7 +7,7 @@ import {messages as messagesHi} from '#/locale/locales/hi/messages' import {messages as messagesJa} from '#/locale/locales/ja/messages' import {messages as messagesFr} from '#/locale/locales/fr/messages' import {messages as messagesDe} from '#/locale/locales/de/messages' -import {messages as messagesEs} from '#/locale/locales/de/messages' +import {messages as messagesEs} from '#/locale/locales/es/messages' import {sanitizeAppLanguageSetting} from '#/locale/helpers' import {AppLanguage} from '#/locale/languages' diff --git a/src/locale/locales/de/messages.po b/src/locale/locales/de/messages.po index 3bbbf8d500..b7c2ba44ef 100644 --- a/src/locale/locales/de/messages.po +++ b/src/locale/locales/de/messages.po @@ -105,11 +105,11 @@ msgstr "Details hinzufügen" msgid "Add details to report" msgstr "Details zum Report hinzufügen" -#: src/view/com/composer/Composer.tsx:438 +#: src/view/com/composer/Composer.tsx:442 msgid "Add link card" msgstr "Link-Karte hinzufügen" -#: src/view/com/composer/Composer.tsx:441 +#: src/view/com/composer/Composer.tsx:445 msgid "Add link card:" msgstr "Link-Karte hinzufügen:" @@ -335,18 +335,22 @@ msgstr "Kamera" msgid "Can only contain letters, numbers, spaces, dashes, and underscores. Must be at least 4 characters long, but no more than 32 characters long." msgstr "Darf nur Buchstaben, Zahlen, Leerzeichen, Bindestriche und Unterstriche enthalten. Muss mindestens 4 Zeichen lang sein, darf aber nicht länger als 32 Zeichen sein." -#: src/view/com/composer/Composer.tsx:285 -#: src/view/com/composer/Composer.tsx:288 src/view/com/modals/AltImage.tsx:128 +#: src/view/com/composer/Composer.tsx:289 +#: src/view/com/composer/Composer.tsx:292 +#: src/view/com/modals/AltImage.tsx:128 #: src/view/com/modals/ChangeEmail.tsx:218 -#: src/view/com/modals/ChangeEmail.tsx:220 src/view/com/modals/Confirm.tsx:88 +#: src/view/com/modals/ChangeEmail.tsx:220 +#: src/view/com/modals/Confirm.tsx:88 #: src/view/com/modals/CreateOrEditList.tsx:267 #: src/view/com/modals/CreateOrEditList.tsx:272 #: src/view/com/modals/DeleteAccount.tsx:150 #: src/view/com/modals/DeleteAccount.tsx:223 #: src/view/com/modals/EditImage.tsx:323 #: src/view/com/modals/EditProfile.tsx:248 -#: src/view/com/modals/LinkWarning.tsx:85 src/view/com/modals/Repost.tsx:73 -#: src/view/com/modals/Waitlist.tsx:136 src/view/screens/Search/Search.tsx:584 +#: src/view/com/modals/LinkWarning.tsx:85 +#: src/view/com/modals/Repost.tsx:73 +#: src/view/com/modals/Waitlist.tsx:136 +#: src/view/screens/Search/Search.tsx:584 #: src/view/shell/desktop/Search.tsx:182 msgid "Cancel" msgstr "Abbrechen" @@ -651,6 +655,10 @@ msgstr "Entwicklungsserver" msgid "Developer Tools" msgstr "Entwickler-Tools" +#: src/view/com/composer/Composer.tsx:210 +msgid "Did you want to say anything?" +msgstr "" + #: src/view/com/composer/Composer.tsx:143 msgid "Discard" msgstr "Verwerfen" @@ -1346,7 +1354,7 @@ msgstr "Oh nein!" msgid "Okay" msgstr "Okay" -#: src/view/com/composer/Composer.tsx:354 +#: src/view/com/composer/Composer.tsx:358 msgid "One or more images is missing alt text." msgstr "Bei einem oder mehreren Bildern fehlt der Alt-Text." @@ -1467,7 +1475,11 @@ msgstr "Bitte gib auch dein Passwort ein:" msgid "Please tell us why you think this content warning was incorrectly applied!" msgstr "Bitte teile uns mit, warum du denkst, dass diese Inhaltswarnung falsch angewendet wurde!" -#: src/view/com/composer/Composer.tsx:337 +#: src/view/com/composer/Composer.tsx:214 +msgid "Please wait for your link card to finish loading" +msgstr "" + +#: src/view/com/composer/Composer.tsx:341 #: src/view/com/post-thread/PostThread.tsx:225 #: src/view/screens/PostThread.tsx:80 msgid "Post" @@ -2274,7 +2286,7 @@ msgstr "Wer antworten kann" msgid "Wide" msgstr "Breit" -#: src/view/com/composer/Composer.tsx:409 +#: src/view/com/composer/Composer.tsx:413 msgid "Write post" msgstr "Beitrag verfassen" diff --git a/src/locale/locales/en/messages.po b/src/locale/locales/en/messages.po index 063b459b48..7139489a90 100644 --- a/src/locale/locales/en/messages.po +++ b/src/locale/locales/en/messages.po @@ -130,11 +130,11 @@ msgstr "" msgid "Add details to report" msgstr "" -#: src/view/com/composer/Composer.tsx:438 +#: src/view/com/composer/Composer.tsx:442 msgid "Add link card" msgstr "" -#: src/view/com/composer/Composer.tsx:441 +#: src/view/com/composer/Composer.tsx:445 msgid "Add link card:" msgstr "" @@ -373,8 +373,8 @@ msgstr "" msgid "Can only contain letters, numbers, spaces, dashes, and underscores. Must be at least 4 characters long, but no more than 32 characters long." msgstr "" -#: src/view/com/composer/Composer.tsx:285 -#: src/view/com/composer/Composer.tsx:288 +#: src/view/com/composer/Composer.tsx:289 +#: src/view/com/composer/Composer.tsx:292 #: src/view/com/modals/AltImage.tsx:128 #: src/view/com/modals/ChangeEmail.tsx:218 #: src/view/com/modals/ChangeEmail.tsx:220 @@ -705,6 +705,10 @@ msgstr "" msgid "Developer Tools" msgstr "" +#: src/view/com/composer/Composer.tsx:210 +msgid "Did you want to say anything?" +msgstr "" + #: src/view/com/composer/Composer.tsx:143 msgid "Discard" msgstr "" @@ -1492,7 +1496,7 @@ msgstr "" msgid "Okay" msgstr "" -#: src/view/com/composer/Composer.tsx:354 +#: src/view/com/composer/Composer.tsx:358 msgid "One or more images is missing alt text." msgstr "" @@ -1620,7 +1624,11 @@ msgstr "" #~ msgid "Please tell us why you think this decision was incorrect." #~ msgstr "" -#: src/view/com/composer/Composer.tsx:337 +#: src/view/com/composer/Composer.tsx:214 +msgid "Please wait for your link card to finish loading" +msgstr "" + +#: src/view/com/composer/Composer.tsx:341 #: src/view/com/post-thread/PostThread.tsx:225 #: src/view/screens/PostThread.tsx:80 msgid "Post" @@ -2497,7 +2505,7 @@ msgstr "" msgid "Wide" msgstr "" -#: src/view/com/composer/Composer.tsx:409 +#: src/view/com/composer/Composer.tsx:413 msgid "Write post" msgstr "" diff --git a/src/locale/locales/es/messages.po b/src/locale/locales/es/messages.po index 671e9e2298..d1ea8ece83 100644 --- a/src/locale/locales/es/messages.po +++ b/src/locale/locales/es/messages.po @@ -110,11 +110,11 @@ msgstr "Agregar detalles" msgid "Add details to report" msgstr "Agregar detalles al informe" -#: src/view/com/composer/Composer.tsx:438 +#: src/view/com/composer/Composer.tsx:442 msgid "Add link card" msgstr "Agregar una tarjeta de enlace" -#: src/view/com/composer/Composer.tsx:441 +#: src/view/com/composer/Composer.tsx:445 msgid "Add link card:" msgstr "Agregar una tarjeta de enlace:" @@ -345,8 +345,8 @@ msgstr "Cámara" msgid "Can only contain letters, numbers, spaces, dashes, and underscores. Must be at least 4 characters long, but no more than 32 characters long." msgstr "Sólo puede contener letras, números, espacios, guiones y guiones bajos. Debe tener al menos 4 caracteres, pero no más de 32." -#: src/view/com/composer/Composer.tsx:285 -#: src/view/com/composer/Composer.tsx:288 +#: src/view/com/composer/Composer.tsx:289 +#: src/view/com/composer/Composer.tsx:292 #: src/view/com/modals/AltImage.tsx:128 #: src/view/com/modals/ChangeEmail.tsx:218 #: src/view/com/modals/ChangeEmail.tsx:220 @@ -669,6 +669,10 @@ msgstr "Servidor de desarrollo" msgid "Developer Tools" msgstr "Herramientas de desarrollador" +#: src/view/com/composer/Composer.tsx:210 +msgid "Did you want to say anything?" +msgstr "" + #: src/view/com/composer/Composer.tsx:143 msgid "Discard" msgstr "Descartar" @@ -1398,7 +1402,7 @@ msgstr "¡Qué problema!" msgid "Okay" msgstr "Está bien" -#: src/view/com/composer/Composer.tsx:354 +#: src/view/com/composer/Composer.tsx:358 msgid "One or more images is missing alt text." msgstr "Falta el texto alternativo en una o varias imágenes." @@ -1526,7 +1530,11 @@ msgstr "" #~ msgid "Please tell us why you think this decision was incorrect." #~ msgstr "Por favor, dinos por qué crees que esta decisión fue incorrecta." -#: src/view/com/composer/Composer.tsx:337 +#: src/view/com/composer/Composer.tsx:214 +msgid "Please wait for your link card to finish loading" +msgstr "" + +#: src/view/com/composer/Composer.tsx:341 #: src/view/com/post-thread/PostThread.tsx:225 #: src/view/screens/PostThread.tsx:80 msgid "Post" @@ -2358,7 +2366,7 @@ msgstr "Quién puede responder" msgid "Wide" msgstr "Ancho" -#: src/view/com/composer/Composer.tsx:409 +#: src/view/com/composer/Composer.tsx:413 msgid "Write post" msgstr "Redactar una publicación" diff --git a/src/locale/locales/fr/messages.po b/src/locale/locales/fr/messages.po index ca8c6af2bb..8afd0e5feb 100644 --- a/src/locale/locales/fr/messages.po +++ b/src/locale/locales/fr/messages.po @@ -110,11 +110,11 @@ msgstr "Ajouter des détails" msgid "Add details to report" msgstr "Ajouter des détails au rapport" -#: src/view/com/composer/Composer.tsx:438 +#: src/view/com/composer/Composer.tsx:442 msgid "Add link card" msgstr "Ajouter une carte link card" -#: src/view/com/composer/Composer.tsx:441 +#: src/view/com/composer/Composer.tsx:445 msgid "Add link card:" msgstr "Ajouter une carte link card :" @@ -345,8 +345,8 @@ msgstr "Caméra" msgid "Can only contain letters, numbers, spaces, dashes, and underscores. Must be at least 4 characters long, but no more than 32 characters long." msgstr "Ne peut contenir que des lettres, des chiffres, des espaces, des tirets et des tirets bas. La longueur doit être d’au moins 4 caractères, mais pas plus de 32." -#: src/view/com/composer/Composer.tsx:285 -#: src/view/com/composer/Composer.tsx:288 +#: src/view/com/composer/Composer.tsx:289 +#: src/view/com/composer/Composer.tsx:292 #: src/view/com/modals/AltImage.tsx:128 #: src/view/com/modals/ChangeEmail.tsx:218 #: src/view/com/modals/ChangeEmail.tsx:220 @@ -669,6 +669,10 @@ msgstr "Serveur de dév" msgid "Developer Tools" msgstr "Outils du dév" +#: src/view/com/composer/Composer.tsx:210 +msgid "Did you want to say anything?" +msgstr "" + #: src/view/com/composer/Composer.tsx:143 msgid "Discard" msgstr "Ignorer" @@ -1398,7 +1402,7 @@ msgstr "Oh non !" msgid "Okay" msgstr "D’accord" -#: src/view/com/composer/Composer.tsx:354 +#: src/view/com/composer/Composer.tsx:358 msgid "One or more images is missing alt text." msgstr "Une ou plusieurs images n’ont pas de texte alt." @@ -1526,7 +1530,11 @@ msgstr "" #~ msgid "Please tell us why you think this decision was incorrect." #~ msgstr "Dites-nous pourquoi vous pensez que cette décision était incorrecte." -#: src/view/com/composer/Composer.tsx:337 +#: src/view/com/composer/Composer.tsx:214 +msgid "Please wait for your link card to finish loading" +msgstr "" + +#: src/view/com/composer/Composer.tsx:341 #: src/view/com/post-thread/PostThread.tsx:225 #: src/view/screens/PostThread.tsx:80 msgid "Post" @@ -2358,7 +2366,7 @@ msgstr "Qui peut répondre ?" msgid "Wide" msgstr "Large" -#: src/view/com/composer/Composer.tsx:409 +#: src/view/com/composer/Composer.tsx:413 msgid "Write post" msgstr "Rédiger une publication" diff --git a/src/locale/locales/hi/messages.po b/src/locale/locales/hi/messages.po index 93769c2ba9..6fa32b369f 100644 --- a/src/locale/locales/hi/messages.po +++ b/src/locale/locales/hi/messages.po @@ -130,11 +130,11 @@ msgstr "विवरण जोड़ें" msgid "Add details to report" msgstr "रिपोर्ट करने के लिए विवरण जोड़ें" -#: src/view/com/composer/Composer.tsx:438 +#: src/view/com/composer/Composer.tsx:442 msgid "Add link card" msgstr "लिंक कार्ड जोड़ें" -#: src/view/com/composer/Composer.tsx:441 +#: src/view/com/composer/Composer.tsx:445 msgid "Add link card:" msgstr "लिंक कार्ड जोड़ें:" @@ -373,8 +373,8 @@ msgstr "कैमरा" msgid "Can only contain letters, numbers, spaces, dashes, and underscores. Must be at least 4 characters long, but no more than 32 characters long." msgstr "केवल अक्षर, संख्या, रिक्त स्थान, डैश और अंडरस्कोर हो सकते हैं। कम से कम 4 अक्षर लंबा होना चाहिए, लेकिन 32 अक्षरों से अधिक लंबा नहीं होना चाहिए।।" -#: src/view/com/composer/Composer.tsx:285 -#: src/view/com/composer/Composer.tsx:288 +#: src/view/com/composer/Composer.tsx:289 +#: src/view/com/composer/Composer.tsx:292 #: src/view/com/modals/AltImage.tsx:128 #: src/view/com/modals/ChangeEmail.tsx:218 #: src/view/com/modals/ChangeEmail.tsx:220 @@ -701,6 +701,10 @@ msgstr "देव सर्वर" msgid "Developer Tools" msgstr "डेवलपर उपकरण" +#: src/view/com/composer/Composer.tsx:210 +msgid "Did you want to say anything?" +msgstr "" + #: src/view/com/composer/Composer.tsx:143 msgid "Discard" msgstr "" @@ -1484,7 +1488,7 @@ msgstr "अरे नहीं!" msgid "Okay" msgstr "ठीक है" -#: src/view/com/composer/Composer.tsx:354 +#: src/view/com/composer/Composer.tsx:358 msgid "One or more images is missing alt text." msgstr "एक या अधिक छवियाँ alt पाठ याद आती हैं।।" @@ -1612,7 +1616,11 @@ msgstr "" #~ msgid "Please tell us why you think this decision was incorrect." #~ msgstr "" -#: src/view/com/composer/Composer.tsx:337 +#: src/view/com/composer/Composer.tsx:214 +msgid "Please wait for your link card to finish loading" +msgstr "" + +#: src/view/com/composer/Composer.tsx:341 #: src/view/com/post-thread/PostThread.tsx:225 #: src/view/screens/PostThread.tsx:80 msgid "Post" @@ -2489,7 +2497,7 @@ msgstr "" msgid "Wide" msgstr "चौड़ा" -#: src/view/com/composer/Composer.tsx:409 +#: src/view/com/composer/Composer.tsx:413 msgid "Write post" msgstr "पोस्ट लिखो" diff --git a/src/locale/locales/ja/messages.po b/src/locale/locales/ja/messages.po index 685554ae5e..d4b2ce3bd7 100644 --- a/src/locale/locales/ja/messages.po +++ b/src/locale/locales/ja/messages.po @@ -9,7 +9,7 @@ msgstr "" "Project-Id-Version: \n" "Report-Msgid-Bugs-To: \n" "PO-Revision-Date: \n" -"Last-Translator: Hima-Zinn\n" +"Last-Translator: noritada\n" "Language-Team: Hima-Zinn, tkusano, dolciss, oboenikui, noritada\n" "Plural-Forms: \n" @@ -110,11 +110,11 @@ msgstr "詳細を追加" msgid "Add details to report" msgstr "レポートに詳細を追加" -#: src/view/com/composer/Composer.tsx:438 +#: src/view/com/composer/Composer.tsx:442 msgid "Add link card" msgstr "リンクカードを追加" -#: src/view/com/composer/Composer.tsx:441 +#: src/view/com/composer/Composer.tsx:445 msgid "Add link card:" msgstr "リンクカードを追加:" @@ -345,8 +345,8 @@ msgstr "カメラ" msgid "Can only contain letters, numbers, spaces, dashes, and underscores. Must be at least 4 characters long, but no more than 32 characters long." msgstr "文字、数字、スペース、ハイフン、およびアンダースコアのみが使用可能です。長さは4文字以上32文字以下である必要があります。" -#: src/view/com/composer/Composer.tsx:285 -#: src/view/com/composer/Composer.tsx:288 +#: src/view/com/composer/Composer.tsx:289 +#: src/view/com/composer/Composer.tsx:292 #: src/view/com/modals/AltImage.tsx:128 #: src/view/com/modals/ChangeEmail.tsx:218 #: src/view/com/modals/ChangeEmail.tsx:220 @@ -669,6 +669,10 @@ msgstr "開発者サーバー" msgid "Developer Tools" msgstr "開発者ツール" +#: src/view/com/composer/Composer.tsx:210 +msgid "Did you want to say anything?" +msgstr "" + #: src/view/com/composer/Composer.tsx:143 msgid "Discard" msgstr "破棄" @@ -771,7 +775,7 @@ msgstr "メールアドレス:" #: src/view/screens/PreferencesHomeFeed.tsx:138 msgid "Enable this setting to only see replies between people you follow." -msgstr "この設定を有効にすると、フォローしているユーザー間の返信だけが表示されます。" +msgstr "この設定を有効にすると、自分がフォローしているユーザーからの返信だけが表示されます。" #: src/view/screens/Profile.tsx:426 msgid "End of feed" @@ -878,11 +882,11 @@ msgstr "何人かのユーザーをフォローして開始します。興味を #: src/view/com/modals/Threadgate.tsx:98 msgid "Followed users" -msgstr "フォローしているユーザー" +msgstr "自分がフォローしているユーザー" #: src/view/screens/PreferencesHomeFeed.tsx:145 msgid "Followed users only" -msgstr "フォローされたユーザーのみ" +msgstr "自分がフォローしているユーザーのみ" #: src/view/screens/ProfileFollowers.tsx:25 msgid "Followers" @@ -1011,7 +1015,7 @@ msgstr "ホーム" #: src/view/screens/PreferencesHomeFeed.tsx:95 #: src/view/screens/Settings.tsx:481 msgid "Home Feed Preferences" -msgstr "ホームフィード設定" +msgstr "ホームフィードの設定" #: src/view/com/auth/login/ForgotPasswordForm.tsx:114 msgid "Hosting provider" @@ -1144,7 +1148,7 @@ msgstr "このフィードをいいね" #: src/view/screens/PostLikedBy.tsx:27 #: src/view/screens/ProfileFeedLikedBy.tsx:27 msgid "Liked by" -msgstr "いいねした人" +msgstr "いいねしたユーザー" #: src/view/screens/Profile.tsx:164 msgid "Likes" @@ -1156,7 +1160,7 @@ msgstr "いいね" #: src/view/com/modals/CreateOrEditList.tsx:186 msgid "List Avatar" -msgstr "リストアバター" +msgstr "リストのアバター" #: src/view/com/modals/CreateOrEditList.tsx:199 msgid "List Name" @@ -1172,15 +1176,15 @@ msgstr "リスト" #: src/view/com/post-thread/PostThread.tsx:259 #: src/view/com/post-thread/PostThread.tsx:267 msgid "Load more posts" -msgstr "より多くの投稿をロード" +msgstr "投稿をさらにロード" #: src/view/screens/Notifications.tsx:144 msgid "Load new notifications" -msgstr "新しい通知をロード" +msgstr "最新の通知をロード" #: src/view/com/feeds/FeedPage.tsx:189 msgid "Load new posts" -msgstr "投稿をロード" +msgstr "最新の投稿をロード" #: src/view/com/composer/text-input/mobile/Autocomplete.tsx:95 msgid "Loading..." @@ -1278,19 +1282,19 @@ msgstr "スレッドをミュート" #: src/view/screens/Moderation.tsx:109 msgid "Muted accounts" -msgstr "ミュートされたアカウント" +msgstr "ミュート中のアカウント" #: src/view/screens/ModerationMutedAccounts.tsx:107 msgid "Muted Accounts" -msgstr "ミュートされたアカウント" +msgstr "ミュート中のアカウント" #: src/view/screens/ModerationMutedAccounts.tsx:115 msgid "Muted accounts have their posts removed from your feed and from your notifications. Mutes are completely private." -msgstr "ミュートをされたアカウントは、フィードと通知からの投稿が削除されます。ミュートの設定は完全に非公開です。" +msgstr "ミュート中のアカウントの投稿は、フィードや通知から取り除かれます。ミュートの設定は完全に非公開です。" #: src/view/screens/ProfileList.tsx:272 msgid "Muting is private. Muted accounts can interact with you, but you will not see their posts or receive notifications from them." -msgstr "ミュートは非公開です。ミュートをされたアカウントはあなたと引き続き関わることができますが、そのアカウントの投稿や通知を受信することはできません。" +msgstr "ミュートの設定は非公開です。ミュート中のアカウントはあなたと引き続き関わることができますが、そのアカウントの投稿や通知を受信することはできません。" #: src/view/com/modals/BirthDateSettings.tsx:56 msgid "My Birthday" @@ -1410,7 +1414,7 @@ msgstr "ちょっと!" msgid "Okay" msgstr "OK" -#: src/view/com/composer/Composer.tsx:354 +#: src/view/com/composer/Composer.tsx:358 msgid "One or more images is missing alt text." msgstr "1つもしくは複数の画像にALTテキストがありません。" @@ -1538,7 +1542,11 @@ msgstr "" #~ msgid "Please tell us why you think this decision was incorrect." #~ msgstr "この判断が誤っていると考える理由を教えてください。" -#: src/view/com/composer/Composer.tsx:337 +#: src/view/com/composer/Composer.tsx:214 +msgid "Please wait for your link card to finish loading" +msgstr "" + +#: src/view/com/composer/Composer.tsx:341 #: src/view/com/post-thread/PostThread.tsx:225 #: src/view/screens/PostThread.tsx:80 msgid "Post" @@ -1726,7 +1734,7 @@ msgstr "リポストまたは引用" #: src/view/screens/PostRepostedBy.tsx:27 msgid "Reposted by" -msgstr "リポストした人" +msgstr "リポストしたユーザー" #: src/view/com/modals/ChangeEmail.tsx:181 #: src/view/com/modals/ChangeEmail.tsx:183 @@ -1881,15 +1889,15 @@ msgstr "新しいパスワードを設定" #: src/view/screens/PreferencesHomeFeed.tsx:216 msgid "Set this setting to \"No\" to hide all quote posts from your feed. Reposts will still be visible." -msgstr "フィードから全ての引用を非表示にするには、この設定を「いいえ」にします。リポストは引き続き表示されます。" +msgstr "フィード内の引用をすべて非表示にするには、この設定を「いいえ」にします。リポストは引き続き表示されます。" #: src/view/screens/PreferencesHomeFeed.tsx:113 msgid "Set this setting to \"No\" to hide all replies from your feed." -msgstr "フィードから全ての返信を非表示にするには、この設定を「いいえ」にします。" +msgstr "フィード内の返信をすべて非表示にするには、この設定を「いいえ」にします。" #: src/view/screens/PreferencesHomeFeed.tsx:182 msgid "Set this setting to \"No\" to hide all reposts from your feed." -msgstr "フィードから全てのリポストを非表示にするには、この設定を「いいえ」にします。" +msgstr "フィード内のリポストをすべて非表示にするには、この設定を「いいえ」にします。" #: src/view/screens/PreferencesThreads.tsx:116 msgid "Set this setting to \"Yes\" to show replies in a threaded view. This is an experimental feature." @@ -1943,7 +1951,7 @@ msgstr "返信を表示" #: src/view/screens/PreferencesThreads.tsx:94 msgid "Show replies by people you follow before all other replies." -msgstr "他のすべての返信の前に、フォローしている人からの返信を表示します。" +msgstr "自分がフォローしているユーザーからの返信を、他のすべての返信の前に表示します。" #: src/view/screens/PreferencesHomeFeed.tsx:179 msgid "Show Reposts" @@ -2364,13 +2372,13 @@ msgstr "アルゴリズムによるフィードにはどの言語を使用しま #: src/view/com/composer/threadgate/ThreadgateBtn.tsx:47 #: src/view/com/modals/Threadgate.tsx:66 msgid "Who can reply" -msgstr "返信できる人" +msgstr "返信できるユーザー" #: src/view/com/modals/crop-image/CropImage.web.tsx:102 msgid "Wide" msgstr "ワイド" -#: src/view/com/composer/Composer.tsx:409 +#: src/view/com/composer/Composer.tsx:413 msgid "Write post" msgstr "投稿を書く" diff --git a/src/state/queries/notifications/unread.tsx b/src/state/queries/notifications/unread.tsx index a189f20e42..abaabbf0e7 100644 --- a/src/state/queries/notifications/unread.tsx +++ b/src/state/queries/notifications/unread.tsx @@ -89,6 +89,9 @@ export function Provider({children}: React.PropsWithChildren<{}>) { // update & broadcast setNumUnread('') broadcast.postMessage({event: ''}) + if (isNative) { + Notifications.setBadgeCountAsync(0) + } }, async checkUnread({invalidate}: {invalidate?: boolean} = {}) { diff --git a/src/state/queries/notifications/util.ts b/src/state/queries/notifications/util.ts index 438879b7e8..411a0f791d 100644 --- a/src/state/queries/notifications/util.ts +++ b/src/state/queries/notifications/util.ts @@ -156,7 +156,7 @@ async function fetchSubjects( ): Promise> { const uris = new Set() for (const notif of groupedNotifs) { - if (notif.subjectUri) { + if (notif.subjectUri && !notif.subjectUri.includes('feed.generator')) { uris.add(notif.subjectUri) } } @@ -216,6 +216,8 @@ function getSubjectUri( ? notif.record.subject?.uri : undefined } + } else if (type === 'feedgen-like') { + return notif.reasonSubject } } diff --git a/src/view/com/composer/Composer.tsx b/src/view/com/composer/Composer.tsx index 64427b837e..9f60923d61 100644 --- a/src/view/com/composer/Composer.tsx +++ b/src/view/com/composer/Composer.tsx @@ -207,7 +207,11 @@ export const ComposePost = observer(function ComposePost({ setError('') if (richtext.text.trim().length === 0 && gallery.isEmpty && !extLink) { - setError('Did you want to say anything?') + setError(_(msg`Did you want to say anything?`)) + return + } + if (extLink?.isLoading) { + setError(_(msg`Please wait for your link card to finish loading`)) return } @@ -438,7 +442,7 @@ export const ComposePost = observer(function ComposePost({ accessibilityLabel={_(msg`Add link card`)} accessibilityHint={`Creates a card with a thumbnail. The card links to ${url}`}> - Add link card: + Add link card:{' '} {toShortUrl(url)} diff --git a/src/view/com/modals/Threadgate.tsx b/src/view/com/modals/Threadgate.tsx index 9d78a2e6dc..0deef185b5 100644 --- a/src/view/com/modals/Threadgate.tsx +++ b/src/view/com/modals/Threadgate.tsx @@ -69,7 +69,7 @@ export function Component({ - Choose "Everybody" or "Nobody" + Choose "Everybody" or "Nobody" - Or combine these options: + Or combine these options: } @@ -166,7 +167,7 @@ let FeedItem = ({ iconStyle = [s.blue3 as FontAwesomeIconStyle] } else if (item.type === 'feedgen-like') { action = `liked your custom feed${ - item.subjectUri ? ` '${new AtUri(item.subjectUri).rkey}}'` : '' + item.subjectUri ? ` '${new AtUri(item.subjectUri).rkey}'` : '' }` icon = 'HeartIconSolid' iconStyle = [ @@ -256,6 +257,13 @@ let FeedItem = ({ {item.type === 'post-like' || item.type === 'repost' ? ( ) : null} + {item.type === 'feedgen-like' && item.subjectUri ? ( + + ) : null} ) @@ -496,6 +504,12 @@ const styles = StyleSheet.create({ marginLeft: 2, opacity: 0.8, }, + feedcard: { + borderWidth: 1, + borderRadius: 8, + paddingVertical: 12, + marginTop: 6, + }, addedContainer: { paddingTop: 4, diff --git a/src/view/com/post-thread/PostThreadItem.tsx b/src/view/com/post-thread/PostThreadItem.tsx index 6a377cdf6a..986fd70b2e 100644 --- a/src/view/com/post-thread/PostThreadItem.tsx +++ b/src/view/com/post-thread/PostThreadItem.tsx @@ -186,9 +186,9 @@ let PostThreadItemLoaded = ({ return makeProfileLink(post.author, 'post', urip.rkey, 'reposted-by') }, [post.uri, post.author]) const repostsTitle = 'Reposts of this post' - const isSelfLabeledPost = + const isModeratedPost = moderation.decisions.post.cause?.type === 'label' && - moderation.decisions.post.cause.label.src === currentAccount?.did + moderation.decisions.post.cause.label.src !== currentAccount?.did const translatorUrl = getTranslatorLink( record?.text || '', @@ -335,7 +335,7 @@ let PostThreadItemLoaded = ({ postUri={post.uri} record={record} showAppealLabelItem={ - post.author.did === currentAccount?.did && !isSelfLabeledPost + post.author.did === currentAccount?.did && isModeratedPost } style={{ paddingVertical: 6, @@ -539,6 +539,7 @@ let PostThreadItemLoaded = ({ timestamp={post.indexedAt} postHref={postHref} showAvatar={isThreadedChild} + avatarModeration={moderation.avatar} avatarSize={28} displayNameType="md-bold" displayNameStyle={isThreadedChild && s.ml2} diff --git a/src/view/com/posts/FeedItem.tsx b/src/view/com/posts/FeedItem.tsx index 2be314266f..942d7bf713 100644 --- a/src/view/com/posts/FeedItem.tsx +++ b/src/view/com/posts/FeedItem.tsx @@ -34,6 +34,7 @@ import {countLines} from 'lib/strings/helpers' import {useComposerControls} from '#/state/shell/composer' import {Shadow, usePostShadow, POST_TOMBSTONE} from '#/state/cache/post-shadow' import {FeedNameText} from '../util/FeedInfoText' +import {useSession} from '#/state/session' export function FeedItem({ post, @@ -102,10 +103,14 @@ let FeedItemInner = ({ }): React.ReactNode => { const {openComposer} = useComposerControls() const pal = usePalette('default') + const {currentAccount} = useSession() const href = useMemo(() => { const urip = new AtUri(post.uri) return makeProfileLink(post.author, 'post', urip.rkey) }, [post.uri, post.author]) + const isModeratedPost = + moderation.decisions.post.cause?.type === 'label' && + moderation.decisions.post.cause.label.src !== currentAccount?.did const replyAuthorDid = useMemo(() => { if (!record?.reply) { @@ -284,7 +289,14 @@ let FeedItemInner = ({ postEmbed={post.embed} postAuthor={post.author} /> - + diff --git a/src/view/com/util/PostMeta.tsx b/src/view/com/util/PostMeta.tsx index eef7094cd7..b9c3842b35 100644 --- a/src/view/com/util/PostMeta.tsx +++ b/src/view/com/util/PostMeta.tsx @@ -11,6 +11,7 @@ import {sanitizeHandle} from 'lib/strings/handles' import {isAndroid} from 'platform/detection' import {TimeElapsed} from './TimeElapsed' import {makeProfileLink} from 'lib/routes/links' +import {ModerationUI} from '@atproto/api' interface PostMetaOpts { author: { @@ -23,6 +24,7 @@ interface PostMetaOpts { postHref: string timestamp: string showAvatar?: boolean + avatarModeration?: ModerationUI avatarSize?: number displayNameType?: TypographyVariant displayNameStyle?: StyleProp @@ -41,7 +43,7 @@ let PostMeta = (opts: PostMetaOpts): React.ReactNode => { )} diff --git a/src/view/com/util/post-ctrls/PostCtrls.tsx b/src/view/com/util/post-ctrls/PostCtrls.tsx index 414fb1e094..a50b521750 100644 --- a/src/view/com/util/post-ctrls/PostCtrls.tsx +++ b/src/view/com/util/post-ctrls/PostCtrls.tsx @@ -31,12 +31,14 @@ let PostCtrls = ({ big, post, record, + showAppealLabelItem, style, onPressReply, }: { big?: boolean post: Shadow record: AppBskyFeedPost.Record + showAppealLabelItem?: boolean style?: StyleProp onPressReply: () => void }): React.ReactNode => { @@ -207,6 +209,7 @@ let PostCtrls = ({ postCid={post.cid} postUri={post.uri} record={record} + showAppealLabelItem={showAppealLabelItem} style={styles.ctrlPad} /> )} diff --git a/src/view/screens/Notifications.tsx b/src/view/screens/Notifications.tsx index e28a67e370..6e2f183056 100644 --- a/src/view/screens/Notifications.tsx +++ b/src/view/screens/Notifications.tsx @@ -1,6 +1,6 @@ import React from 'react' import {View} from 'react-native' -import {useFocusEffect} from '@react-navigation/native' +import {useFocusEffect, useIsFocused} from '@react-navigation/native' import {useQueryClient} from '@tanstack/react-query' import { NativeStackScreenProps, @@ -46,6 +46,7 @@ export function NotificationsScreen({}: Props) { const unreadNotifs = useUnreadNotifications() const unreadApi = useUnreadNotificationsApi() const hasNew = !!unreadNotifs + const isScreenFocused = useIsFocused() // event handlers // = @@ -83,8 +84,11 @@ export function NotificationsScreen({}: Props) { }, [screen, setMinimalShellMode]), ) React.useEffect(() => { + if (!isScreenFocused) { + return + } return listenSoftReset(onPressLoadLatest) - }, [onPressLoadLatest]) + }, [onPressLoadLatest, isScreenFocused]) const ListHeaderComponent = React.useCallback(() => { if (isDesktop) { diff --git a/src/view/screens/PreferencesHomeFeed.tsx b/src/view/screens/PreferencesHomeFeed.tsx index fe17be5e80..20ef729236 100644 --- a/src/view/screens/PreferencesHomeFeed.tsx +++ b/src/view/screens/PreferencesHomeFeed.tsx @@ -117,7 +117,7 @@ export function PreferencesHomeFeed({navigation}: Props) { setFeedViewPref({ diff --git a/src/view/screens/ProfileFeed.tsx b/src/view/screens/ProfileFeed.tsx index cde39a33f4..211306c0d0 100644 --- a/src/view/screens/ProfileFeed.tsx +++ b/src/view/screens/ProfileFeed.tsx @@ -57,6 +57,7 @@ import {useLikeMutation, useUnlikeMutation} from '#/state/queries/like' import {useComposerControls} from '#/state/shell/composer' import {truncateAndInvalidate} from '#/state/queries/util' import {isNative} from '#/platform/detection' +import {listenSoftReset} from '#/state/events' const SECTION_TITLES = ['Posts', 'About'] @@ -446,6 +447,7 @@ const FeedSection = React.forwardRef( const [hasNew, setHasNew] = React.useState(false) const [isScrolledDown, setIsScrolledDown] = React.useState(false) const queryClient = useQueryClient() + const isScreenFocused = useIsFocused() const onScrollToTop = useCallback(() => { scrollElRef.current?.scrollToOffset({ @@ -460,6 +462,13 @@ const FeedSection = React.forwardRef( scrollToTop: onScrollToTop, })) + React.useEffect(() => { + if (!isScreenFocused) { + return + } + return listenSoftReset(onScrollToTop) + }, [onScrollToTop, isScreenFocused]) + const renderPostsEmpty = useCallback(() => { return }, []) diff --git a/src/view/screens/ProfileList.tsx b/src/view/screens/ProfileList.tsx index 2db768cc57..c51758ae51 100644 --- a/src/view/screens/ProfileList.tsx +++ b/src/view/screens/ProfileList.tsx @@ -57,6 +57,7 @@ import { } from '#/state/queries/preferences' import {logger} from '#/logger' import {useAnalytics} from '#/lib/analytics/analytics' +import {listenSoftReset} from '#/state/events' const SECTION_TITLES_CURATE = ['Posts', 'About'] const SECTION_TITLES_MOD = ['About'] @@ -601,6 +602,7 @@ const FeedSection = React.forwardRef( const queryClient = useQueryClient() const [hasNew, setHasNew] = React.useState(false) const [isScrolledDown, setIsScrolledDown] = React.useState(false) + const isScreenFocused = useIsFocused() const onScrollToTop = useCallback(() => { scrollElRef.current?.scrollToOffset({ @@ -614,6 +616,13 @@ const FeedSection = React.forwardRef( scrollToTop: onScrollToTop, })) + React.useEffect(() => { + if (!isScreenFocused) { + return + } + return listenSoftReset(onScrollToTop) + }, [onScrollToTop, isScreenFocused]) + const renderPostsEmpty = useCallback(() => { return }, []) diff --git a/src/view/screens/Search/Search.tsx b/src/view/screens/Search/Search.tsx index 60fd216749..b522edfba5 100644 --- a/src/view/screens/Search/Search.tsx +++ b/src/view/screens/Search/Search.tsx @@ -212,12 +212,17 @@ function SearchScreenPostResults({query}: {query: string}) { const items = React.useMemo(() => { let temp: SearchResultSlice[] = [] + const seenUris = new Set() for (const post of posts) { + if (seenUris.has(post.uri)) { + continue + } temp.push({ type: 'post', key: post.uri, post, }) + seenUris.add(post.uri) } if (isFetchingNextPage) {