diff options
author | Samuel Newman <mozzius@protonmail.com> | 2025-09-05 18:34:00 +0300 |
---|---|---|
committer | GitHub <noreply@github.com> | 2025-09-05 08:34:00 -0700 |
commit | ee3e08393882a9d72ae9cab5f765ed2885c5a98d (patch) | |
tree | a18396cf22b84b22073059922819e278890cc36a /src/view/com/composer/select-language | |
parent | 0f089060d2596bf75f141d1d574f14952bca1066 (diff) | |
download | voidsky-ee3e08393882a9d72ae9cab5f765ed2885c5a98d.tar.zst |
Restore quick language select (#8981)
* restore quick language select * rm showCancel * rm margin from thread button * alf composer icons * stop hiding keyboard * use trans
Diffstat (limited to 'src/view/com/composer/select-language')
-rw-r--r-- | src/view/com/composer/select-language/PostLanguageSelect.tsx | 131 | ||||
-rw-r--r-- | src/view/com/composer/select-language/PostLanguageSelectDialog.tsx (renamed from src/view/com/composer/select-language/SelectPostLanguagesDialog.tsx) | 80 |
2 files changed, 139 insertions, 72 deletions
diff --git a/src/view/com/composer/select-language/PostLanguageSelect.tsx b/src/view/com/composer/select-language/PostLanguageSelect.tsx new file mode 100644 index 000000000..6291e8422 --- /dev/null +++ b/src/view/com/composer/select-language/PostLanguageSelect.tsx @@ -0,0 +1,131 @@ +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' + +import {LANG_DROPDOWN_HITSLOP} from '#/lib/constants' +import {codeToLanguageName} from '#/locale/helpers' +import { + toPostLanguages, + useLanguagePrefs, + useLanguagePrefsApi, +} from '#/state/preferences/languages' +import {atoms as a, useTheme} from '#/alf' +import {Button, type ButtonProps} from '#/components/Button' +import * as Dialog from '#/components/Dialog' +import {ChevronRight_Stroke2_Corner0_Rounded as ChevronRightIcon} from '#/components/icons/Chevron' +import {Globe_Stroke2_Corner0_Rounded as GlobeIcon} from '#/components/icons/Globe' +import * as Menu from '#/components/Menu' +import {Text} from '#/components/Typography' +import {PostLanguageSelectDialog} from './PostLanguageSelectDialog' + +export function PostLanguageSelect() { + const {_} = useLingui() + const langPrefs = useLanguagePrefs() + const setLangPrefs = useLanguagePrefsApi() + const languageDialogControl = Dialog.useDialogControl() + + const dedupedHistory = Array.from( + new Set([...langPrefs.postLanguageHistory, langPrefs.postLanguage]), + ) + + if ( + dedupedHistory.length === 1 && + dedupedHistory[0] === langPrefs.postLanguage + ) { + return ( + <> + <LanguageBtn onPress={languageDialogControl.open} /> + <PostLanguageSelectDialog control={languageDialogControl} /> + </> + ) + } + + return ( + <> + <Menu.Root> + <Menu.Trigger label={_(msg`Select post language`)}> + {({props}) => <LanguageBtn {...props} />} + </Menu.Trigger> + <Menu.Outer> + <Menu.Group> + {dedupedHistory.map(historyItem => { + const langCodes = historyItem.split(',') + const langName = langCodes + .map(code => codeToLanguageName(code, langPrefs.appLanguage)) + .join(' + ') + return ( + <Menu.Item + key={historyItem} + label={_(msg`Select ${langName}`)} + onPress={() => setLangPrefs.setPostLanguage(historyItem)}> + <Menu.ItemText>{langName}</Menu.ItemText> + <Menu.ItemRadio + selected={historyItem === langPrefs.postLanguage} + /> + </Menu.Item> + ) + })} + </Menu.Group> + <Menu.Divider /> + <Menu.Item + label={_(msg`More languages...`)} + onPress={languageDialogControl.open}> + <Menu.ItemText> + <Trans>More languages...</Trans> + </Menu.ItemText> + <Menu.ItemIcon icon={ChevronRightIcon} /> + </Menu.Item> + </Menu.Outer> + </Menu.Root> + + <PostLanguageSelectDialog control={languageDialogControl} /> + </> + ) +} + +function LanguageBtn(props: Omit<ButtonProps, 'label' | 'children'>) { + const {_} = useLingui() + const langPrefs = useLanguagePrefs() + const t = useTheme() + + const postLanguagesPref = toPostLanguages(langPrefs.postLanguage) + + return ( + <Button + testID="selectLangBtn" + size="small" + hitSlop={LANG_DROPDOWN_HITSLOP} + label={_( + msg({ + message: `Post language selection`, + comment: `Accessibility label for button that opens dialog to choose post language settings`, + }), + )} + accessibilityHint={_(msg`Opens post language settings`)} + style={[a.mr_xs]} + {...props}> + {({pressed, hovered}) => { + const color = + pressed || hovered ? t.palette.primary_300 : t.palette.primary_500 + if (postLanguagesPref.length > 0) { + return ( + <Text + style={[ + {color}, + a.font_bold, + a.text_sm, + a.leading_snug, + {maxWidth: 100}, + ]} + numberOfLines={1}> + {postLanguagesPref + .map(lang => codeToLanguageName(lang, langPrefs.appLanguage)) + .join(', ')} + </Text> + ) + } else { + return <GlobeIcon size="xs" style={{color}} /> + } + }} + </Button> + ) +} diff --git a/src/view/com/composer/select-language/SelectPostLanguagesDialog.tsx b/src/view/com/composer/select-language/PostLanguageSelectDialog.tsx index c8ecc2b89..1137415e6 100644 --- a/src/view/com/composer/select-language/SelectPostLanguagesDialog.tsx +++ b/src/view/com/composer/select-language/PostLanguageSelectDialog.tsx @@ -1,16 +1,13 @@ import {useCallback, useMemo, useState} from 'react' -import {Keyboard, useWindowDimensions, View} from 'react-native' +import {useWindowDimensions, View} from 'react-native' import {useSafeAreaInsets} from 'react-native-safe-area-context' import {msg, Trans} from '@lingui/macro' import {useLingui} from '@lingui/react' -import {LANG_DROPDOWN_HITSLOP} from '#/lib/constants' import {languageName} from '#/locale/helpers' -import {codeToLanguageName} from '#/locale/helpers' import {type Language, LANGUAGES, LANGUAGES_MAP_CODE2} from '#/locale/languages' import {isNative, isWeb} from '#/platform/detection' import { - toPostLanguages, useLanguagePrefs, useLanguagePrefsApi, } from '#/state/preferences/languages' @@ -21,75 +18,14 @@ import {Button, ButtonIcon, ButtonText} from '#/components/Button' import * as Dialog from '#/components/Dialog' import {SearchInput} from '#/components/forms/SearchInput' import * as Toggle from '#/components/forms/Toggle' -import {Globe_Stroke2_Corner0_Rounded as GlobeIcon} from '#/components/icons/Globe' import {TimesLarge_Stroke2_Corner0_Rounded as XIcon} from '#/components/icons/Times' import {Text} from '#/components/Typography' -export function SelectPostLanguagesBtn() { - const {_} = useLingui() - const langPrefs = useLanguagePrefs() - const t = useTheme() - const control = Dialog.useDialogControl() - - const onPressMore = useCallback(async () => { - if (isNative) { - if (Keyboard.isVisible()) { - Keyboard.dismiss() - } - } - control.open() - }, [control]) - - const postLanguagesPref = toPostLanguages(langPrefs.postLanguage) - - return ( - <> - <Button - testID="selectLangBtn" - onPress={onPressMore} - size="small" - hitSlop={LANG_DROPDOWN_HITSLOP} - label={_( - msg({ - message: `Post language selection`, - comment: `Accessibility label for button that opens dialog to choose post language settings`, - }), - )} - accessibilityHint={_(msg`Opens post language settings`)} - style={[a.mx_md]}> - {({pressed, hovered, focused}) => { - const color = - pressed || hovered || focused - ? t.palette.primary_300 - : t.palette.primary_500 - if (postLanguagesPref.length > 0) { - return ( - <Text - style={[ - {color}, - a.font_bold, - a.text_sm, - a.leading_snug, - {maxWidth: 100}, - ]} - numberOfLines={1}> - {postLanguagesPref - .map(lang => codeToLanguageName(lang, langPrefs.appLanguage)) - .join(', ')} - </Text> - ) - } else { - return <GlobeIcon size="xs" style={{color}} /> - } - }} - </Button> - - <LanguageDialog control={control} /> - </> - ) -} - -function LanguageDialog({control}: {control: Dialog.DialogControlProps}) { +export function PostLanguageSelectDialog({ + control, +}: { + control: Dialog.DialogControlProps +}) { const {height} = useWindowDimensions() const insets = useSafeAreaInsets() @@ -104,13 +40,13 @@ function LanguageDialog({control}: {control: Dialog.DialogControlProps}) { nativeOptions={{minHeight: height - insets.top}}> <Dialog.Handle /> <ErrorBoundary renderError={renderErrorBoundary}> - <PostLanguagesSettingsDialogInner /> + <DialogInner /> </ErrorBoundary> </Dialog.Outer> ) } -export function PostLanguagesSettingsDialogInner() { +export function DialogInner() { const control = Dialog.useDialogContext() const [headerHeight, setHeaderHeight] = useState(0) |