1
0
mirror of https://github.com/tooot-app/app synced 2025-06-05 22:19:13 +02:00

Update color scheme

This commit is contained in:
Zhiyuan Zheng
2020-12-26 00:40:27 +01:00
parent 9d1c366eda
commit 7f574576ef
17 changed files with 138 additions and 108 deletions

View File

@ -171,20 +171,25 @@ export const Index: React.FC<Props> = ({ localCorrupt }) => {
})} })}
tabBarOptions={{ tabBarOptions={{
activeTintColor: theme.primary, activeTintColor: theme.primary,
inactiveTintColor: localInstance ? theme.secondary : theme.disabled, inactiveTintColor: theme.secondary,
showLabel: false showLabel: false
}} }}
> >
<Tab.Screen <Tab.Screen
name='Screen-Local' name='Screen-Local'
component={ScreenLocal} component={ScreenLocal}
listeners={{ listeners={({ navigation }) => ({
tabPress: e => { tabPress: e => {
if (!localInstance) { if (!localInstance) {
e.preventDefault() e.preventDefault()
toast({
type: 'error',
content: '请先登录',
onHide: () => navigation.navigate('Screen-Me')
})
} }
} }
}} })}
/> />
<Tab.Screen name='Screen-Public' component={ScreenPublic} /> <Tab.Screen name='Screen-Public' component={ScreenPublic} />
<Tab.Screen <Tab.Screen
@ -192,10 +197,17 @@ export const Index: React.FC<Props> = ({ localCorrupt }) => {
listeners={({ navigation }) => ({ listeners={({ navigation }) => ({
tabPress: e => { tabPress: e => {
e.preventDefault() e.preventDefault()
localInstance && if (localInstance) {
navigation.navigate(getCurrentTab(navigation), { navigation.navigate(getCurrentTab(navigation), {
screen: 'Screen-Shared-Compose' screen: 'Screen-Shared-Compose'
}) })
} else {
toast({
type: 'error',
content: '请先登录',
onHide: () => navigation.navigate('Screen-Me')
})
}
} }
})} })}
> >
@ -207,15 +219,23 @@ export const Index: React.FC<Props> = ({ localCorrupt }) => {
options={{ options={{
tabBarBadge: tabBarBadge:
prevNotification && prevNotification.unread ? '' : undefined, prevNotification && prevNotification.unread ? '' : undefined,
tabBarBadgeStyle: { transform: [{ scale: 0.5 }] } tabBarBadgeStyle: {
transform: [{ scale: 0.5 }],
backgroundColor: theme.red
}
}} }}
listeners={{ listeners={({ navigation }) => ({
tabPress: e => { tabPress: e => {
if (!localInstance) { if (!localInstance) {
e.preventDefault() e.preventDefault()
toast({
type: 'error',
content: '请先登录',
onHide: () => navigation.navigate('Screen-Me')
})
} }
} }
}} })}
/> />
<Tab.Screen name='Screen-Me' component={ScreenMe} /> <Tab.Screen name='Screen-Me' component={ScreenMe} />
</Tab.Navigator> </Tab.Navigator>

View File

@ -27,7 +27,7 @@ const Core: React.FC<Props> = ({ text, destructive = false }) => {
return ( return (
<View style={styles.core}> <View style={styles.core}>
<Text style={{ color: destructive ? theme.error : theme.primary }}> <Text style={{ color: destructive ? theme.red : theme.primary }}>
{text} {text}
</Text> </Text>
</View> </View>

View File

@ -36,7 +36,7 @@ const renderNode = ({
<Text <Text
key={index} key={index}
style={{ style={{
color: theme.link, color: theme.blue,
fontSize: StyleConstants.Font.Size[size] fontSize: StyleConstants.Font.Size[size]
}} }}
onPress={() => { onPress={() => {
@ -55,7 +55,7 @@ const renderNode = ({
<Text <Text
key={index} key={index}
style={{ style={{
color: theme.link, color: theme.blue,
fontSize: StyleConstants.Font.Size[size] fontSize: StyleConstants.Font.Size[size]
}} }}
onPress={() => { onPress={() => {
@ -79,7 +79,7 @@ const renderNode = ({
<Text <Text
key={index} key={index}
style={{ style={{
color: theme.link, color: theme.blue,
fontSize: StyleConstants.Font.Size[size] fontSize: StyleConstants.Font.Size[size]
}} }}
onPress={async () => await openLink(href)} onPress={async () => await openLink(href)}
@ -87,7 +87,7 @@ const renderNode = ({
<Feather <Feather
name='external-link' name='external-link'
size={StyleConstants.Font.Size[size]} size={StyleConstants.Font.Size[size]}
color={theme.link} color={theme.blue}
/>{' '} />{' '}
{showFullLink ? href : domain[1]} {showFullLink ? href : domain[1]}
</Text> </Text>
@ -152,7 +152,7 @@ const ParseContent: React.FC<Props> = ({
const [totalLines, setTotalLines] = useState<number | undefined>() const [totalLines, setTotalLines] = useState<number | undefined>()
const [lineHeight, setLineHeight] = useState<number | undefined>() const [lineHeight, setLineHeight] = useState<number | undefined>()
const [shownLines, setShownLines] = useState(numberOfLines) const [shownLines, setShownLines] = useState(numberOfLines)
// console.log(children)
return ( return (
<> <>
<Text <Text

View File

@ -143,16 +143,19 @@ const TimelineActions: React.FC<Props> = ({
} }
}) })
}, []) }, [])
const onPressReblog = useCallback( const onPressReblog = useCallback(() => {
() => if (status.visibility === 'private' || status.visibility === 'direct') {
console.log('awjerio')
toast({ type: 'error', content: '禁止转发' })
} else {
mutate({ mutate({
id: status.id, id: status.id,
type: 'reblog', type: 'reblog',
stateKey: 'reblogged', stateKey: 'reblogged',
prevState: status.reblogged prevState: status.reblogged
}), })
[status.reblogged] }
) }, [status.reblogged])
const onPressFavourite = useCallback( const onPressFavourite = useCallback(
() => () =>
mutate({ mutate({
@ -218,11 +221,7 @@ const TimelineActions: React.FC<Props> = ({
() => ( () => (
<Feather <Feather
name='repeat' name='repeat'
color={ color={iconColorAction(status.reblogged)}
status.visibility === 'public' || status.visibility === 'unlisted'
? iconColorAction(status.reblogged)
: theme.disabled
}
size={StyleConstants.Font.Size.M + 2} size={StyleConstants.Font.Size.M + 2}
/> />
), ),
@ -270,11 +269,7 @@ const TimelineActions: React.FC<Props> = ({
<Pressable <Pressable
style={styles.action} style={styles.action}
onPress={ onPress={onPressReblog}
status.visibility === 'public' || status.visibility === 'unlisted'
? onPressReblog
: null
}
children={childrenReblog} children={childrenReblog}
/> />

View File

@ -93,8 +93,8 @@ const AttachmentAudio: React.FC<Props> = ({ sensitiveShown, audio }) => {
minimumValue={0} minimumValue={0}
maximumValue={audio.meta.original.duration * 1000} maximumValue={audio.meta.original.duration * 1000}
value={audioPosition} value={audioPosition}
minimumTrackTintColor={theme.secondary} minimumTrackTintColor={theme.primary}
maximumTrackTintColor={theme.disabled} maximumTrackTintColor={theme.secondary}
onSlidingStart={() => { onSlidingStart={() => {
audioPlayer?.pauseAsync() audioPlayer?.pauseAsync()
setAudioPlaying(false) setAudioPlaying(false)

View File

@ -53,6 +53,11 @@ const ToastBase = ({ config }: { config: Config }) => {
error: 'x-circle', error: 'x-circle',
warning: 'alert-circle' warning: 'alert-circle'
} }
enum colorMapping {
success = 'blue',
error = 'red',
warning = 'primary'
}
return ( return (
<SafeAreaView <SafeAreaView
@ -65,7 +70,7 @@ const ToastBase = ({ config }: { config: Config }) => {
<Feather <Feather
// @ts-ignore // @ts-ignore
name={iconSet[config.type]} name={iconSet[config.type]}
color={theme[config.type]} color={theme[colorMapping[config.type]]}
size={StyleConstants.Font.Size.M + 2} size={StyleConstants.Font.Size.M + 2}
/> />
<View style={styles.texts}> <View style={styles.texts}>

View File

@ -31,6 +31,8 @@ import { StyleConstants } from '@utils/styles/constants'
import { useTheme } from '@utils/styles/ThemeManager' import { useTheme } from '@utils/styles/ThemeManager'
import formatText from '@screens/Shared/Compose/formatText' import formatText from '@screens/Shared/Compose/formatText'
import { useQueryClient } from 'react-query' import { useQueryClient } from 'react-query'
import Toast from 'react-native-toast-message'
import { toastConfig } from '@root/components/toast'
const Stack = createNativeStackNavigator() const Stack = createNativeStackNavigator()
@ -566,8 +568,7 @@ const Compose: React.FC<Props> = ({ route: { params }, navigation }) => {
style={[ style={[
styles.count, styles.count,
{ {
color: color: totalTextCount > 500 ? theme.red : theme.secondary
totalTextCount > 500 ? theme.error : theme.secondary
} }
]} ]}
> >
@ -596,6 +597,7 @@ const Compose: React.FC<Props> = ({ route: { params }, navigation }) => {
</Stack.Screen> </Stack.Screen>
</Stack.Navigator> </Stack.Navigator>
</SafeAreaView> </SafeAreaView>
<Toast ref={(ref: any) => Toast.setRef(ref)} config={toastConfig} />
</KeyboardAvoidingView> </KeyboardAvoidingView>
) )
} }

View File

@ -1,17 +1,17 @@
import { Feather } from '@expo/vector-icons' import { Feather } from '@expo/vector-icons'
import React, { useCallback, useContext, useMemo } from 'react' import React, { RefObject, useCallback, useContext, useMemo } from 'react'
import { ActionSheetIOS, StyleSheet, View } from 'react-native' import { ActionSheetIOS, StyleSheet, TextInput, View } from 'react-native'
import { StyleConstants } from '@utils/styles/constants' import { StyleConstants } from '@utils/styles/constants'
import { useTheme } from '@utils/styles/ThemeManager' import { useTheme } from '@utils/styles/ThemeManager'
import { ComposeContext } from '@screens/Shared/Compose' import { ComposeContext } from '@screens/Shared/Compose'
import addAttachments from '@screens/Shared/Compose/addAttachments' import addAttachments from '@screens/Shared/Compose/addAttachments'
import { toast } from '@root/components/toast'
const ComposeActions: React.FC = () => { const ComposeActions: React.FC = () => {
const { composeState, composeDispatch } = useContext(ComposeContext) const { composeState, composeDispatch } = useContext(ComposeContext)
const { theme } = useTheme() const { theme } = useTheme()
const attachmentColor = useMemo(() => { const attachmentColor = useMemo(() => {
if (composeState.poll.active) return theme.disabled
if (composeState.attachmentUploadProgress) return theme.primary if (composeState.attachmentUploadProgress) return theme.primary
if (composeState.attachments.uploads.length) { if (composeState.attachments.uploads.length) {
@ -25,7 +25,13 @@ const ComposeActions: React.FC = () => {
composeState.attachmentUploadProgress composeState.attachmentUploadProgress
]) ])
const attachmentOnPress = useCallback(async () => { const attachmentOnPress = useCallback(async () => {
if (composeState.poll.active) return if (composeState.poll.active) {
toast({
type: 'error',
content: '长毛象不支持同时发布附件及投票'
})
return
}
if (composeState.attachmentUploadProgress) return if (composeState.attachmentUploadProgress) return
if (!composeState.attachments.uploads.length) { if (!composeState.attachments.uploads.length) {
@ -38,9 +44,6 @@ const ComposeActions: React.FC = () => {
]) ])
const pollColor = useMemo(() => { const pollColor = useMemo(() => {
if (composeState.attachments.uploads.length) return theme.disabled
if (composeState.attachmentUploadProgress) return theme.disabled
if (composeState.poll.active) { if (composeState.poll.active) {
return theme.primary return theme.primary
} else { } else {
@ -52,6 +55,17 @@ const ComposeActions: React.FC = () => {
composeState.attachmentUploadProgress composeState.attachmentUploadProgress
]) ])
const pollOnPress = useCallback(() => { const pollOnPress = useCallback(() => {
if (
composeState.attachments.uploads.length ||
composeState.attachmentUploadProgress
) {
toast({
type: 'error',
content: '长毛象不支持同时发布附件及投票'
})
return
}
if ( if (
!composeState.attachments.uploads.length && !composeState.attachments.uploads.length &&
!composeState.attachmentUploadProgress !composeState.attachmentUploadProgress
@ -82,9 +96,8 @@ const ComposeActions: React.FC = () => {
return 'mail' return 'mail'
} }
}, [composeState.visibility]) }, [composeState.visibility])
const visibilityOnPress = useCallback( const visibilityOnPress = useCallback(() => {
() => if (!composeState.visibilityLock) {
!composeState.visibilityLock &&
ActionSheetIOS.showActionSheetWithOptions( ActionSheetIOS.showActionSheetWithOptions(
{ {
options: ['公开', '不公开', '仅关注着', '私信', '取消'], options: ['公开', '不公开', '仅关注着', '私信', '取消'],
@ -106,21 +119,21 @@ const ComposeActions: React.FC = () => {
break break
} }
} }
), )
[] }
) }, [])
const spoilerOnPress = useCallback( const spoilerOnPress = useCallback(() => {
() => if (composeState.spoiler.active) {
composeDispatch({ composeState.textInputFocus.refs.text.current?.focus()
type: 'spoiler', }
payload: { active: !composeState.spoiler.active } composeDispatch({
}), type: 'spoiler',
[composeState.spoiler.active] payload: { active: !composeState.spoiler.active }
) })
}, [composeState.spoiler.active, composeState.textInputFocus])
const emojiColor = useMemo(() => { const emojiColor = useMemo(() => {
if (!composeState.emoji.emojis) return theme.disabled
if (composeState.emoji.active) { if (composeState.emoji.active) {
return theme.primary return theme.primary
} else { } else {
@ -128,6 +141,14 @@ const ComposeActions: React.FC = () => {
} }
}, [composeState.emoji.active, composeState.emoji.emojis]) }, [composeState.emoji.active, composeState.emoji.emojis])
const emojiOnPress = useCallback(() => { const emojiOnPress = useCallback(() => {
if (!composeState.emoji.emojis) {
toast({
type: 'error',
content: '提取emoji错误'
})
return
}
if (composeState.emoji.emojis) { if (composeState.emoji.emojis) {
if (composeState.emoji.active) { if (composeState.emoji.active) {
composeDispatch({ composeDispatch({
@ -165,7 +186,7 @@ const ComposeActions: React.FC = () => {
<Feather <Feather
name={visibilityIcon} name={visibilityIcon}
size={24} size={24}
color={composeState.visibilityLock ? theme.disabled : theme.secondary} color={composeState.visibilityLock ? theme.primary : theme.secondary}
onPress={visibilityOnPress} onPress={visibilityOnPress}
/> />
<Feather <Feather

View File

@ -59,7 +59,7 @@ const ComposePoll: React.FC = () => {
styles.textInput, styles.textInput,
{ {
borderColor: theme.border, borderColor: theme.border,
color: hasConflict ? theme.error : theme.primary color: hasConflict ? theme.red : theme.primary
} }
]} ]}
placeholder={`选项`} placeholder={`选项`}

View File

@ -31,7 +31,10 @@ const ComposeReply: React.FC = () => {
<TimelineContent status={replyToStatus!} /> <TimelineContent status={replyToStatus!} />
)} )}
{replyToStatus!.media_attachments.length > 0 && ( {replyToStatus!.media_attachments.length > 0 && (
<TimelineAttachment status={replyToStatus!} width={contentWidth} /> <TimelineAttachment
status={replyToStatus!}
contentWidth={contentWidth}
/>
)} )}
{replyToStatus!.card && <TimelineCard card={replyToStatus!.card} />} {replyToStatus!.card && <TimelineCard card={replyToStatus!.card} />}
</View> </View>

View File

@ -40,19 +40,15 @@ const ListItem = React.memo(
({ ({
item, item,
composeState, composeState,
composeDispatch, composeDispatch
textInputRef
}: { }: {
item: Mastodon.Account & Mastodon.Tag item: Mastodon.Account & Mastodon.Tag
composeState: ComposeState composeState: ComposeState
composeDispatch: Dispatch<ComposeAction> composeDispatch: Dispatch<ComposeAction>
textInputRef: RefObject<TextInput>
}) => { }) => {
const { theme } = useTheme() const { theme } = useTheme()
const onPress = useCallback(() => { const onPress = useCallback(() => {
const focusedInput = textInputRef.current?.isFocused() const focusedInput = composeState.textInputFocus.current
? 'text'
: 'spoiler'
updateText({ updateText({
composeState: { composeState: {
...composeState, ...composeState,
@ -161,8 +157,6 @@ const ComposeRoot: React.FC = () => {
} }
}, [emojisData]) }, [emojisData])
const textInputRef = useRef<TextInput>(null)
const listEmpty = useMemo(() => { const listEmpty = useMemo(() => {
if (isFetching) { if (isFetching) {
return <ActivityIndicator /> return <ActivityIndicator />
@ -180,7 +174,6 @@ const ComposeRoot: React.FC = () => {
item={item} item={item}
composeState={composeState} composeState={composeState}
composeDispatch={composeDispatch} composeDispatch={composeDispatch}
textInputRef={textInputRef}
/> />
) : null, ) : null,
[isSuccess] [isSuccess]

View File

@ -9,7 +9,7 @@ import ComposeReply from '@screens/Shared/Compose/Reply'
const ComposeRootFooter: React.FC = () => { const ComposeRootFooter: React.FC = () => {
const { composeState } = useContext(ComposeContext) const { composeState } = useContext(ComposeContext)
console.log(composeState)
return ( return (
<> <>
{composeState.emoji.active && ( {composeState.emoji.active && (

View File

@ -44,6 +44,12 @@ const ComposeSpoilerInput: React.FC = () => {
}} }}
ref={composeState.textInputFocus.refs.spoiler} ref={composeState.textInputFocus.refs.spoiler}
scrollEnabled scrollEnabled
onFocus={() =>
composeDispatch({
type: 'textInputFocus',
payload: { current: 'spoiler' }
})
}
> >
<Text>{composeState.spoiler.formatted}</Text> <Text>{composeState.spoiler.formatted}</Text>
</TextInput> </TextInput>

View File

@ -1,4 +1,4 @@
import React, { useContext } from 'react' import React, { useCallback, useContext } from 'react'
import { StyleSheet, Text, TextInput } from 'react-native' import { StyleSheet, Text, TextInput } from 'react-native'
import { StyleConstants } from '@utils/styles/constants' import { StyleConstants } from '@utils/styles/constants'
import { useTheme } from '@utils/styles/ThemeManager' import { useTheme } from '@utils/styles/ThemeManager'

View File

@ -17,7 +17,7 @@ export interface Params {
const TagText = ({ text }: { text: string }) => { const TagText = ({ text }: { text: string }) => {
const { theme } = useTheme() const { theme } = useTheme()
return <Text style={{ color: theme.link }}>{text}</Text> return <Text style={{ color: theme.blue }}>{text}</Text>
} }
const debouncedSuggestions = debounce( const debouncedSuggestions = debounce(

View File

@ -128,7 +128,6 @@ export const timelineFetch = async ({
return Promise.resolve({ toots: res.body }) return Promise.resolve({ toots: res.body })
case 'Account_Media': case 'Account_Media':
console.log(account)
res = await client({ res = await client({
method: 'get', method: 'get',
instance: 'local', instance: 'local',

View File

@ -4,17 +4,14 @@ export type ColorDefinitions =
| 'primary' | 'primary'
| 'primaryOverlay' | 'primaryOverlay'
| 'secondary' | 'secondary'
| 'disabled' | 'blue'
| 'red'
| 'background' | 'background'
| 'backgroundGradientStart' | 'backgroundGradientStart'
| 'backgroundGradientEnd' | 'backgroundGradientEnd'
| 'backgroundOverlay' | 'backgroundOverlay'
| 'link'
| 'border' | 'border'
| 'separator' | 'separator'
| 'success'
| 'error'
| 'warning'
const themeColors: { const themeColors: {
[key in ColorDefinitions]: { [key in ColorDefinitions]: {
@ -23,41 +20,42 @@ const themeColors: {
} }
} = { } = {
primary: { primary: {
light: 'rgb(0, 0, 0)', light: 'rgb(18, 18, 18)',
dark: 'rgb(255, 255, 255)' dark: 'rgb(218, 218, 218)'
}, },
primaryOverlay: { primaryOverlay: {
light: 'rgb(255, 255, 255)', light: 'rgb(250, 250, 250)',
dark: 'rgb(0, 0, 0)' dark: 'rgb(218, 218, 218)'
}, },
secondary: { secondary: {
light: 'rgb(153, 153, 153)', light: 'rgb(135, 135, 135)',
dark: 'rgb(117, 117, 117)' dark: 'rgb(135, 135, 135)'
}, },
disabled: { blue: {
light: 'rgb(229, 229, 234)', light: 'rgb(43, 144, 221)',
dark: 'rgb(44, 44, 46)' dark: 'rgb(43, 144, 221)'
}, },
red: {
light: 'rgb(225, 45, 35)',
dark: 'rgb(225, 98, 89)'
},
background: { background: {
light: 'rgb(255, 255, 255)', light: 'rgb(250, 250, 250)',
dark: 'rgb(0, 0, 0)' dark: 'rgb(18, 18, 18)'
}, },
backgroundGradientStart: { backgroundGradientStart: {
light: 'rgba(255, 255, 255, 0.5)', light: 'rgba(250, 250, 250, 0.5)',
dark: 'rgba(0, 0, 0, 0.5)' dark: 'rgba(18, 18, 18, 0.5)'
}, },
backgroundGradientEnd: { backgroundGradientEnd: {
light: 'rgba(255, 255, 255, 1)', light: 'rgba(250, 250, 250, 1)',
dark: 'rgba(0, 0, 0, 1)' dark: 'rgba(18, 18, 18, 1)'
}, },
backgroundOverlay: { backgroundOverlay: {
light: 'rgba(0, 0, 0, 0.5)', light: 'rgba(18, 18, 18, 0.5)',
dark: 'rgba(255, 255, 255, 0.5)' dark: 'rgba(255, 255, 255, 0.5)'
}, },
link: {
light: 'rgb(0, 122, 255)',
dark: 'rgb(10, 132, 255)'
},
border: { border: {
light: 'rgba(0, 0, 0, 0.3)', light: 'rgba(0, 0, 0, 0.3)',
dark: 'rgba(255, 255, 255, 0.16)' dark: 'rgba(255, 255, 255, 0.16)'
@ -65,18 +63,6 @@ const themeColors: {
separator: { separator: {
light: 'rgba(0, 0, 0, 0.1)', light: 'rgba(0, 0, 0, 0.1)',
dark: 'rgba(255, 255, 255, 0.1)' dark: 'rgba(255, 255, 255, 0.1)'
},
success: {
light: 'rgb(52, 199, 89)',
dark: 'rgb(48, 209, 88)'
},
error: {
light: 'rgb(255, 59, 48)',
dark: 'rgb(255, 69, 58)'
},
warning: {
light: 'rgb(255, 149, 0)',
dark: 'rgb(255, 159, 10)'
} }
} }