Bluesky app fork with some witchin' additions 馃挮 witchsky.app
bluesky fork client
at main 155 lines 4.9 kB view raw
1import {useCallback} from 'react' 2import {View} from 'react-native' 3import {Image} from 'expo-image' 4import {LinearGradient} from 'expo-linear-gradient' 5import {msg} from '@lingui/core/macro' 6import {useLingui} from '@lingui/react' 7import {Trans} from '@lingui/react/macro' 8 9import {atoms as a, useTheme, web} from '#/alf' 10import {Button, ButtonText} from '#/components/Button' 11import * as Dialog from '#/components/Dialog' 12import {useNuxDialogContext} from '#/components/dialogs/nuxs' 13import {Sparkle_Stroke2_Corner0_Rounded as SparkleIcon} from '#/components/icons/Sparkle' 14import {Text} from '#/components/Typography' 15import {IS_E2E, IS_NATIVE, IS_WEB} from '#/env' 16import {createIsEnabledCheck, isExistingUserAsOf} from './utils' 17 18export const enabled = createIsEnabledCheck(props => { 19 return ( 20 !IS_E2E && 21 IS_NATIVE && 22 isExistingUserAsOf( 23 '2026-02-05T00:00:00.000Z', 24 props.currentProfile.createdAt, 25 ) 26 ) 27}) 28 29export function DraftsAnnouncement() { 30 const t = useTheme() 31 const {_} = useLingui() 32 const nuxDialogs = useNuxDialogContext() 33 const control = Dialog.useDialogControl() 34 35 Dialog.useAutoOpen(control) 36 37 const onClose = useCallback(() => { 38 nuxDialogs.dismissActiveNux() 39 }, [nuxDialogs]) 40 41 return ( 42 <Dialog.Outer 43 control={control} 44 onClose={onClose} 45 nativeOptions={{preventExpansion: true}}> 46 <Dialog.Handle fill={t.palette.primary_400} /> 47 48 <Dialog.ScrollableInner 49 label={_(msg`Introducing drafts`)} 50 style={[web({maxWidth: 440})]} 51 contentContainerStyle={[ 52 { 53 paddingTop: 0, 54 paddingLeft: 0, 55 paddingRight: 0, 56 }, 57 ]}> 58 <View 59 style={[ 60 a.align_center, 61 a.overflow_hidden, 62 { 63 paddingTop: IS_WEB ? 24 : 40, 64 borderTopLeftRadius: a.rounded_md.borderRadius, 65 borderTopRightRadius: a.rounded_md.borderRadius, 66 }, 67 ]}> 68 <LinearGradient 69 colors={[t.palette.primary_100, t.palette.primary_200]} 70 locations={[0, 1]} 71 start={{x: 0, y: 0}} 72 end={{x: 0, y: 1}} 73 style={[a.absolute, a.inset_0]} 74 /> 75 <View 76 style={[a.flex_row, a.align_center, a.gap_xs, {marginBottom: -12}]}> 77 <SparkleIcon fill={t.palette.primary_800} size="sm" /> 78 <Text 79 style={[ 80 a.font_semi_bold, 81 { 82 color: t.palette.primary_800, 83 }, 84 ]}> 85 <Trans>New Feature</Trans> 86 </Text> 87 </View> 88 <Image 89 accessibilityIgnoresInvertColors 90 source={require('../../../../assets/images/drafts_announcement_nux.webp')} 91 style={[ 92 a.w_full, 93 { 94 aspectRatio: 393 / 226, 95 }, 96 ]} 97 alt={_( 98 msg({ 99 message: `A screenshot of the post composer with a new button next to the post button that says "Drafts", with a rainbow firework effect. Below, the text in the composer reads "Hey, did you hear the news? Bluesky has drafts now!!!".`, 100 comment: 101 'Contains a post that originally appeared in English. Consider translating the post text if it makes sense in your language, and noting that the post was translated from English.', 102 }), 103 )} 104 /> 105 </View> 106 <View style={[a.align_center, a.px_xl, a.pt_xl, a.gap_2xl, a.pb_sm]}> 107 <View style={[a.gap_sm, a.align_center]}> 108 <Text 109 style={[ 110 a.text_3xl, 111 a.leading_tight, 112 a.font_bold, 113 a.text_center, 114 { 115 fontSize: IS_WEB ? 28 : 32, 116 maxWidth: 300, 117 }, 118 ]}> 119 <Trans>Drafts</Trans> 120 </Text> 121 <Text 122 style={[ 123 a.text_md, 124 a.leading_snug, 125 a.text_center, 126 { 127 maxWidth: 340, 128 }, 129 ]}> 130 <Trans> 131 Not ready to hit post? Keep your best ideas in Drafts until the 132 timing is just right. 133 </Trans> 134 </Text> 135 </View> 136 137 {!IS_WEB && ( 138 <Button 139 label={_(msg`Close`)} 140 size="large" 141 color="primary" 142 onPress={() => control.close()} 143 style={[a.w_full]}> 144 <ButtonText> 145 <Trans>Finally!</Trans> 146 </ButtonText> 147 </Button> 148 )} 149 </View> 150 151 <Dialog.Close /> 152 </Dialog.ScrollableInner> 153 </Dialog.Outer> 154 ) 155}