Bluesky app fork with some witchin' additions 💫
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

Always show post dropdown button at the bottom of the post, add share button to highlighted post (#2646)

* Always show post dropdown at the bottom

* Rm useless view (no longer needed)

* space icons evenly in big, add equal padding

* add share icon

* add onShare

* confirmed figma noob. figured it out.

* use our svg naming strat

* Update icon

---------

Co-authored-by: Hailey <me@haileyok.com>
Co-authored-by: Eric Bailey <git@esb.lol>

authored by

dan
Hailey
Eric Bailey
and committed by
GitHub
ad8f9e56 7f4dbe94

+51 -39
+1
assets/icons/arrowOutOfBox_stroke2_corner0_rounded.svg
··· 1 + <svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24"><path fill="#000" fill-rule="evenodd" d="M12.707 3.293a1 1 0 0 0-1.414 0l-4.5 4.5a1 1 0 0 0 1.414 1.414L11 6.414v8.836a1 1 0 1 0 2 0V6.414l2.793 2.793a1 1 0 1 0 1.414-1.414l-4.5-4.5ZM5 12.75a1 1 0 1 0-2 0V20a1 1 0 0 0 1 1h16a1 1 0 0 0 1-1v-7.25a1 1 0 1 0-2 0V19H5v-6.25Z" clip-rule="evenodd"/></svg>
+5
src/components/icons/ArrowOutOfBox.tsx
··· 1 + import {createSinglePathSVG} from './TEMPLATE' 2 + 3 + export const ArrowOutOfBox_Stroke2_Corner0_Rounded = createSinglePathSVG({ 4 + path: 'M12.707 3.293a1 1 0 0 0-1.414 0l-4.5 4.5a1 1 0 0 0 1.414 1.414L11 6.414v8.836a1 1 0 1 0 2 0V6.414l2.793 2.793a1 1 0 1 0 1.414-1.414l-4.5-4.5ZM5 12.75a1 1 0 1 0-2 0V20a1 1 0 0 0 1 1h16a1 1 0 0 0 1-1v-7.25a1 1 0 1 0-2 0V19H5v-6.25Z', 5 + })
+1 -24
src/view/com/post-thread/PostThreadItem.tsx
··· 23 23 import {PostMeta} from '../util/PostMeta' 24 24 import {PostEmbeds} from '../util/post-embeds' 25 25 import {PostCtrls} from '../util/post-ctrls/PostCtrls' 26 - import {PostDropdownBtn} from '../util/forms/PostDropdownBtn' 27 26 import {PostHider} from '../util/moderation/PostHider' 28 27 import {ContentHider} from '../util/moderation/ContentHider' 29 28 import {PostAlerts} from '../util/moderation/PostAlerts' ··· 43 42 import {useOpenLink} from '#/state/preferences/in-app-browser' 44 43 import {Shadow, usePostShadow, POST_TOMBSTONE} from '#/state/cache/post-shadow' 45 44 import {ThreadPost} from '#/state/queries/post-thread' 46 - import {useSession} from '#/state/session' 47 45 import {WhoCanReply} from '../threadgate/WhoCanReply' 48 46 49 47 export function PostThreadItem({ ··· 162 160 const {_} = useLingui() 163 161 const langPrefs = useLanguagePrefs() 164 162 const {openComposer} = useComposerControls() 165 - const {currentAccount} = useSession() 166 163 const [limitLines, setLimitLines] = React.useState( 167 164 () => countLines(richText?.text) >= MAX_POST_LINES, 168 165 ) ··· 188 185 return makeProfileLink(post.author, 'post', urip.rkey, 'reposted-by') 189 186 }, [post.uri, post.author]) 190 187 const repostsTitle = _(msg`Reposts of this post`) 191 - const isModeratedPost = 192 - moderation.decisions.post.cause?.type === 'label' && 193 - moderation.decisions.post.cause.label.src !== currentAccount?.did 194 188 195 189 const translatorUrl = getTranslatorLink( 196 190 record?.text || '', ··· 331 325 </Link> 332 326 </View> 333 327 </View> 334 - <PostDropdownBtn 335 - testID="postDropdownBtn" 336 - postAuthor={post.author} 337 - postCid={post.cid} 338 - postUri={post.uri} 339 - record={record} 340 - richText={richText} 341 - showAppealLabelItem={ 342 - post.author.did === currentAccount?.did && isModeratedPost 343 - } 344 - style={{ 345 - paddingVertical: 6, 346 - paddingHorizontal: 10, 347 - marginLeft: 'auto', 348 - width: 40, 349 - }} 350 - /> 351 328 </View> 352 329 <View style={[s.pl10, s.pr10, s.pb10]}> 353 330 <ContentHider ··· 437 414 ) : ( 438 415 <></> 439 416 )} 440 - <View style={[s.pl10, s.pb5]}> 417 + <View style={[s.pl10, s.pr10, s.pb5]}> 441 418 <PostCtrls 442 419 big 443 420 post={post}
+44 -15
src/view/com/util/post-ctrls/PostCtrls.tsx
··· 9 9 import { 10 10 AppBskyFeedDefs, 11 11 AppBskyFeedPost, 12 + AtUri, 12 13 RichText as RichTextAPI, 13 14 } from '@atproto/api' 14 15 import {Text} from '../text/Text' ··· 30 31 import {useRequireAuth} from '#/state/session' 31 32 import {msg} from '@lingui/macro' 32 33 import {useLingui} from '@lingui/react' 34 + import {ArrowOutOfBox_Stroke2_Corner0_Rounded as ArrowOutOfBox} from '#/components/icons/ArrowOutOfBox' 35 + import {toShareUrl} from 'lib/strings/url-helpers' 36 + import {shareUrl} from 'lib/sharing' 37 + import {makeProfileLink} from 'lib/routes/links' 33 38 34 39 let PostCtrls = ({ 35 40 big, ··· 116 121 closeModal, 117 122 ]) 118 123 124 + const onShare = useCallback(() => { 125 + const urip = new AtUri(post.uri) 126 + const href = makeProfileLink(post.author, 'post', urip.rkey) 127 + const url = toShareUrl(href) 128 + shareUrl(url) 129 + }, [post.uri, post.author]) 130 + 119 131 return ( 120 132 <View style={[styles.ctrls, style]}> 121 133 <View 122 134 style={[ 123 - styles.ctrl, 135 + big ? styles.ctrlBig : styles.ctrl, 124 136 post.viewer?.replyDisabled ? {opacity: 0.5} : undefined, 125 137 ]}> 126 138 <TouchableOpacity ··· 149 161 ) : undefined} 150 162 </TouchableOpacity> 151 163 </View> 152 - <View style={styles.ctrl}> 164 + <View style={big ? styles.ctrlBig : styles.ctrl}> 153 165 <RepostButton 154 166 big={big} 155 167 isReposted={!!post.viewer?.repost} ··· 158 170 onQuote={onQuote} 159 171 /> 160 172 </View> 161 - <View style={styles.ctrl}> 173 + <View style={big ? styles.ctrlBig : styles.ctrl}> 162 174 <TouchableOpacity 163 175 testID="likeBtn" 164 176 style={[styles.btn, !big && styles.btnPad]} ··· 193 205 ) : undefined} 194 206 </TouchableOpacity> 195 207 </View> 196 - {big ? undefined : ( 197 - <View style={styles.ctrl}> 198 - <PostDropdownBtn 199 - testID="postDropdownBtn" 200 - postAuthor={post.author} 201 - postCid={post.cid} 202 - postUri={post.uri} 203 - record={record} 204 - richText={richText} 205 - showAppealLabelItem={showAppealLabelItem} 206 - style={styles.btnPad} 207 - /> 208 + {big && ( 209 + <View style={styles.ctrlBig}> 210 + <TouchableOpacity 211 + testID="likeBtn" 212 + style={[styles.btn]} 213 + onPress={onShare} 214 + accessibilityRole="button" 215 + accessibilityLabel={`${ 216 + post.viewer?.like ? _(msg`Unlike`) : _(msg`Like`) 217 + } (${post.likeCount} ${pluralize(post.likeCount || 0, 'like')})`} 218 + accessibilityHint="" 219 + hitSlop={big ? HITSLOP_20 : HITSLOP_10}> 220 + <ArrowOutOfBox style={[defaultCtrlColor, styles.mt1]} width={22} /> 221 + </TouchableOpacity> 208 222 </View> 209 223 )} 224 + <View style={big ? styles.ctrlBig : styles.ctrl}> 225 + <PostDropdownBtn 226 + testID="postDropdownBtn" 227 + postAuthor={post.author} 228 + postCid={post.cid} 229 + postUri={post.uri} 230 + record={record} 231 + richText={richText} 232 + showAppealLabelItem={showAppealLabelItem} 233 + style={styles.btnPad} 234 + /> 235 + </View> 210 236 </View> 211 237 ) 212 238 } ··· 222 248 ctrl: { 223 249 flex: 1, 224 250 alignItems: 'flex-start', 251 + }, 252 + ctrlBig: { 253 + alignItems: 'center', 225 254 }, 226 255 btn: { 227 256 flexDirection: 'row',