[ALF] Theme & palette cleanup (#4769)
* Invert primary scale * Invert negative palette * Replace theme specific styles in Toggle * Remove theme specific colors from Button, improves secondary solid on dark mode * TextField * Remove from MessageItem * Threadgate editor * IconCircle * Muted words * Generate themes from hues * Cleanup * Deprecate more values, fix circular import * Invert positive too, hardly use * Button tweaks, some theme diffs * Match disabled state for negative button * Fix unread noty bgzio/stable
parent
ea0586cd67
commit
74186950b2
|
@ -1,7 +1,9 @@
|
|||
import React from 'react'
|
||||
import {Dimensions} from 'react-native'
|
||||
|
||||
import * as themes from '#/alf/themes'
|
||||
import {createThemes, defaultTheme} from '#/alf/themes'
|
||||
import {Theme, ThemeName} from '#/alf/types'
|
||||
import {BLUE_HUE, GREEN_HUE, RED_HUE} from '#/alf/util/colorGeneration'
|
||||
|
||||
export {atoms} from '#/alf/atoms'
|
||||
export * as tokens from '#/alf/tokens'
|
||||
|
@ -39,8 +41,8 @@ function getActiveBreakpoints({width}: {width: number}) {
|
|||
* Context
|
||||
*/
|
||||
export const Context = React.createContext<{
|
||||
themeName: themes.ThemeName
|
||||
theme: themes.Theme
|
||||
themeName: ThemeName
|
||||
theme: Theme
|
||||
breakpoints: {
|
||||
active: BreakpointName | undefined
|
||||
gtPhone: boolean
|
||||
|
@ -49,7 +51,7 @@ export const Context = React.createContext<{
|
|||
}
|
||||
}>({
|
||||
themeName: 'light',
|
||||
theme: themes.light,
|
||||
theme: defaultTheme,
|
||||
breakpoints: {
|
||||
active: undefined,
|
||||
gtPhone: false,
|
||||
|
@ -61,7 +63,16 @@ export const Context = React.createContext<{
|
|||
export function ThemeProvider({
|
||||
children,
|
||||
theme: themeName,
|
||||
}: React.PropsWithChildren<{theme: themes.ThemeName}>) {
|
||||
}: React.PropsWithChildren<{theme: ThemeName}>) {
|
||||
const themes = React.useMemo(() => {
|
||||
return createThemes({
|
||||
hues: {
|
||||
primary: BLUE_HUE,
|
||||
negative: RED_HUE,
|
||||
positive: GREEN_HUE,
|
||||
},
|
||||
})
|
||||
}, [])
|
||||
const theme = themes[themeName]
|
||||
const [breakpoints, setBreakpoints] = React.useState(() =>
|
||||
getActiveBreakpoints({width: Dimensions.get('window').width}),
|
||||
|
|
1016
src/alf/themes.ts
1016
src/alf/themes.ts
File diff suppressed because it is too large
Load Diff
|
@ -1,77 +1,6 @@
|
|||
import {
|
||||
BLUE_HUE,
|
||||
generateScale,
|
||||
GREEN_HUE,
|
||||
RED_HUE,
|
||||
} from '#/alf/util/colorGeneration'
|
||||
|
||||
export const scale = generateScale(6, 100)
|
||||
// dim shifted 6% lighter
|
||||
export const dimScale = generateScale(12, 100)
|
||||
|
||||
export const color = {
|
||||
trueBlack: '#000000',
|
||||
|
||||
temp_purple: 'rgb(105 0 255)',
|
||||
temp_purple_dark: 'rgb(83 0 202)',
|
||||
|
||||
gray_0: `hsl(${BLUE_HUE}, 20%, ${scale[14]}%)`,
|
||||
gray_25: `hsl(${BLUE_HUE}, 20%, ${scale[13]}%)`,
|
||||
gray_50: `hsl(${BLUE_HUE}, 20%, ${scale[12]}%)`,
|
||||
gray_100: `hsl(${BLUE_HUE}, 20%, ${scale[11]}%)`,
|
||||
gray_200: `hsl(${BLUE_HUE}, 20%, ${scale[10]}%)`,
|
||||
gray_300: `hsl(${BLUE_HUE}, 20%, ${scale[9]}%)`,
|
||||
gray_400: `hsl(${BLUE_HUE}, 20%, ${scale[8]}%)`,
|
||||
gray_500: `hsl(${BLUE_HUE}, 20%, ${scale[7]}%)`,
|
||||
gray_600: `hsl(${BLUE_HUE}, 24%, ${scale[6]}%)`,
|
||||
gray_700: `hsl(${BLUE_HUE}, 24%, ${scale[5]}%)`,
|
||||
gray_800: `hsl(${BLUE_HUE}, 28%, ${scale[4]}%)`,
|
||||
gray_900: `hsl(${BLUE_HUE}, 28%, ${scale[3]}%)`,
|
||||
gray_950: `hsl(${BLUE_HUE}, 28%, ${scale[2]}%)`,
|
||||
gray_975: `hsl(${BLUE_HUE}, 28%, ${scale[1]}%)`,
|
||||
gray_1000: `hsl(${BLUE_HUE}, 28%, ${scale[0]}%)`,
|
||||
|
||||
blue_25: `hsl(${BLUE_HUE}, 99%, 97%)`,
|
||||
blue_50: `hsl(${BLUE_HUE}, 99%, 95%)`,
|
||||
blue_100: `hsl(${BLUE_HUE}, 99%, 90%)`,
|
||||
blue_200: `hsl(${BLUE_HUE}, 99%, 80%)`,
|
||||
blue_300: `hsl(${BLUE_HUE}, 99%, 70%)`,
|
||||
blue_400: `hsl(${BLUE_HUE}, 99%, 60%)`,
|
||||
blue_500: `hsl(${BLUE_HUE}, 99%, 53%)`,
|
||||
blue_600: `hsl(${BLUE_HUE}, 99%, 42%)`,
|
||||
blue_700: `hsl(${BLUE_HUE}, 99%, 34%)`,
|
||||
blue_800: `hsl(${BLUE_HUE}, 99%, 26%)`,
|
||||
blue_900: `hsl(${BLUE_HUE}, 99%, 18%)`,
|
||||
blue_950: `hsl(${BLUE_HUE}, 99%, 10%)`,
|
||||
blue_975: `hsl(${BLUE_HUE}, 99%, 7%)`,
|
||||
|
||||
green_25: `hsl(${GREEN_HUE}, 82%, 97%)`,
|
||||
green_50: `hsl(${GREEN_HUE}, 82%, 95%)`,
|
||||
green_100: `hsl(${GREEN_HUE}, 82%, 90%)`,
|
||||
green_200: `hsl(${GREEN_HUE}, 82%, 80%)`,
|
||||
green_300: `hsl(${GREEN_HUE}, 82%, 70%)`,
|
||||
green_400: `hsl(${GREEN_HUE}, 82%, 60%)`,
|
||||
green_500: `hsl(${GREEN_HUE}, 82%, 50%)`,
|
||||
green_600: `hsl(${GREEN_HUE}, 82%, 42%)`,
|
||||
green_700: `hsl(${GREEN_HUE}, 82%, 34%)`,
|
||||
green_800: `hsl(${GREEN_HUE}, 82%, 26%)`,
|
||||
green_900: `hsl(${GREEN_HUE}, 82%, 18%)`,
|
||||
green_950: `hsl(${GREEN_HUE}, 82%, 10%)`,
|
||||
green_975: `hsl(${GREEN_HUE}, 82%, 7%)`,
|
||||
|
||||
red_25: `hsl(${RED_HUE}, 91%, 97%)`,
|
||||
red_50: `hsl(${RED_HUE}, 91%, 95%)`,
|
||||
red_100: `hsl(${RED_HUE}, 91%, 90%)`,
|
||||
red_200: `hsl(${RED_HUE}, 91%, 80%)`,
|
||||
red_300: `hsl(${RED_HUE}, 91%, 70%)`,
|
||||
red_400: `hsl(${RED_HUE}, 91%, 60%)`,
|
||||
red_500: `hsl(${RED_HUE}, 91%, 50%)`,
|
||||
red_600: `hsl(${RED_HUE}, 91%, 42%)`,
|
||||
red_700: `hsl(${RED_HUE}, 91%, 34%)`,
|
||||
red_800: `hsl(${RED_HUE}, 91%, 26%)`,
|
||||
red_900: `hsl(${RED_HUE}, 91%, 18%)`,
|
||||
red_950: `hsl(${RED_HUE}, 91%, 10%)`,
|
||||
red_975: `hsl(${RED_HUE}, 91%, 7%)`,
|
||||
} as const
|
||||
|
||||
export const space = {
|
||||
|
@ -178,10 +107,3 @@ export const gradients = {
|
|||
hover_value: '#755B62',
|
||||
},
|
||||
} as const
|
||||
|
||||
export type Color = keyof typeof color
|
||||
export type Space = keyof typeof space
|
||||
export type FontSize = keyof typeof fontSize
|
||||
export type LineHeight = keyof typeof lineHeight
|
||||
export type BorderRadius = keyof typeof borderRadius
|
||||
export type FontWeight = keyof typeof fontWeight
|
||||
|
|
172
src/alf/types.ts
172
src/alf/types.ts
|
@ -1,21 +1,4 @@
|
|||
import {StyleProp, ViewStyle, TextStyle} from 'react-native'
|
||||
|
||||
type LiteralToCommon<T extends PropertyKey> = T extends number
|
||||
? number
|
||||
: T extends string
|
||||
? string
|
||||
: T extends symbol
|
||||
? symbol
|
||||
: never
|
||||
|
||||
/**
|
||||
* @see https://stackoverflow.com/questions/68249999/use-as-const-in-typescript-without-adding-readonly-modifiers
|
||||
*/
|
||||
export type Mutable<T> = {
|
||||
-readonly [K in keyof T]: T[K] extends PropertyKey
|
||||
? LiteralToCommon<T[K]>
|
||||
: Mutable<T[K]>
|
||||
}
|
||||
import {StyleProp, TextStyle, ViewStyle} from 'react-native'
|
||||
|
||||
export type TextStyleProp = {
|
||||
style?: StyleProp<TextStyle>
|
||||
|
@ -24,3 +7,156 @@ export type TextStyleProp = {
|
|||
export type ViewStyleProp = {
|
||||
style?: StyleProp<ViewStyle>
|
||||
}
|
||||
|
||||
export type ThemeName = 'light' | 'dim' | 'dark'
|
||||
export type Palette = {
|
||||
white: string
|
||||
black: string
|
||||
|
||||
contrast_25: string
|
||||
contrast_50: string
|
||||
contrast_100: string
|
||||
contrast_200: string
|
||||
contrast_300: string
|
||||
contrast_400: string
|
||||
contrast_500: string
|
||||
contrast_600: string
|
||||
contrast_700: string
|
||||
contrast_800: string
|
||||
contrast_900: string
|
||||
contrast_950: string
|
||||
contrast_975: string
|
||||
|
||||
primary_25: string
|
||||
primary_50: string
|
||||
primary_100: string
|
||||
primary_200: string
|
||||
primary_300: string
|
||||
primary_400: string
|
||||
primary_500: string
|
||||
primary_600: string
|
||||
primary_700: string
|
||||
primary_800: string
|
||||
primary_900: string
|
||||
primary_950: string
|
||||
primary_975: string
|
||||
|
||||
positive_25: string
|
||||
positive_50: string
|
||||
positive_100: string
|
||||
positive_200: string
|
||||
positive_300: string
|
||||
positive_400: string
|
||||
positive_500: string
|
||||
positive_600: string
|
||||
positive_700: string
|
||||
positive_800: string
|
||||
positive_900: string
|
||||
positive_950: string
|
||||
positive_975: string
|
||||
|
||||
negative_25: string
|
||||
negative_50: string
|
||||
negative_100: string
|
||||
negative_200: string
|
||||
negative_300: string
|
||||
negative_400: string
|
||||
negative_500: string
|
||||
negative_600: string
|
||||
negative_700: string
|
||||
negative_800: string
|
||||
negative_900: string
|
||||
negative_950: string
|
||||
negative_975: string
|
||||
}
|
||||
export type ThemedAtoms = {
|
||||
text: {
|
||||
color: string
|
||||
}
|
||||
text_contrast_low: {
|
||||
color: string
|
||||
}
|
||||
text_contrast_medium: {
|
||||
color: string
|
||||
}
|
||||
text_contrast_high: {
|
||||
color: string
|
||||
}
|
||||
text_inverted: {
|
||||
color: string
|
||||
}
|
||||
bg: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_25: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_50: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_100: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_200: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_300: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_400: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_500: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_600: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_700: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_800: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_900: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_950: {
|
||||
backgroundColor: string
|
||||
}
|
||||
bg_contrast_975: {
|
||||
backgroundColor: string
|
||||
}
|
||||
border_contrast_low: {
|
||||
borderColor: string
|
||||
}
|
||||
border_contrast_medium: {
|
||||
borderColor: string
|
||||
}
|
||||
border_contrast_high: {
|
||||
borderColor: string
|
||||
}
|
||||
shadow_sm: {
|
||||
shadowRadius: number
|
||||
shadowOpacity: number
|
||||
elevation: number
|
||||
shadowColor: string
|
||||
}
|
||||
shadow_md: {
|
||||
shadowRadius: number
|
||||
shadowOpacity: number
|
||||
elevation: number
|
||||
shadowColor: string
|
||||
}
|
||||
shadow_lg: {
|
||||
shadowRadius: number
|
||||
shadowOpacity: number
|
||||
elevation: number
|
||||
shadowColor: string
|
||||
}
|
||||
}
|
||||
export type Theme = {
|
||||
name: ThemeName
|
||||
palette: Palette
|
||||
atoms: ThemedAtoms
|
||||
}
|
||||
|
|
|
@ -15,3 +15,7 @@ export function generateScale(start: number, end: number) {
|
|||
return start + range * stop
|
||||
})
|
||||
}
|
||||
|
||||
export const defaultScale = generateScale(6, 100)
|
||||
// dim shifted 6% lighter
|
||||
export const dimScale = generateScale(12, 100)
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import {ThemeName} from '#/alf/themes'
|
||||
import {ThemeName} from '#/alf/types'
|
||||
|
||||
export function select<T>(name: ThemeName, options: Record<ThemeName, T>) {
|
||||
switch (name) {
|
||||
|
|
|
@ -4,7 +4,8 @@ import * as SystemUI from 'expo-system-ui'
|
|||
|
||||
import {isWeb} from 'platform/detection'
|
||||
import {useThemePrefs} from 'state/shell'
|
||||
import {dark, dim, light, ThemeName} from '#/alf/themes'
|
||||
import {dark, dim, light} from '#/alf/themes'
|
||||
import {ThemeName} from '#/alf/types'
|
||||
|
||||
export function useColorModeTheme(): ThemeName {
|
||||
const theme = useThemeName()
|
||||
|
|
|
@ -13,7 +13,7 @@ import {
|
|||
} from 'react-native'
|
||||
import {LinearGradient} from 'expo-linear-gradient'
|
||||
|
||||
import {android, atoms as a, flatten, tokens, useTheme} from '#/alf'
|
||||
import {android, atoms as a, flatten, select, tokens, useTheme} from '#/alf'
|
||||
import {Props as SVGIconProps} from '#/components/icons/common'
|
||||
import {normalizeTextStyles} from '#/components/Typography'
|
||||
|
||||
|
@ -152,7 +152,6 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
const {baseStyles, hoverStyles} = React.useMemo(() => {
|
||||
const baseStyles: ViewStyle[] = []
|
||||
const hoverStyles: ViewStyle[] = []
|
||||
const light = t.name === 'light'
|
||||
|
||||
if (color === 'primary') {
|
||||
if (variant === 'solid') {
|
||||
|
@ -165,7 +164,11 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
})
|
||||
} else {
|
||||
baseStyles.push({
|
||||
backgroundColor: t.palette.primary_700,
|
||||
backgroundColor: select(t.name, {
|
||||
light: t.palette.primary_700,
|
||||
dim: t.palette.primary_300,
|
||||
dark: t.palette.primary_300,
|
||||
}),
|
||||
})
|
||||
}
|
||||
} else if (variant === 'outline') {
|
||||
|
@ -178,24 +181,18 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
borderColor: t.palette.primary_500,
|
||||
})
|
||||
hoverStyles.push(a.border, {
|
||||
backgroundColor: light
|
||||
? t.palette.primary_50
|
||||
: t.palette.primary_950,
|
||||
backgroundColor: t.palette.primary_50,
|
||||
})
|
||||
} else {
|
||||
baseStyles.push(a.border, {
|
||||
borderColor: light
|
||||
? t.palette.primary_200
|
||||
: t.palette.primary_900,
|
||||
borderColor: t.palette.primary_200,
|
||||
})
|
||||
}
|
||||
} else if (variant === 'ghost') {
|
||||
if (!disabled) {
|
||||
baseStyles.push(t.atoms.bg)
|
||||
hoverStyles.push({
|
||||
backgroundColor: light
|
||||
? t.palette.primary_100
|
||||
: t.palette.primary_900,
|
||||
backgroundColor: t.palette.primary_100,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
@ -203,14 +200,26 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
if (variant === 'solid') {
|
||||
if (!disabled) {
|
||||
baseStyles.push({
|
||||
backgroundColor: t.palette.contrast_25,
|
||||
backgroundColor: select(t.name, {
|
||||
light: t.palette.contrast_25,
|
||||
dim: t.palette.contrast_100,
|
||||
dark: t.palette.contrast_100,
|
||||
}),
|
||||
})
|
||||
hoverStyles.push({
|
||||
backgroundColor: t.palette.contrast_50,
|
||||
backgroundColor: select(t.name, {
|
||||
light: t.palette.contrast_50,
|
||||
dim: t.palette.contrast_200,
|
||||
dark: t.palette.contrast_200,
|
||||
}),
|
||||
})
|
||||
} else {
|
||||
baseStyles.push({
|
||||
backgroundColor: t.palette.contrast_100,
|
||||
backgroundColor: select(t.name, {
|
||||
light: t.palette.contrast_100,
|
||||
dim: t.palette.contrast_25,
|
||||
dark: t.palette.contrast_25,
|
||||
}),
|
||||
})
|
||||
}
|
||||
} else if (variant === 'outline') {
|
||||
|
@ -247,7 +256,7 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
})
|
||||
} else {
|
||||
baseStyles.push({
|
||||
backgroundColor: t.palette.contrast_700,
|
||||
backgroundColor: t.palette.contrast_600,
|
||||
})
|
||||
}
|
||||
} else if (variant === 'outline') {
|
||||
|
@ -284,7 +293,11 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
})
|
||||
} else {
|
||||
baseStyles.push({
|
||||
backgroundColor: t.palette.negative_700,
|
||||
backgroundColor: select(t.name, {
|
||||
light: t.palette.negative_700,
|
||||
dim: t.palette.negative_300,
|
||||
dark: t.palette.negative_300,
|
||||
}),
|
||||
})
|
||||
}
|
||||
} else if (variant === 'outline') {
|
||||
|
@ -297,24 +310,18 @@ export const Button = React.forwardRef<View, ButtonProps>(
|
|||
borderColor: t.palette.negative_500,
|
||||
})
|
||||
hoverStyles.push(a.border, {
|
||||
backgroundColor: light
|
||||
? t.palette.negative_50
|
||||
: t.palette.negative_975,
|
||||
backgroundColor: t.palette.negative_50,
|
||||
})
|
||||
} else {
|
||||
baseStyles.push(a.border, {
|
||||
borderColor: light
|
||||
? t.palette.negative_200
|
||||
: t.palette.negative_900,
|
||||
borderColor: t.palette.negative_200,
|
||||
})
|
||||
}
|
||||
} else if (variant === 'ghost') {
|
||||
if (!disabled) {
|
||||
baseStyles.push(t.atoms.bg)
|
||||
hoverStyles.push({
|
||||
backgroundColor: light
|
||||
? t.palette.negative_100
|
||||
: t.palette.negative_975,
|
||||
backgroundColor: t.palette.negative_100,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
@ -482,7 +489,6 @@ export function useSharedButtonTextStyles() {
|
|||
const {color, variant, disabled, size} = useButtonContext()
|
||||
return React.useMemo(() => {
|
||||
const baseStyles: TextStyle[] = []
|
||||
const light = t.name === 'light'
|
||||
|
||||
if (color === 'primary') {
|
||||
if (variant === 'solid') {
|
||||
|
@ -494,7 +500,7 @@ export function useSharedButtonTextStyles() {
|
|||
} else if (variant === 'outline') {
|
||||
if (!disabled) {
|
||||
baseStyles.push({
|
||||
color: light ? t.palette.primary_600 : t.palette.primary_500,
|
||||
color: t.palette.primary_600,
|
||||
})
|
||||
} else {
|
||||
baseStyles.push({color: t.palette.primary_600, opacity: 0.5})
|
||||
|
|
|
@ -2,14 +2,14 @@ import React from 'react'
|
|||
import {View} from 'react-native'
|
||||
|
||||
import {
|
||||
useTheme,
|
||||
atoms as a,
|
||||
ViewStyleProp,
|
||||
TextStyleProp,
|
||||
flatten,
|
||||
TextStyleProp,
|
||||
useTheme,
|
||||
ViewStyleProp,
|
||||
} from '#/alf'
|
||||
import {Growth_Stroke2_Corner0_Rounded as Growth} from '#/components/icons/Growth'
|
||||
import {Props} from '#/components/icons/common'
|
||||
import {Growth_Stroke2_Corner0_Rounded as Growth} from '#/components/icons/Growth'
|
||||
|
||||
export function IconCircle({
|
||||
icon: Icon,
|
||||
|
@ -32,8 +32,7 @@ export function IconCircle({
|
|||
{
|
||||
width: size === 'lg' ? 52 : 64,
|
||||
height: size === 'lg' ? 52 : 64,
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.primary_50 : t.palette.primary_950,
|
||||
backgroundColor: t.palette.primary_50,
|
||||
},
|
||||
flatten(style),
|
||||
]}>
|
||||
|
|
|
@ -357,12 +357,11 @@ function TargetToggle({children}: React.PropsWithChildren<{}>) {
|
|||
a.px_sm,
|
||||
gtMobile && a.px_md,
|
||||
a.rounded_sm,
|
||||
t.atoms.bg_contrast_50,
|
||||
(ctx.hovered || ctx.focused) && t.atoms.bg_contrast_100,
|
||||
t.atoms.bg_contrast_25,
|
||||
(ctx.hovered || ctx.focused) && t.atoms.bg_contrast_50,
|
||||
ctx.selected && [
|
||||
{
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.primary_50 : t.palette.primary_975,
|
||||
backgroundColor: t.palette.primary_50,
|
||||
},
|
||||
],
|
||||
ctx.disabled && {
|
||||
|
|
|
@ -196,10 +196,7 @@ function Selectable({
|
|||
t.atoms.bg_contrast_50,
|
||||
(hovered || focused) && t.atoms.bg_contrast_100,
|
||||
isSelected && {
|
||||
backgroundColor:
|
||||
t.name === 'light'
|
||||
? t.palette.primary_50
|
||||
: t.palette.primary_975,
|
||||
backgroundColor: t.palette.primary_100,
|
||||
},
|
||||
style,
|
||||
]}>
|
||||
|
|
|
@ -72,8 +72,7 @@ let MessageItem = ({
|
|||
lastInGroupRef.current = isLastInGroup
|
||||
}
|
||||
|
||||
const pendingColor =
|
||||
t.name === 'light' ? t.palette.primary_200 : t.palette.primary_800
|
||||
const pendingColor = t.palette.primary_200
|
||||
|
||||
const rt = useMemo(() => {
|
||||
return new RichTextAPI({text: message.text, facets: message.facets})
|
||||
|
@ -110,12 +109,7 @@ let MessageItem = ({
|
|||
}>
|
||||
<RichText
|
||||
value={rt}
|
||||
style={[
|
||||
a.text_md,
|
||||
isFromSelf && {color: t.palette.white},
|
||||
isPending &&
|
||||
t.name !== 'light' && {color: t.palette.primary_300},
|
||||
]}
|
||||
style={[a.text_md, isFromSelf && {color: t.palette.white}]}
|
||||
interactiveStyle={a.underline}
|
||||
enableTags
|
||||
emojiMultiplier={3}
|
||||
|
|
|
@ -101,16 +101,13 @@ export function useSharedInputStyles() {
|
|||
]
|
||||
const error: ViewStyle[] = [
|
||||
{
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.negative_25 : t.palette.negative_900,
|
||||
borderColor:
|
||||
t.name === 'light' ? t.palette.negative_300 : t.palette.negative_800,
|
||||
backgroundColor: t.palette.negative_25,
|
||||
borderColor: t.palette.negative_300,
|
||||
},
|
||||
]
|
||||
const errorHover: ViewStyle[] = [
|
||||
{
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.negative_25 : t.palette.negative_900,
|
||||
backgroundColor: t.palette.negative_25,
|
||||
borderColor: t.palette.negative_500,
|
||||
},
|
||||
]
|
||||
|
|
|
@ -281,24 +281,20 @@ export function createSharedToggleStyles({
|
|||
|
||||
if (selected) {
|
||||
base.push({
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.primary_25 : t.palette.primary_900,
|
||||
backgroundColor: t.palette.primary_25,
|
||||
borderColor: t.palette.primary_500,
|
||||
})
|
||||
|
||||
if (hovered) {
|
||||
baseHover.push({
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.primary_100 : t.palette.primary_800,
|
||||
borderColor:
|
||||
t.name === 'light' ? t.palette.primary_600 : t.palette.primary_400,
|
||||
backgroundColor: t.palette.primary_100,
|
||||
borderColor: t.palette.primary_600,
|
||||
})
|
||||
}
|
||||
} else {
|
||||
if (hovered) {
|
||||
baseHover.push({
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.contrast_50 : t.palette.contrast_100,
|
||||
backgroundColor: t.palette.contrast_50,
|
||||
borderColor: t.palette.contrast_500,
|
||||
})
|
||||
}
|
||||
|
@ -306,16 +302,13 @@ export function createSharedToggleStyles({
|
|||
|
||||
if (isInvalid) {
|
||||
base.push({
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.negative_25 : t.palette.negative_975,
|
||||
borderColor:
|
||||
t.name === 'light' ? t.palette.negative_300 : t.palette.negative_800,
|
||||
backgroundColor: t.palette.negative_25,
|
||||
borderColor: t.palette.negative_300,
|
||||
})
|
||||
|
||||
if (hovered) {
|
||||
baseHover.push({
|
||||
backgroundColor:
|
||||
t.name === 'light' ? t.palette.negative_25 : t.palette.negative_900,
|
||||
backgroundColor: t.palette.negative_25,
|
||||
borderColor: t.palette.negative_600,
|
||||
})
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@ import type {PathProps, SvgProps} from 'react-native-svg'
|
|||
import {Defs, LinearGradient, Stop} from 'react-native-svg'
|
||||
import {nanoid} from 'nanoid/non-secure'
|
||||
|
||||
import {tokens} from '#/alf'
|
||||
import {tokens, useTheme} from '#/alf'
|
||||
|
||||
export type Props = {
|
||||
fill?: PathProps['fill']
|
||||
|
@ -22,10 +22,11 @@ export const sizes = {
|
|||
}
|
||||
|
||||
export function useCommonSVGProps(props: Props) {
|
||||
const t = useTheme()
|
||||
const {fill, size, gradient, ...rest} = props
|
||||
const style = StyleSheet.flatten(rest.style)
|
||||
const _size = Number(size ? sizes[size] : rest.width || sizes.md)
|
||||
let _fill = fill || style?.color || tokens.color.blue_500
|
||||
let _fill = fill || style?.color || t.palette.primary_500
|
||||
let gradientDef = null
|
||||
|
||||
if (gradient && tokens.gradients[gradient]) {
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
import React, {ReactNode, createContext, useContext} from 'react'
|
||||
import React, {createContext, ReactNode, useContext} from 'react'
|
||||
import {TextStyle, ViewStyle} from 'react-native'
|
||||
|
||||
import {ThemeName} from '#/alf/types'
|
||||
import {darkTheme, defaultTheme, dimTheme} from './themes'
|
||||
import {ThemeName} from '#/alf/themes'
|
||||
|
||||
export type ColorScheme = 'light' | 'dark'
|
||||
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
import {Platform} from 'react-native'
|
||||
import type {Theme} from './ThemeContext'
|
||||
import {colors} from './styles'
|
||||
|
||||
import {darkPalette, lightPalette, dimPalette} from '#/alf/themes'
|
||||
import {darkPalette, dimPalette, lightPalette} from '#/alf/themes'
|
||||
import {colors} from './styles'
|
||||
import type {Theme} from './ThemeContext'
|
||||
|
||||
export const defaultTheme: Theme = {
|
||||
colorScheme: 'light',
|
||||
|
@ -308,8 +308,8 @@ export const darkTheme: Theme = {
|
|||
textVeryLight: darkPalette.contrast_400,
|
||||
replyLine: darkPalette.contrast_200,
|
||||
replyLineDot: darkPalette.contrast_200,
|
||||
unreadNotifBg: darkPalette.primary_975,
|
||||
unreadNotifBorder: darkPalette.primary_900,
|
||||
unreadNotifBg: darkPalette.primary_25,
|
||||
unreadNotifBorder: darkPalette.primary_100,
|
||||
postCtrl: darkPalette.contrast_500,
|
||||
brandText: darkPalette.primary_500,
|
||||
emptyStateIcon: darkPalette.contrast_300,
|
||||
|
@ -357,8 +357,8 @@ export const dimTheme: Theme = {
|
|||
textVeryLight: dimPalette.contrast_400,
|
||||
replyLine: dimPalette.contrast_200,
|
||||
replyLineDot: dimPalette.contrast_200,
|
||||
unreadNotifBg: dimPalette.primary_975,
|
||||
unreadNotifBorder: dimPalette.primary_900,
|
||||
unreadNotifBg: dimPalette.primary_25,
|
||||
unreadNotifBorder: dimPalette.primary_100,
|
||||
postCtrl: dimPalette.contrast_500,
|
||||
brandText: dimPalette.primary_500,
|
||||
emptyStateIcon: dimPalette.contrast_300,
|
||||
|
|
|
@ -20,29 +20,31 @@ export function Buttons() {
|
|||
<H1>Buttons</H1>
|
||||
|
||||
<View style={[a.flex_row, a.flex_wrap, a.gap_md, a.align_start]}>
|
||||
{['primary', 'secondary', 'secondary_inverted'].map(color => (
|
||||
<View key={color} style={[a.gap_md, a.align_start]}>
|
||||
{['solid', 'outline', 'ghost'].map(variant => (
|
||||
<React.Fragment key={variant}>
|
||||
<Button
|
||||
variant={variant as ButtonVariant}
|
||||
color={color as ButtonColor}
|
||||
size="large"
|
||||
label="Click here">
|
||||
<ButtonText>Button</ButtonText>
|
||||
</Button>
|
||||
<Button
|
||||
disabled
|
||||
variant={variant as ButtonVariant}
|
||||
color={color as ButtonColor}
|
||||
size="large"
|
||||
label="Click here">
|
||||
<ButtonText>Button</ButtonText>
|
||||
</Button>
|
||||
</React.Fragment>
|
||||
))}
|
||||
</View>
|
||||
))}
|
||||
{['primary', 'secondary', 'secondary_inverted', 'negative'].map(
|
||||
color => (
|
||||
<View key={color} style={[a.gap_md, a.align_start]}>
|
||||
{['solid', 'outline', 'ghost'].map(variant => (
|
||||
<React.Fragment key={variant}>
|
||||
<Button
|
||||
variant={variant as ButtonVariant}
|
||||
color={color as ButtonColor}
|
||||
size="large"
|
||||
label="Click here">
|
||||
<ButtonText>Button</ButtonText>
|
||||
</Button>
|
||||
<Button
|
||||
disabled
|
||||
variant={variant as ButtonVariant}
|
||||
color={color as ButtonColor}
|
||||
size="large"
|
||||
label="Click here">
|
||||
<ButtonText>Button</ButtonText>
|
||||
</Button>
|
||||
</React.Fragment>
|
||||
))}
|
||||
</View>
|
||||
),
|
||||
)}
|
||||
|
||||
<View style={[a.flex_row, a.gap_md, a.align_start]}>
|
||||
<View style={[a.gap_md, a.align_start]}>
|
||||
|
@ -68,6 +70,7 @@ export function Buttons() {
|
|||
),
|
||||
)}
|
||||
</View>
|
||||
{/*
|
||||
<View style={[a.gap_md, a.align_start]}>
|
||||
{['gradient_sunset', 'gradient_nordic', 'gradient_bonfire'].map(
|
||||
name => (
|
||||
|
@ -91,6 +94,7 @@ export function Buttons() {
|
|||
),
|
||||
)}
|
||||
</View>
|
||||
*/}
|
||||
</View>
|
||||
</View>
|
||||
|
||||
|
|
|
@ -41,6 +41,16 @@ export function Forms() {
|
|||
/>
|
||||
</TextField.Root>
|
||||
|
||||
<TextField.Root>
|
||||
<TextField.Icon icon={Globe} />
|
||||
<TextField.Input
|
||||
value={value}
|
||||
onChangeText={setValue}
|
||||
label="Text field"
|
||||
isInvalid
|
||||
/>
|
||||
</TextField.Root>
|
||||
|
||||
<View style={[a.w_full]}>
|
||||
<TextField.LabelText>Text field</TextField.LabelText>
|
||||
<TextField.Root>
|
||||
|
|
Loading…
Reference in New Issue